先写一个demo,查看FindWindowW FindWindowExW的函数指针
HMODULE hModule = LoadLibrary(L"user32.dll");
if (hModule != NULL)
{
while (true)
{
FUN_FindWindowW FindWindowWFunc = (FUN_FindWindowW)GetProcAddress(hModule, "FindWindowW");
if (FindWindowWFunc != NULL)
{
printf("FindWindowW 函数指针地址:%p\r\n", FindWindowWFunc);
HWND hWnd = FindWindowWFunc(L"123", NULL);
}
FUN_FindWindowExW FindWindowExWFunc = (FUN_FindWindowExW)GetProcAddress(hModule, "FindWindowExW");
if (FindWindowExWFunc != NULL)
{
printf("FindWindowExW 函数指针地址:%p\r\n", FindWindowExWFunc);
HWND hWnd = FindWindowExWFunc(NULL,NULL, L"DingtalkMsgComming", NULL);
int n = (BYTE*)FindWindowExWFunc - (BYTE*)FindWindowWFunc;
printf("指针偏移:%d 0X%X\r\n",n,n);
FUN_FindWindowExW TextFun = (FUN_FindWindowExW)((BYTE*)FindWindowWFunc + n);
printf("TextFun 函数指针地址:%p\r\n", TextFun);
hWnd = TextFun(NULL, NULL, L"DingtalkMsgComming", NULL);
int wjr = 0;
}
Sleep(5000);
}
FreeLibrary(hModule);
}
windbg调试该程序 设置断点
bu USER32!FindWindowW
可以看到函数指针地址和打印出来的都一样的 都是**68483650
当函数命中时,地址也一致
按F8(t)一直往下走,耐心走
可以看到他掉用了FindWindowExW函数 地址 00007ffc68485f50 和demo程序打印出来的一致
我们继续按F8还可以看到 他内部会调用USER32!InternalFindWindowExW函数,这个函数是未公开的函数地址是68485f6c
用idea工具查看下FindWindowExW函数,他调用一个sub_180025F6C函数
在点进去看
我们尝试定义InternalFindWindowExW函数原型指针
typedef HWND(WINAPI* FUN_InternalFindWindowExW)(HWND hWndParent, HWND hWndChildAfter, LPCWSTR lpClassName, LPCWSTR lpWindowName,int code);
用InternalFindWindowExW 减去 00007ffc68485f6c - FindWindowExW地址 00007ffc68485f50
= 0x1C
此时我们修改下源码
HMODULE hModule = LoadLibrary(L"user32.dll");
if (hModule != NULL)
{
while (true)
{
FUN_FindWindowW FindWindowWFunc = (FUN_FindWindowW)GetProcAddress(hModule, "FindWindowW");
if (FindWindowWFunc != NULL)
{
printf("FindWindowW 函数指针地址:%p\r\n", FindWindowWFunc);
HWND hWnd = FindWindowWFunc(L"123", NULL);
}
FUN_FindWindowExW FindWindowExWFunc = (FUN_FindWindowExW)GetProcAddress(hModule, "FindWindowExW");
if (FindWindowExWFunc != NULL)
{
printf("FindWindowExW 函数指针地址:%p\r\n", FindWindowExWFunc);
HWND hWnd = FindWindowExWFunc(NULL,NULL, L"DingtalkMsgComming", NULL);
int n = (BYTE*)FindWindowExWFunc - (BYTE*)FindWindowWFunc;
printf("指针偏移:%d 0X%X\r\n",n,n);
FUN_FindWindowExW TextFun = (FUN_FindWindowExW)((BYTE*)FindWindowWFunc + n);
printf("TextFun 函数指针地址:%p\r\n", TextFun);
HWND hWnd1 = TextFun(NULL, NULL, L"DingtalkMsgComming", NULL);
//int wjr = 0;
HWND hWnd2 = 0;
FUN_InternalFindWindowExW InternalFindWindowExWFunc = (FUN_InternalFindWindowExW)((BYTE*)FindWindowExWFunc + 0x1c);
if (InternalFindWindowExWFunc != NULL)
{
hWnd2 = InternalFindWindowExWFunc(NULL, NULL, L"DingtalkMsgComming", NULL,0);
}
int wjr = 0;
}
Sleep(5000);
}
FreeLibrary(hModule);
}
可以发现InternalFindWindowExWFunc 返回值和?FindWindowExW 一致