在Windows挂钩中注入dll后出现无效的挂钩过程错误

问题描述 投票:0回答:1

我正在尝试通过注入dll全局插入Windows。我的代码可与python2.7一起使用,但在使用Python3.7且已提及的错误时可悲地失败了。这是示例代码:

user32.SetWindowsHookExA.errcheck = errcheck_bool
user32.SetWindowsHookExA.restype = HHOOK
user32.SetWindowsHookExA.argtypes = (c_int,     # _In_ idHook
                                     HOOKPROC,  # _In_ lpfn
                                     HINSTANCE, # _In_ hMod
                                     DWORD)     # _In_ dwThreadId

user32.CallNextHookEx.restype = LRESULT
user32.CallNextHookEx.argtypes = (HHOOK,  # _In_opt_ hhk
                                  c_int,  # _In_     nCode
                                  WPARAM, # _In_     wParam
                                  LPARAM) # _In_     lParam

user32.GetMessageW.argtypes = (LPMSG, # _Out_    lpMsg
                               HWND,  # _In_opt_ hWnd
                               UINT,  # _In_     wMsgFilterMin
                               UINT)  # _In_     wMsgFilterMax

user32.TranslateMessage.argtypes = (LPMSG,)
user32.DispatchMessageW.argtypes = (LPMSG,)

GetModuleHandle = ctypes.windll.kernel32.GetModuleHandleA
GetModuleHandle.restype = POINTER(c_void_p)

LoadLibrary = ctypes.windll.kernel32.LoadLibraryA
LoadLibrary.restype = HINSTANCE

GetProcAddress = ctypes.windll.kernel32.GetProcAddress
GetProcAddress.restype = HOOKPROC

user32.GetWindowThreadProcessId.restype = DWORD

def pointer_msg_loop():
    lib = LoadLibrary(r'C:\Users\Braun\Documents\BA_Thesis\ba-oliver-braun-logging-tool-code\MessagesDll\x64\Release\Dll.dll')
    handle = GetModuleHandle(r'C:\Users\Braun\Documents\BA_Thesis\ba-oliver-braun-logging-tool-code\MessagesDll\x64\Release\Dll.dll')
    print(lib)
    print(handle)
    procedure = GetProcAddress(handle, "meconnect".encode())
    print(procedure)
    print('correct value procedure')
    tHook = user32.SetWindowsHookExA(WH_GETMESSAGE, procedure, lib, 0)
    time.sleep(30)
    user32.UnhookWindowsHookEx(tHook)
    print(tHook)
    msg = MSG()
    while True:
        bRet = user32.GetMessageW(byref(msg), None, 0, 0)
        if not bRet:
            break
        if bRet == -1:
            raise WinError(get_last_error())
        user32.TranslateMessage(byref(msg))
        user32.DispatchMessageW(byref(msg))

if __name__ == '__main__':
    import time
    import datetime
    import threading
    control_key_pressed = False
    startTime = datetime.datetime.now()
    tmouse = threading.Thread(target=mouse_msg_loop)
    tkeyboard = threading.Thread(target=keyboard_msg_loop)
    ttouch = threading.Thread(target=pointer_msg_loop)
    tmouse.start()
    tkeyboard.start()
    ttouch.start()
    while True:
        try:
            time.sleep(1)
        except KeyboardInterrupt:
            user32.PostThreadMessageW(tmouse.ident, WM_QUIT, 0, 0)
            break

DLL:

// dllmain.cpp : Defines the entry point for the DLL application.
#include "pch.h"
#pragma data_seg("Shared")
#pragma data_seg()
#pragma comment(linker,"/section:Shared,rws")

#include <windows.h>
#include <stdio.h>
#include <string.h>

HHOOK tHook;

extern "C" __declspec(dllexport) LRESULT meconnect(int code, WPARAM wParam, LPARAM lParam) {
    BOOL EnableMouseInPointer = TRUE;
    if (code == HC_ACTION) {
        LPMSG data = (LPMSG)lParam;
        if (data->message == WM_POINTERDOWN) {
            MessageBoxA(NULL, "eee", NULL, 0);
        }
    }
    return(CallNextHookEx(tHook, code, wParam, lParam));
}

[一些有趣的观察:将LoadLibraryA更改为LoadLibraryW时,甚至python2.7也会失败。这似乎真的很明显,我怀疑是因为两个版本都强制使用不同的字符串类型?但是,是的,我可以做些什么才能使其在Python3.7中起作用

python windows winapi hook ctypes
1个回答
0
投票

在Python 3.7中,sys.getdefaultencoding()的结果为'utf-8'。 @jfs的This answer表示

sys.getdefaultencoding()始终在以下系统的所有系统上运行'ascii'Python 2,除非您重写它。

这可能是您弄错了的原因。

  1. 使用b''代替r'',或仅使用宽字节功能。
  2. GetProcAddress没有宽字节版本。只需使用GetProcAddress(handle, b'meconnect')
  3. 未定义DLL中的tHook,它将在下一个挂钩中导致未定义的行为。
  4. 您最好将消息循环放在UnhookWindowsHookEx之前,而不是sleep方法。

您可以在DLL中调用SetWindowsHookEx。这是示例。DLL:

// dllmain.cpp : Defines the entry point for the DLL application.
#include "pch.h"
#include <windows.h>
#include <stdio.h>
#include <string.h>
HHOOK tHook;
HMODULE hinstDLL;
LRESULT CALLBACK meconnect(int code, WPARAM wParam, LPARAM lParam) {
    BOOL EnableMouseInPointer = TRUE;
    if (code == HC_ACTION) {
        LPMSG data = (LPMSG)lParam;
        if (data->message == WM_POINTERDOWN) {
            MessageBoxA(NULL, "eee", NULL, 0);
        }
    }
    return(CallNextHookEx(tHook, code, wParam, lParam));
}
extern "C" __declspec(dllexport) BOOL SetHook()
{
    tHook = SetWindowsHookEx(WH_GETMESSAGE, meconnect, hinstDLL, 0);

    if (tHook == NULL)
        return FALSE;
    else
        return TRUE;
}
extern "C" __declspec(dllexport) BOOL UnHook()
{
    return UnhookWindowsHookEx(tHook);
}


BOOL APIENTRY DllMain( HMODULE hModule,
                       DWORD  ul_reason_for_call,
                       LPVOID lpReserved
                     )
{
    switch (ul_reason_for_call)
    {
    case DLL_PROCESS_ATTACH:
        hinstDLL = hModule;
        break;
    case DLL_THREAD_ATTACH:
    case DLL_THREAD_DETACH:
    case DLL_PROCESS_DETACH:
        break;
    }
    return TRUE;
}

python:

import threading
import ctypes
from ctypes import wintypes
from ctypes import *
import win32api
import win32gui
def pointer_msg_loop():
    lib = cdll.LoadLibrary(b'PATH\DLL.dll')
    print(lib)
    res = lib.SetHook()
    print(res)
    win32gui.PumpMessages()
    res = lib.UnHook()


if __name__ == '__main__':
    ttouch = threading.Thread(target=pointer_msg_loop)
    ttouch.start()
    ttouch.join()
最新问题
© www.soinside.com 2019 - 2024. All rights reserved.