private int WaitForProcessToConnect(string tempDir, string text, bool attachMode = false, uint result = 0) { bool fProfiledProcessInitialized = profiledProcess != null; if (fProfiledProcessInitialized) { if (!VerifyCorrectBitness(profiledProcess)) return -1; } ConnectNamedPipe(handshakingPipeHandle, IntPtr.Zero); ConnectNamedPipe(loggingPipeHandle, IntPtr.Zero); int pid = 0; byte[] handshakingBuffer = new byte[9]; int handshakingReadBytes = 0; // IMPORTANT: maxloggingBufferSize must match bufferSize defined in ProfilerCallback.cpp. const int maxloggingBufferSize = 512; byte[] loggingBuffer = new byte[maxloggingBufferSize]; int loggingReadBytes = 0; WaitingForConnectionForm waitingForConnectionForm = null; int beginTickCount = Environment.TickCount; //Do not show the text in attachmode if (attachMode == false) { if (noUI) { Console.WriteLine(text); } else { if (waitingForConnectionForm == null) waitingForConnectionForm = new WaitingForConnectionForm(); waitingForConnectionForm.setMessage(text); waitingForConnectionForm.Visible = true; } } // loop reading two pipes, // until // (1)successfully connected // (2)User canceled // (3)attach failed // (4)target process exited while (true) { #region handshaking //(1)succeeded try { handshakingReadBytes += handshakingPipe.Read(handshakingBuffer, handshakingReadBytes, 9 - handshakingReadBytes); } catch (System.IO.IOException) { } //Read 9 bytes from handshaking pipe //means the profielr was initialized successfully if (handshakingReadBytes == 9) break; Application.DoEvents(); // (2)User canceled if (!noUI) { if (waitingForConnectionForm != null && waitingForConnectionForm.DialogResult == DialogResult.Cancel) { pid = -1; break; } } #endregion handshaking #region logging // (3)attach failed // (3.1) read logging message // (3.2) break if attach failed. // (3.1) read logging message try { loggingReadBytes += loggingPipe.Read(loggingBuffer, loggingReadBytes, maxloggingBufferSize - loggingReadBytes); } catch (System.IO.IOException) { } if (loggingReadBytes == maxloggingBufferSize) { char[] charBuffer = new char[loggingReadBytes]; for (int i = 0; i < loggingReadBytes; i++) charBuffer[i] = Convert.ToChar(loggingBuffer[i]); string message = new String(charBuffer, 0, loggingReadBytes); if (attachMode == false && noUI == false) { waitingForConnectionForm.addMessage(message); } else { ShowErrorMessage(message); } loggingReadBytes = 0; while (true) { try { if (loggingPipe.Read(loggingBuffer, 0, 1) == 0) { DisconnectNamedPipe(loggingPipeHandle); ConnectNamedPipe(loggingPipeHandle, IntPtr.Zero); break; } } catch (System.IO.IOException) { DisconnectNamedPipe(loggingPipeHandle); ConnectNamedPipe(loggingPipeHandle, IntPtr.Zero); break; } } } // (3.2) break if attach failed. if (attachMode == true && result != 0) { pid = -1; break; } #endregion logging // (4)target process exited if ((fProfiledProcessInitialized && profiledProcess == null) || (profiledProcess != null && ProfiledProcessHasExited())) { pid = -1; break; } Thread.Sleep(100); } if (waitingForConnectionForm != null) waitingForConnectionForm.Visible = false; if (pid == -1) return pid; if (handshakingReadBytes == 9) { char[] charBuffer = new char[9]; for (int i = 0; i < handshakingBuffer.Length; i++) charBuffer[i] = Convert.ToChar(handshakingBuffer[i]); pid = Int32.Parse(new String(charBuffer, 0, 8), NumberStyles.HexNumber); CreateEvents(pid); string fileName = getLogFileName(pid); byte[] fileNameBuffer = new Byte[fileName.Length + 1]; for (int i = 0; i < fileName.Length; i++) fileNameBuffer[i] = (byte)fileName[i]; fileNameBuffer[fileName.Length] = 0; handshakingPipe.Write(fileNameBuffer, 0, fileNameBuffer.Length); handshakingPipe.Flush(); logFileName = tempDir + "\\" + fileName; log = new ReadNewLog(logFileName); lastLogResult = null; ObjectGraph.cachedGraph = null; while (true) { try { if (handshakingPipe.Read(handshakingBuffer, 0, 1) == 0) // && GetLastError() == 109/*ERROR_BROKEN_PIPE*/) { DisconnectNamedPipe(handshakingPipeHandle); ConnectNamedPipe(handshakingPipeHandle, IntPtr.Zero); break; } } catch (System.IO.IOException) { DisconnectNamedPipe(handshakingPipeHandle); ConnectNamedPipe(handshakingPipeHandle, IntPtr.Zero); break; } } } else { string error = string.Format("Error {0} occurred", GetLastError()); ShowErrorMessage(error); } if (noUI) { Console.WriteLine("CLRProfiler is loaded in the target process."); } else { EnableDisableViewMenuItems(); EnableDisableLaunchControls(false); if (!allocationsCheckBox.Checked && callsCheckBox.Checked) showHeapButton.Enabled = false; else showHeapButton.Enabled = true; killApplicationButton.Enabled = true; detachProcessMenuItem.Enabled = false; } logFileStartOffset = 0; logFileEndOffset = long.MaxValue; profilerConnected = true; return pid; }
private int WaitForWindowsStoreAppProcessToConnect(uint pid, string text, bool attachMode = false, uint result = 0) { if (!VerifyCorrectBitness(Process.GetProcessById((int) pid))) return -1; WaitingForConnectionForm waitingForConnectionForm = null; //Do not show the text in attachmode if (attachMode == false) { if (noUI) { Console.WriteLine(text); } else { if (waitingForConnectionForm == null) waitingForConnectionForm = new WaitingForConnectionForm(); waitingForConnectionForm.setMessage(text); waitingForConnectionForm.Visible = true; } } string fileName = getLogFileName((int)pid); string logFilePath = GetLogDir() + "\\" + fileName; // When log file has been created, that's our sign that profilerObj.dll is up and running while (!File.Exists(logFilePath)) { Application.DoEvents(); if (!noUI) { if (waitingForConnectionForm != null && waitingForConnectionForm.DialogResult == DialogResult.Cancel) { waitingForConnectionForm.Close(); return -1; } } Thread.Sleep(100); } if (waitingForConnectionForm != null) waitingForConnectionForm.Visible = false; CreateEvents((int)pid); logFileName = logFilePath; log = new ReadNewLog(logFileName); if (noUI) { Console.WriteLine("CLRProfiler is loaded in the target process."); } else { EnableDisableViewMenuItems(); EnableDisableLaunchControls(false); if (!allocationsCheckBox.Checked && callsCheckBox.Checked) showHeapButton.Enabled = false; else showHeapButton.Enabled = true; killApplicationButton.Enabled = true; } logFileStartOffset = 0; logFileEndOffset = long.MaxValue; profilerConnected = true; return (int) pid; }