Python GetModuleHandleW OSError: [WinError 126] The specified module could not be found

你离开我真会死。 提交于 2019-12-13 07:06:51

问题


The following code generates the error :

OSError: [WinError 126] The specified module could not be found
windll.kernel32.GetModuleHandleW.restype = wintypes.HMODULE
windll.kernel32.GetModuleHandleW.argtypes = [wintypes.LPCWSTR]
KERNEL32 = windll.GetModuleHandleW("C:\\Windows\\System32\\kernel32.dll")

However, if I use

KERNEL32 = windll.LoadLibrary("C:\\Windows\\System32\\kernel32.dll")

The dll is found but I encounter a different error by the following code:

LoadLibAddy = windll.kernel32.GetProcAddress(KERNEL32, "LoadLibraryA")

The error generated is :

ctypes.ArgumentError: argument 1:  Don't know how to convert parameter 1

I was hoping someone would have an idea on how to fix either of these errors. The full script:

from ctypes import *
from ctypes import wintypes

def dllinjector(processID, DLL_NAME):
    KERNEL32 = WinDLL('kernel32.dll', use_last_error=True)
    KERNEL32.GetProcAddress.restype = c_void_p
    KERNEL32.GetProcAddress.argtypes = (wintypes.HMODULE, wintypes.LPCSTR)
    PROCESS_CREATE_THREAD = 0x0002
    PROCESS_QUERY_INFORMATION = 0x0400
    PROCESS_VM_OPERATION = 0x0008
    PROCESS_VM_WRITE = 0x0020
    PROCESS_VM_READ = 0x0010
    openHandle = KERNEL32.OpenProcess(PROCESS_CREATE_THREAD|
                                             PROCESS_QUERY_INFORMATION|
                                             PROCESS_VM_OPERATION|
                                             PROCESS_VM_WRITE|
                                             PROCESS_VM_READ, False, processID)
    MEM_RESERVE = 0x00002000
    MEM_COMMIT = 0x00001000
    PAGE_READWRITE = 0x04

    if not openHandle:
        print("OpenProcess failed.")
        print("GetLastError: ", KERNEL32.GetLastError())
        return False
    print("openProcess GetLastError: ", KERNEL32.GetLastError())
    #print("Successfully opened process.")

    LoadLibAddy = KERNEL32.GetProcAddress(KERNEL32._handle, b"LoadLibraryA")
    if not LoadLibAddy:
        raise WinError(ctypes.get_last_error())
    print("LoadLibAddy: ", LoadLibAddy)
    print("LoadLibAddy GetLastError: ", KERNEL32.GetLastError())

    # Allocate space in the process for the dll
    RemoteString = KERNEL32.VirtualAllocEx(openHandle, None, len(DLL_NAME), MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE)
    print("RemoteString GetLastError: ", KERNEL32.GetLastError())
    if not RemoteString:
        print("VirtualAllocEx failed.")
        return False

    # Write the string name of the dll in the memory allocated
    if not KERNEL32.WriteProcessMemory(openHandle, RemoteString, DLL_NAME, len(DLL_NAME), None):
        print("WriteProcessMemory failed.")
        return False
    print("WriteProcessMemory GetLastError: ", KERNEL32.GetLastError())

    #Load the dll
    if not KERNEL32.CreateRemoteThread(openHandle, None, None, c_longlong(LoadLibAddy), RemoteString, None, None):
        print("CreateRemoteThread failed.")
        return False
    print("CreateRemotedThread GetLastError: ", windll.kernel32.GetLastError())
    #print("CreateRemoteThread: ", windll.kernel32.CreateRemoteThread(openHandle, None, None, LoadLibAddy, RemoteString, None, None))

    KERNEL32.CloseHandle(openHandle)
    print("CloseHandle GetLastError: ", KERNEL32.GetLastError())

    return True

def main():
    processID = 25408
    DLL_NAME = "mydll32.dll"

    dllinjector(processID, DLL_NAME)

    print("program completed.")

main()

回答1:


It should be windll.kernel32.GetModuleHandleW("kernel32.dll"). But please don't use windll when defining function prototypes because it's global to all modules that use ctypes, which leads to conflicting prototypes. Use kernel32 = WinDLL('kernel32', use_last_error=True). The DLL handle is kernel32._handle.

For your 2nd problem, first and foremost there's no reason to ever directly call GetProcAddress (or dlsym on POSIX systems) when using ctypes. But in principle it would be as follows:

kernel32 = ctypes.WinDLL('kernel32', use_last_error=True)   
kernel32.GetProcAddress.restype = ctypes.c_void_p
kernel32.GetProcAddress.argtypes = (wintypes.HMODULE, wintypes.LPCSTR)

LoadLibAddy = kernel32.GetProcAddress(kernel32._handle, b'LoadLibraryA')
if not LoadLibAddy:
    raise ctypes.WinError(ctypes.get_last_error())

Note that the function name is passed as bytes. Anyway, you don't need this since kernel32.LoadLibraryA (or kernel32.LoadLibraryW) is a function pointer that you can pass as an argument or cast to c_void_p, etc.



来源:https://stackoverflow.com/questions/33779657/python-getmodulehandlew-oserror-winerror-126-the-specified-module-could-not-b

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!