18,357
社区成员
发帖
与我相关
我的任务
分享
class CHOOKAPI {
public:
LPVOID pOldFunEntry, pNewFunEntry ; // 初始函数地址、HOOK后的函数地址
BYTE bOldByte[5], bNewByte[5] ; // 原始字节、目标字节
public:
CHOOKAPI () {}
~CHOOKAPI() {}
// 实现HOOK API
void Hook ( PSTR szModuleName, PSTR szFunName, FARPROC pFun )
{
HMODULE hMod = ::GetModuleHandleA ( szModuleName ) ;
if ( hMod != NULL )
{
pNewFunEntry = (LPVOID)pFun ;
pOldFunEntry = (LPVOID)GetProcAddress ( hMod, szFunName ) ;
bNewByte[0] = 0xE9 ;
*((PDWORD)(&(bNewByte[1]))) = (DWORD)pNewFunEntry - (DWORD)pOldFunEntry - 5 ;
DWORD dwProtect, dwWriteByte, dwReadByte ;
VirtualProtect ( (LPVOID)pOldFunEntry, 5, PAGE_READWRITE, &dwProtect );
ReadProcessMemory ( GetCurrentProcess(), (LPVOID)pOldFunEntry, bOldByte, 5, &dwReadByte ) ;
WriteProcessMemory ( GetCurrentProcess(), (LPVOID)pOldFunEntry, bNewByte, 5, &dwWriteByte ) ;
VirtualProtect ( (LPVOID)pOldFunEntry, 5, dwProtect, NULL ) ;
}
}
// 重新HOOK
void ReHook ()
{
DWORD dwProtect, dwWriteByte ;
VirtualProtect ( pOldFunEntry, 5, PAGE_READWRITE, &dwProtect );
WriteProcessMemory ( GetCurrentProcess(), pOldFunEntry, bNewByte, 5, &dwWriteByte ) ;
VirtualProtect ( pOldFunEntry, 5, dwProtect, NULL ) ;
}
// 撤消HOOK
void UnHook ()
{
DWORD dwProtect, dwWriteByte ;
VirtualProtect ( pOldFunEntry, 5, PAGE_READWRITE, &dwProtect );
WriteProcessMemory ( GetCurrentProcess(), pOldFunEntry, bOldByte, 5, &dwWriteByte ) ;
VirtualProtect ( pOldFunEntry, 5, dwProtect, NULL ) ;
}
} ;
CHOOKAPI dnshook;
long WINAPI DnsQuery_Wnew( __in PCWSTR pszName,
__in WORD wType,
__in DWORD Options,
__inout_opt PVOID pExtra,
__deref_out_opt PDNS_RECORD * ppQueryResults,
__deref_opt_out_opt PVOID * pReserved
)
{
dnshook.UnHook();
long ret=0;
/*
DNS解析相关的代码
*/
dnshook.ReHook();
return ret;
}
然后调用:
dnshook.Hook("dnsapi.dll","DnsQuery_W",(FARPROC)DnsQuery_Wnew);//写在NSPStartup或WSPStartup都可以
这样写在win7 64位下,就不能用了。
听说可以在NSPLookupServiceBegin NSPLookupServiceNext NSPLookupServiceEnd这三个函数里写代码。看找了好多资料也没有搞明白,也没有找到三个API成功的例子。
我应该怎么做了。不管是用hook还是NSP,只要能实现功能,都OK。
在网上收到的"使用NSPLookupServiceBegin的本地DNS截取例程 - 下载频道 - CSDN"这个里面的代码,只能取到域名