所以我在winspool.drv!WritePrinter
有一个钩子函数,它成功地与远程注入spoolsv.exe的非托管C ++挂钩。
目前,钩子似乎要么替换原始函数,要么以不可检测的方式破坏堆栈:挂钩后,WritePrinter调用导致钩子外没有打印机活动。
我发现至少有一种方法可以调用原始函数,即所谓的LhGetOldProc
。但是,使用它会导致崩溃,不确定这是否与easyhook相关的错误或者只是糟糕的投射。
使用LhGetOldProc
挂钩回调:
UCHAR *uc = NULL;
LhGetOldProc(hhW, &uc);
typedef BOOL (*wp)(_In_ HANDLE, _In_ LPVOID, _In_ DWORD cbBuf, _Out_ LPDWORD);
wp my_wp = reinterpret_cast<wp>(reinterpret_cast<long>(uc)); // http://stackoverflow.com/questions/1096341/function-pointers-casting-in-c
BOOL res ;
if (my_wp == 0x0) {
return -1;
} else {
res = my_wp(hPrinter, pBuf, cbBuf, pcWritten); // crash
}
钩子代码:
HMODULE hSpoolsv = LoadLibraryA("winspool.drv");
TRACED_HOOK_HANDLE hHook = new HOOK_TRACE_INFO();
NTSTATUS NtStatus;
UNICODE_STRING* NameBuffer = NULL;
HANDLE hRemoteThread;
FORCE(LhInstallHook(GetProcAddress(hSpoolsv, "WritePrinter"), WritePrinterHookA, 0x0, hHook));
ULONG ACLEntries[1] = { (ULONG) - 1 };
FORCE(LhSetExclusiveACL(ACLEntries, 1, hHook));
hhW = hHook;
TIL:2013年,CodePlex(EasyHook讨论列表所在的位置)在使用Microsoft帐户注册时不接受电子邮件的第三级域名。不会使用Firebug绕过表单。
答案 0 :(得分:4)
堆栈被破坏,因为你的函数指针有错误的调用约定。
默认调用约定是__cdecl,它希望调用者清理堆栈。
typedef BOOL (* wp)(_In_ HANDLE ....);
等于:
typedef BOOL (__cdecl* wp)(_In_ HANDLE ...);
但是winapi函数使用__stdcall调用约定,它希望被调用者清理堆栈。 你必须输入一个__stdcall函数:
typedef BOOL (__stdcall* wp)(_In_ HANDLE ....);