Example #1
0
        public static Debuggee Launch(string executable,
                                      string argumentString = null, string workingDirectory = null)
        {
            var si = new STARTUPINFO {
                cb = Marshal.SizeOf(typeof(STARTUPINFO)),
            };
            var pi = new PROCESS_INFORMATION();

            if (argumentString == string.Empty)
            {
                argumentString = null;
            }
            if (workingDirectory == string.Empty)
            {
                workingDirectory = null;
            }

            if (!API.CreateProcess(executable, argumentString, IntPtr.Zero, IntPtr.Zero, true,
                                   ProcessCreationFlags.CreateNewConsole |   // Create extra console for the process
                                   ProcessCreationFlags.DebugOnlyThisProcess // Grant debugger access to the process
                                   , IntPtr.Zero, workingDirectory, ref si, out pi))
            {
                throw new Win32Exception(Marshal.GetLastWin32Error());
            }

            var dbg = new Debuggee(executable,
                                   pi.hProcess, pi.dwProcessId,
                                   pi.hThread, pi.dwThreadId,
                                   ExecutableMetaInfo.ExtractFrom(executable));

            return(dbg);
        }
Example #2
0
 public DebugProcessModule(IntPtr imageBase, string imageFile, ExecutableMetaInfo emi)
 {
     this.ImageBase      = imageBase;
     this.ImageFile      = imageFile;
     this.ModuleMetaInfo = emi;
     ContainsSymbolData  = emi.CodeViewSection != null;
 }
Example #3
0
        static void Main(string[] args)
        {
            var exe = "TestProgram\\myprogram.exe";

            var emi = ExecutableMetaInfo.ExtractFrom(exe);

            string module;
            ushort line;

            emi.TryDetermineCodeLocation(0x00403022, out module, out line);

            Console.WriteLine(module + ":" + line);

            var sw = new StringWriter();

            foreach (var codeSection in emi.CodeSections)
            {
                if (codeSection is CodeViewDebugSection)
                {
                    var cv = (CodeViewDebugSection)codeSection;

                    foreach (var ss in cv.Data.SubsectionDirectory.Sections)
                    {
                        if (ss is sstSrcModule)
                        {
                            var src = (sstSrcModule)ss;

                            foreach (var fi in src.FileInfo)
                            {
                                sw.WriteLine(fi.SourceFileName + ":");
                                for (uint k = 0; k < fi.Segments.Length; k++)
                                {
                                    var segment = fi.Segments[k];
                                    sw.WriteLine("\tSegment #" + k + " (" + fi.segmentStartOffsets[k] + " - " + fi.segmentEndOffsets[k] + ")");

                                    for (int m = 0; m < segment.Lines.Length; m++)
                                    {
                                        sw.WriteLine("\t\tLine " + segment.Lines[m] + " @ 0x" + string.Format("{0:X8} = {0}", segment.Offsets[m]));
                                    }
                                }
                            }
                        }
                    }
                }
                else if (codeSection is ExportSection)
                {
                }
            }

            sw.Flush();
            File.WriteAllText(exe + ".log", sw.ToString());
        }
Example #4
0
        internal Debuggee(string executable,
                          IntPtr procHandle, uint procId,
                          IntPtr mainThreadHandle, uint mainThreadId,
                          ExecutableMetaInfo emi = null)
        {
            // Note: The CodeView information extraction will be done per module, i.e. when the module/process is loaded into the memory.
            Memory       = new MemoryManagement(this);
            Breakpoints  = new BreakpointManagement(this);
            CodeStepping = new Stepping(this);

            var mProc = new DebugProcess(this, executable, procHandle, procId, mainThreadHandle, mainThreadId, emi);

            CurrentThread = mProc.MainThread;
            processes.Add(mProc);
        }
Example #5
0
        public DebugProcess(Debuggee dbg,
                            string executableFile,
                            IntPtr processHandle, uint processId,
                            IntPtr mainThreadHandle, uint mainThreadId,
                            ExecutableMetaInfo emi)
        {
            this.Debuggee = dbg;
            Handle        = processHandle;
            Id            = processId;

            MainModule = new DebugProcessModule(new IntPtr(emi.PEHeader.OptionalHeader32.ImageBase), executableFile, emi);
            RegModule(MainModule);

            MainThread = new DebugThread(this, mainThreadHandle, mainThreadId, MainModule.StartAddress, IntPtr.Zero);
            RegThread(MainThread);
        }
Example #6
0
        public DebugProcess(Debuggee dbg, Win32.CREATE_PROCESS_DEBUG_INFO info, uint id, uint threadId)
        {
            this.Debuggee = dbg;
            Handle        = info.hProcess;
            Id            = id == 0 ? API.GetProcessId(Handle) : id;

            var moduleFile = APIIntermediate.GetModulePath(Handle, info.lpBaseOfImage, info.hFile);

            // Deduce main module
            MainModule = new DebugProcessModule(info.lpBaseOfImage, moduleFile, ExecutableMetaInfo.ExtractFrom(moduleFile));
            RegModule(MainModule);

            // Create main thread
            MainThread = new DebugThread(this,
                                         info.hThread,
                                         threadId == 0 ? API.GetThreadId(info.hThread) : threadId,
                                         info.lpStartAddress,
                                         info.lpThreadLocalBase);
            RegThread(MainThread);
        }
Example #7
0
        void HandleDebugEvent(DebugEventData de)
        {
            var p  = ProcessById(de.dwProcessId);
            var th = CurrentThread = p.ThreadById(de.dwThreadId);

            switch (de.dwDebugEventCode)
            {
            case DebugEventCode.EXCEPTION_DEBUG_EVENT:
                HandleException(th, de.Exception);
                break;


            case DebugEventCode.CREATE_PROCESS_DEBUG_EVENT:
                var cpi = de.CreateProcessInfo;

                if (MainProcess != null && de.dwProcessId == MainProcess.Id)
                {
                    API.CloseHandle(cpi.hProcess);
                    API.CloseHandle(cpi.hThread);
                    API.CloseHandle(cpi.hFile);

                    foreach (var l in DDebugger.EventListeners)
                    {
                        l.OnCreateProcess(MainProcess);
                    }
                    break;
                }

                // After a new process was created (also occurs after initial WaitForDebugEvent()!!),
                p = new DebugProcess(this, cpi, de.dwProcessId, de.dwThreadId);

                API.CloseHandle(cpi.hFile);

                // enlist it
                processes.Add(p);

                // and call the listeners
                foreach (var l in DDebugger.EventListeners)
                {
                    l.OnCreateProcess(p);
                }
                break;


            case DebugEventCode.CREATE_THREAD_DEBUG_EVENT:
                p = ProcessById(de.dwProcessId);

                // Create new thread wrapper
                th = CurrentThread = new DebugThread(p,
                                                     de.CreateThread.hThread,
                                                     de.dwThreadId,
                                                     de.CreateThread.lpStartAddress,
                                                     de.CreateThread.lpThreadLocalBase);
                // Register it to main process
                p.RegThread(th);

                // Call listeners
                foreach (var l in DDebugger.EventListeners)
                {
                    l.OnCreateThread(th);
                }
                break;


            case DebugEventCode.EXIT_PROCESS_DEBUG_EVENT:

                foreach (var l in DDebugger.EventListeners)
                {
                    l.OnProcessExit(p, de.ExitProcess.dwExitCode);
                }

                processes.Remove(p);
                p.Dispose();
                break;


            case DebugEventCode.EXIT_THREAD_DEBUG_EVENT:

                foreach (var l in DDebugger.EventListeners)
                {
                    l.OnThreadExit(th, de.ExitThread.dwExitCode);
                }

                p.RemThread(th);
                th.Dispose();
                break;


            case DebugEventCode.LOAD_DLL_DEBUG_EVENT:
                var loadParam = de.LoadDll;

                var modName = APIIntermediate.GetModulePath(p.Handle, loadParam.lpBaseOfDll, loadParam.hFile);
                API.CloseHandle(loadParam.hFile);

                var mod = new DebugProcessModule(loadParam.lpBaseOfDll, modName, ExecutableMetaInfo.ExtractFrom(modName));
                p.RegModule(mod);

                foreach (var l in DDebugger.EventListeners)
                {
                    l.OnModuleLoaded(p, mod);
                }
                break;


            case DebugEventCode.UNLOAD_DLL_DEBUG_EVENT:
                mod = p.ModuleByBase(de.UnloadDll.lpBaseOfDll);

                foreach (var l in DDebugger.EventListeners)
                {
                    l.OnModuleUnloaded(p, mod);
                }

                p.RemModule(mod);
                break;


            case DebugEventCode.OUTPUT_DEBUG_STRING_EVENT:
                var message = APIIntermediate.ReadString(p.Handle,
                                                         de.DebugString.lpDebugStringData,
                                                         de.DebugString.fUnicode == 0 ? Encoding.ASCII : Encoding.Unicode,
                                                         (int)de.DebugString.nDebugStringLength);

                foreach (var l in DDebugger.EventListeners)
                {
                    l.OnDebugOutput(th, message);
                }
                break;
            }
        }