70006¥

IT & DIARY 自己満ブログ

windows) python debugger #1 (失敗)

今回はパイソンでdebuggerを作ってみ ることにしてみた。

まずパイソンでwinapiの一種であるCreateProcessAを使うためstructureを定義するmy_debugger_defines.pyを作ってみた。

以下my_debugger_defines.pyのコード:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
from ctypes import *
 
WORD    = c_ushort
DWORD    = c_ulong
LPBYTE    = POINTER(c_ubyte)
LPTSTR    = POINTER(c_char)
HANDLE    = c_void_p
 
# like DEFINE
DEBUG_PROCESS        = 0x00000001
CREATE_NEW_CONSOLE    = 0x00000010
 
#structure for CreateProcessA 
class STARTUPINFO(Structure):
    _fields_ = [
    ("cb",                DWORD),
    ("lpReserved",        LPTSTR),
    ("lpDesktop",        LPTSTR),
    ("lpTitle",            LPTSTR),
    ("dwX",                DWORD),
    ("dwY",                DWORD),
    ("dwXSize",            DWORD),
    ("dwYSize",            DWORD),
    ("dwXCountChars",    DWORD),
    ("dwYCountChars",    DWORD),
    ("dwFillAttribute",    DWORD),
    ("dwFlags",            DWORD),
    ("wShowWindow",        WORD),
    ("cbReserved2",        WORD),
    ("lpReserved2",        LPBYTE),
    ("hStdInput",        HANDLE),
    ("hStdOutput",        HANDLE),
    ("hStdError",        HANDLE),
    ]
 
class PROCESS_INFORMATION(Structure):
    _fields_ = [
    ("hProcess",    HANDLE),
    ("hThread",        HANDLE),
    ("dwProcessId",    DWORD),
    ("dwThreadId",    DWORD),
    ]
 
 
    
cs

 

次はこのAPIを使って実行したprocessをdebuggerに添付するclass debuggerが書いているmy_debugger.pyのコード:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
from ctypes import *
from my_debugger_defines import *
 
kernel32  = windll.kernel32
 
class debugger():
    def __init__(self):
        self.h_process            = None
        self.pid                 = None
        self.debugger_active    = False
        
    def load(self,path_to_exe):
        #if you want to see GUI of Calc, creation_flags = CREATE_NEW_CONSOLE
        creation_flags = DEBUG_PROCESS
 
        startupinfo         = STARTUPINFO()
        process_information    = PROCESS_INFORMATION()
 
        startupinfo.dwFlags        = 0x1
        startupinfo.wShowWindow    = 0x0
 
        startupinfo.cb             = sizeof(startupinfo)
 
        if kernel32.CreateProcessA(    path_to_exe,
                                    None,
                                    None,
                                    None,
                                    None,
                                    creation_flags,
                                    None,
                                    None,
                                    byref(startupinfo),
                                    byref(process_information)):
            print "[*] We have successfully launched the process!"
            print "[*] PID: %d" % process_information.dwProcessId
            self.h_process = self.open_process(process_information.dwProcessId)
        else:
            print "[*] Error: 0x%08x." % kernel32.GetLastError()
 
    def open_process(self,pid):
        h_process = kernel32.OpenProcess(PROCESS_ALL_ACCESS,False,pid)
        return h_process
        
    def attach(self,pid):
        self.h_process = self.open_process(pid)
 
        if kernel32.DebugActiveProcess(pid):
            self.debugger_active = True
            self.pid              = int(pid)
        else:
            print "[*] Unable to attach to the process."
    
    def run(self):
        while self.debugger_active == True:
            self.get_debug_event()
 
    def get_debug_event(self):
        debug_event     = DEBUG_EVENT()
        continue_status = DBG_CONTINUE
 
        if kernel32.WaitForDebugEvent(byref(debug_event),INFINITE):
            raw_input("Press a Key to continue...")
            self.debugger_active = False
            kernel32.ContinueDebugEvent( \
                debug_event.dwProcessId,\
                debug_event.dwThreadId,\
                continue_status )
 
    def detatch(self):
        if kernel32.DebugActiveProcessStop(self.pid):
            print "[*] Finished debugging. Exiting..."
            return True
        else:
            print "There was an error"
            return False

cs

 

 

 

最後にpidを入力してdebuggerにprocessを添付させるmy_test.pyのコード:

1
2
3
4
5
6
7
import my_debugger
 
debugger = my_debugger.debugger()
pid = raw_input("Enter the PID of the process to attach to: ")
debugger.attach(int(pid))
debugger.detach()
 
cs

 

結果:失敗。

問題点が何かがわからない。次はこの問題を解決してみせる。