Setwindowshookex注入
SetWindowsHookEx注入
##原理 一个正常的消息发送如下: 客户端代码:
HWND hwnd = ::FindWindow(NULL,TEXT("接收端窗口名"));
if(hwnd == NULL)
{
MessageBox(0,TEXT("没找到窗口"),TEXT("ERROR"),MB_OK);
}
else
{
// 发送消息
//SendMessage(hwnd,WM_USER+0x1,NULL, (LPARAM)100);
PostMessage(hwnd,WM_USER+0x1, NULL, (LPARAM)100);
}
接收端代码:
switch(uMsg)
{
case WM_CLOSE:
{
EndDialog(hDlg,0);
break;
}
case WM_USER+0x1:
{
DWORD x = wParam;
DWORD y = lParam;
MessageBox(0,0,0,0);
break;
}
case WM_COMMAND:
switch (LOWORD (wParam))
{
case IDC_BUTTON_RECV:
{
return TRUE;
}
}
break ;
}
但是一般不是自己写的程序是没有WM_USER+0x1这个类型的消息,别的程序不认识,所以我们需要自定义消息来实现。windows允许自己定义消息
系统消息已经占用了1023
//$define WM_USER 0x400
如果我们需要定义自己的消息一般WM_USER+0x1 这种消息系统一定不会用
但是不是自己写的程序一定没有WM_USER+0x1 ,所以我们需要注入代码,这个注入就是消息HOOK 利用SetWindowsHookEx函数进行挂钩。
SetWindowsHookEx
HHOOK WINAPI SetWindowsHookEx(
_In_ int idHook, 设置钩子的类型.意思就是我要设置的钩子是什么钩子. 可以是监视窗口过程.可以是监视消息队列.
_In_ HOOKPROC lpfn, 根据钩子类型.设置不同的回调函数.
_In_ HINSTANCE hMod, 钩子设置的Dll实例句柄,就是DLL的句柄
_In_ DWORD dwThreadId 设置钩子的线程ID. 如果为0 则设置为全局钩子.
);
HHOOK 返回值. 是一个钩子过程句柄.
先生成一个dll,定义3个函数,分别用于安装钩子,卸载钩子和自定义消息处理函数。其中前两个函数是导出函数,由消息发送程序调用。
// dllmain.cpp : 定义 DLL 应用程序的入口点。
#define _CRT_SECURE_NO_WARNINGS
#include "framework.h"
#include <stdio.h>
HHOOK g_HookProc;
extern "C" void __declspec(dllexport) SetHook(); // 安装HOOK
extern "C" void __declspec(dllexport) UnHook(); // 卸载HOOK
LRESULT CALLBACK MessageHookProc(int nCode, WPARAM wParam, LPARAM lParam); //消息处理函数
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
extern "C" void __declspec(dllexport) SetHook()
{
g_HookProc = SetWindowsHookEx(WH_CALLWNDPROC, MessageHookProc, GetModuleHandle(TEXT("MessageHook.dll")), 0);
}
extern "C" void __declspec(dllexport) UnHook()
{
if (NULL != g_HookProc)
UnhookWindowsHookEx(g_HookProc);
}
LRESULT CALLBACK MessageHookProc(int nCode, WPARAM wParam, LPARAM lParam) //我们自己的程序处理
{
if (nCode == HC_ACTION)
{
PCWPSTRUCT pcw = (PCWPSTRUCT)lParam;
if (pcw->message == WM_USER + 0x1)
{
char szBuf[200] = { 0 };
sprintf(szBuf, "wParam: %d\nlParam: %d\nPID: %d\n", pcw->wParam, pcw->lParam,GetCurrentProcessId());
MessageBoxA(0, szBuf, "接收到自定义消息", 0);
}
}
return CallNextHookEx(g_HookProc, nCode, wParam, lParam); //继续调用钩子过程
}
然后建立控制台项目:
// hooktest.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//
#include <iostream>
#include <Windows.h>
#include <stdio.h>
BOOL Inject()
{
// 安装HOOK
HMODULE hModule = LoadLibrary(TEXT("messagehook.dll"));
if (hModule == NULL)
{
printf("LoadLibrary失败\n");
return FALSE;
}
typedef void(*PFNSETHOOK)();
PFNSETHOOK pFnSetHook = (PFNSETHOOK)GetProcAddress(hModule, "SetHook");
if (NULL == pFnSetHook)
{
printf("获取函数地址失败\n");
return FALSE;
}
pFnSetHook();
// 发送自定义消息
HWND hWnd = FindWindow(NULL, TEXT("无标题 - 记事本"));
if (!hWnd)
{
printf("获取窗口句柄失败\n");
return FALSE;
}
SendMessage(hWnd, WM_USER + 0x1, (DWORD)100, (DWORD)200);
//直接卸载
typedef void(*PFNUNHOOK)();
PFNUNHOOK pFnUnHook = (PFNUNHOOK)GetProcAddress(hModule, "UnHook");
pFnSetHook();
return TRUE;
}
int main()
{
Inject();
return 0;
}