/// <summary> /// Attempts to retrieve the path to the binary from a running process /// Returns null on failure /// </summary> /// <param name="processId">The process to get the binary for</param> /// <returns>The path to the primary executable or null if it could not be determined</returns> private static string GetBinaryPathFromPid(int processId) { string programBinary = null; try { CorPublish.CorPublish cp = new CorPublish.CorPublish(); CorPublish.CorPublishProcess cpp = cp.GetProcess(processId); programBinary = cpp.DisplayName; } catch { // try an alternate method using (ProcessSafeHandle ph = CorDebug.NativeMethods.OpenProcess( (int)(CorDebug.NativeMethods.ProcessAccessOptions.ProcessVMRead | CorDebug.NativeMethods.ProcessAccessOptions.ProcessQueryInformation | CorDebug.NativeMethods.ProcessAccessOptions.ProcessDupHandle | CorDebug.NativeMethods.ProcessAccessOptions.Synchronize), false, // inherit handle processId)) { if (!ph.IsInvalid) { StringBuilder sb = new StringBuilder(CorDebug.NativeMethods.MAX_PATH); int neededSize = sb.Capacity; CorDebug.NativeMethods.QueryFullProcessImageName(ph, 0, sb, ref neededSize); programBinary = sb.ToString(); } } } return(programBinary); }
/// <summary> /// Attach to a process with the given Process ID /// </summary> /// <param name="processId">The Process ID to attach to.</param> /// <returns>The resulting MDbgProcess.</returns> public MDbgProcess Attach(int processId) { string deeVersion; try { deeVersion = CorDebugger.GetDebuggerVersionFromPid(processId); } catch { // GetDebuggerVersionFromPid isn't implemented on Win9x and so will // throw NotImplementedException. We'll also get an ArgumentException // if the specified process doesn't have the CLR loaded yet. // Rather than be selective (and potentially brittle), we'll handle all errors. // Ideally we'd assert (or log) that we're only getting the errors we expect, // but it's complex and ugly to do that in C#. // Fall back to guessing the version based on the filename. // Environment variables (eg. COMPLUS_Version) may have resulted // in a different choice. try { CorPublish.CorPublish cp = new CorPublish.CorPublish(); CorPublish.CorPublishProcess cpp = cp.GetProcess(processId); string programBinary = cpp.DisplayName; deeVersion = CorDebugger.GetDebuggerVersionFromFile(programBinary); } catch { // This will also fail if the process doesn't have the CLR loaded yet. // It could also fail if the image EXE has been renamed since it started. // For whatever reason, fall back to using the default CLR deeVersion = null; } } MDbgProcess p = m_processMgr.CreateLocalProcess(deeVersion); p.Attach(processId); return(p); }