From e17400ed632d5d7f59b82b1c8ed4c6aca3f2eeeb Mon Sep 17 00:00:00 2001 From: hakril Date: Thu, 15 Sep 2016 00:23:26 +0200 Subject: [PATCH] Debugger.detach remove self.target + better handling/clean of Thread/Process handles --- windows/debug/debugger.py | 27 +++++++++++++++++++++++++-- windows/utils/winutils.py | 5 +++++ windows/winobject/process.py | 2 +- 3 files changed, 31 insertions(+), 3 deletions(-) diff --git a/windows/debug/debugger.py b/windows/debug/debugger.py index ba88c69..7807101 100644 --- a/windows/debug/debugger.py +++ b/windows/debug/debugger.py @@ -85,7 +85,17 @@ class Debugger(object): def detach(self, target=None): """Detach from all debugged processes or process ``target``""" if target is None: - for proc in self.processes.values(): + targets = self.processes.values() + if not targets: + # We are not following any process + # maybe a attach/detach with Debugger.loop + # Just detach from the initial target + if self.target: + tpid = self.target.pid + self.target = None # Remove ref to process -> GC -> CloseHandle -> process is destroyed + windows.winproxy.DebugActiveProcessStop(tpid) + return + for proc in targets: self.detach(proc) return if not isinstance(target, WinProcess): @@ -118,6 +128,10 @@ class Debugger(object): if target is self.current_process: self._finish_debug_event(self.REMOVE_ME_debug_event, DBG_CONTINUE) + if target is self.target: + self.target = None + + print("Detach from {0}".format(target.pid)) windows.winproxy.DebugActiveProcessStop(target.pid) def _killed_in_action(self): @@ -612,9 +626,18 @@ class Debugger(object): proc_handle = HANDLE() thread_handle = HANDLE() cp_handle = windows.current_process.handle + + + winproxy.DuplicateHandle(cp_handle, create_process.hProcess, cp_handle, ctypes.byref(proc_handle), dwOptions=DUPLICATE_SAME_ACCESS) winproxy.DuplicateHandle(cp_handle, create_process.hThread, cp_handle, ctypes.byref(thread_handle), dwOptions=DUPLICATE_SAME_ACCESS) + dbgprint(" Got PROC handle {0:#x}".format(create_process.hProcess, self), "HANDLE") + dbgprint(" PROC handle duplicated: {0:#x}".format(proc_handle.value), "HANDLE") + + dbgprint(" Got THREAD handle {0:#x}".format(create_process.hThread, self), "HANDLE") + dbgprint(" THREAD handle duplicated: {0:#x}".format(thread_handle.value), "HANDLE") + self.current_process = WinProcess._from_handle(proc_handle.value) self.current_thread = WinThread._from_handle(thread_handle.value) @@ -809,7 +832,7 @@ class Debugger(object): if target is None: target = self.current_process res = {} - cp_watch_page = self._watched_pages[self.current_process.pid] + cp_watch_page = self._watched_pages[target.pid] page_protection = DWORD() for page_addr, watched_page in cp_watch_page.items(): target.virtual_protect(page_addr, PAGE_SIZE, watched_page.original_prot, page_protection) diff --git a/windows/utils/winutils.py b/windows/utils/winutils.py index a49dae8..5ea58a5 100644 --- a/windows/utils/winutils.py +++ b/windows/utils/winutils.py @@ -6,6 +6,7 @@ import code import datetime import windows +from windows.dbgprint import dbgprint from .. import winproxy from ..generated_def import windef from ..generated_def.winstructs import * @@ -84,6 +85,10 @@ def create_process(path, args=None, dwCreationFlags=0, show_windows=True): if args: lpCommandLine = (" ".join([str(a) for a in args])) windows.winproxy.CreateProcessA(path, lpCommandLine=lpCommandLine, dwCreationFlags=dwCreationFlags, lpProcessInformation=ctypes.byref(proc_info), lpStartupInfo=lpStartupInfo) + dbgprint("CreateProcessA new process handle {:#x}".format(proc_info.hProcess), "HANDLE") + dbgprint("CreateProcessA new thread handle {:#x}".format(proc_info.hThread), "HANDLE") + dbgprint("Automatic close of thread handle {:#x}".format(proc_info.hThread), "HANDLE") + windows.winproxy.CloseHandle(proc_info.hThread) # Give access to a WinThread in addition of the WinProcess ? return windows.winobject.process.WinProcess(pid=proc_info.dwProcessId, handle=proc_info.hProcess) diff --git a/windows/winobject/process.py b/windows/winobject/process.py index f10727d..b361112 100644 --- a/windows/winobject/process.py +++ b/windows/winobject/process.py @@ -56,7 +56,7 @@ class AutoHandle(object): def __del__(self): if hasattr(self, "_handle") and self._handle: - #dbgprint("Closing Handle {0} for {1}".format(hex(self._handle), self), "HANDLE") + dbgprint("Closing Handle {0} for {1}".format(hex(self._handle), self), "HANDLE") self._close_function(self._handle)