我正在使用ctypes
,并尝试使用PEB
函数获取NtQueryInformationProcess
地址。
返回值为0,表示该函数已成功完成。
但是PROCESS_BASIC_INFORMATION
结构(作为第三个参数)不包含PEB
地址。
class PROCESS_BASIC_INFORMATION(Structure):
_fields_ = [
("Reserved1", c_void_p),
("PebBaseAddress", DWORD),
("Reserved2", c_void_p * 2),
("UniqueProcessId", DWORD),
("Reserved3", c_void_p)]
ntdll = WinDLL('ntdll')
NTSTATUS = LONG
ntdll.argtypes = [HANDLE, DWORD, c_void_p, DWORD, PDWORD]
ntdll.restype = NTSTATUS
processInformation = PROCESS_BASIC_INFORMATION()
processInformationLength = sizeof(PROCESS_BASIC_INFORMATION)
result = ntdll.NtQueryInformationProcess(hProcess, 0, processInformation, processInformationLength, byref(DWORD(0)))
考虑返回值为0的事实,这可能是什么问题?
答案 0 :(得分:0)
列出[Python 3.Docs]: ctypes - A foreign function library for Python。
您为错误对象( ntdll )定义了 argtypes 和 restype 。您应该为ntdll.NtQueryInformationProcess
定义它们。当我们在这里时,很明显您喜欢 DWORD 。即使在这种情况下也没关系,请保持函数签名与 C 中的签名一致:
ntdll.NtQueryInformationProcess.argtypes = [HANDLE, c_int, c_void_p, ULONG, PULONG]
ntdll.NtQueryInformationProcess.restype = NTSTATUS
未能在函数上定义 argtypes 和 restype (或做错了),可能(并且很可能会)导致:
根据[MS.Docs]: NtQueryInformationProcess function(强调是我的):
ProcessInformation
指向由调用应用程序提供的缓冲区的指针,函数将请求的信息写入其中。
因此,您的呼叫应类似于(通过引用传递 processInformation ):
result = ntdll.NtQueryInformationProcess(hProcess, 0, byref(processInformation), processInformationLength, byref(DWORD(0)))
根据同一页面,您的结构定义不正确。应该是:
class PROCESS_BASIC_INFORMATION(Structure):
_fields_ = [
("Reserved1", c_void_p),
("PebBaseAddress", c_void_p),
("Reserved2", c_void_p * 2),
("UniqueProcessId", c_void_p),
("Reserved3", c_void_p),
]
您的版本(在 64bit 上)要短8个字节(由于 DWORD 和指针之间的(两个)大小差异),导致传递的缓冲区太短功能,它是 U 未定义的 B 行为(可能会导致崩溃)。