第一次使用 detours 库,参照网上的代码做了一个 api hook 的 dll,并注入到 explorer.exe 中,在 win2003 下测试正常。 以下是 dll 代码: #define DLL_EXPORT #include "use_detour.h" #include "../detour/detours.h" #include <stdio.h> #pragma comment( lib, "../detour/detoured.lib" ) #pragma comment( lib, "../detour/detours.lib" ) PROC g_proc = NULL; BOOL WINAPI myShellNotifyIconW ( DWORD dwMessage, PNOTIFYICONDATAW lpData ); // int WINAPI DllMain( HINSTANCE hInst, DWORD dwReason, LPVOID lpReserved ) { switch( dwReason ) { case DLL_PROCESS_ATTACH: OutputDebugString( "===== dll attach =====/n" ); if( !hook() ) { OutputDebugString( "===== hook failed ! =====/n" ); return FALSE; } else OutputDebugString( "===== hook succeeded ! =====/n" ); break; case DLL_PROCESS_DETACH: unhook(); OutputDebugString( "===== dll detach =====/n" ); break; } return TRUE; } BOOL DLLAPI hook() { HMODULE hMod = NULL; if( NULL != g_proc ) return FALSE; hMod = GetModuleHandle( "Shell32.dll" ); if( NULL == hMod ) { OutputDebugString( "===== GetModuleHandle failed ! =====/n" ); return FALSE; } g_proc = GetProcAddress( hMod, "Shell_NotifyIconW" ); if( NULL == g_proc ) { OutputDebugString( "===== GetProcAddress failed ! =====/n" ); return FALSE; } DetourTransactionBegin(); DetourUpdateThread( GetCurrentThread() ); DetourAttach( (PVOID*)&g_proc, myShellNotifyIconW ); return ( NO_ERROR == DetourTransactionCommit() ); } void DLLAPI unhook() { DetourTransactionBegin(); DetourUpdateThread( GetCurrentThread() ); DetourDetach( (PVOID*)&g_proc, myShellNotifyIconW ); DetourTransactionCommit(); g_proc = NULL; } BOOL WINAPI myShellNotifyIconW( DWORD dwMessage, PNOTIFYICONDATAW lpData ) { static char lpszText[MAX_PATH] = { 0 }; switch( dwMessage ) { case NIM_ADD: memset( lpszText, 0, sizeof(char) * MAX_PATH ); sprintf( lpszText, "===== NIM_ADD - 0x%08x =====/n", lpData->hWnd ); OutputDebugString( lpszText ); break; case NIM_DELETE: memset( lpszText, 0, sizeof(char) * MAX_PATH ); sprintf( lpszText, "===== NIM_DEL - 0x%08x =====/n", lpData->hWnd ); OutputDebugString( lpszText ); break; default: break; } return g_proc( dwMessage, lpData ); }