原理参见http://www.opscn.com/index.php?actio...rum=1&topic=15
代码:
/* * 安装ndis协议hook */ int init_ndis_hook(void* ProtoBlock) { PNDIS60_PROTOCOL_BLOCK protocol = ProtoBlock; PNDIS_OPEN_BLOCK TcpOpenBlock = NULL; PUNICODE_STRING BindDeviceName = NULL; PUNICODE_STRING RootDeviceName = NULL; unsigned char *buf = NULL; KdPrint(("init_ndis_hook:%x %x\n", protocol, protocol->NextProtocol)); ndisFindMiniportOnGlobalList = search_ndisFindMiniportOnGlobalList(); while (protocol = protocol->NextProtocol) { PUNICODE_STRING Name = NULL; Name = &protocol->Name; KdPrint(("Enume protocol %wZ\n", Name)); if (0 == wcsncmp(Name->Buffer, (const wchar_t*)&L"TCPIP", Name->Length>>1)){ TcpOpenBlock = protocol->OpenQueue; break; } } if (!TcpOpenBlock) return -1; KdPrint(("TcpOpenBlock %x %x\n", TcpOpenBlock, MmUserProbeAddress)); ndis_hook_info.OpenBlock = TcpOpenBlock; /* 搜索BindDeviceName以及RootDeviceName */ for (buf = (unsigned char*)TcpOpenBlock; buf < (unsigned char*)TcpOpenBlock + 0x500; buf+=4) { if (*(PULONG)(buf) > MmUserProbeAddress && **(PULONG*)(buf) == 0x005e005c && **(PULONG*)(buf + 4) == 0x005e005c) { BindDeviceName = *(PUNICODE_STRING*)buf; RootDeviceName = *(PUNICODE_STRING*)(buf + 4); ndis_hook_info.RootDeviceName = RootDeviceName; KdPrint(("tcp root dev %wZ\n", RootDeviceName)); break; } } /* 搜索 ReceiveNetBufferLists 地址 */ for (buf = (unsigned char*)TcpOpenBlock; buf < (unsigned char*)TcpOpenBlock + 0x500; buf+=4) { if (*(PULONG)(buf) > MmUserProbeAddress && *(PULONG)(buf) == *(PULONG)(buf + 4) && *(PULONG)(buf) == *(PULONG)(buf + 12)) { /* buf->tcpip!FlReceiveNetBufferListChain */ ndis_hook_info.POpenBlockReceiveHandler = (PVOID*)(buf + 8); ndis_hook_info.ReceiveNetBufferLists = *(PVOID*)(buf + 8); KdPrint(("ReceiveNetBufferLists:%x\n", *(PVOID*)(buf + 8))); break; } } /* 搜索底层 miniblock数据发送函数 */ if (ndisFindMiniportOnGlobalList && RootDeviceName) { PNDIS_MINIPORT_BLOCK miniBlock = ndisFindMiniportOnGlobalList(RootDeviceName); if (miniBlock) { /* 0x16c NextSendNetBufferListsHandler 偏移地址NDIS6中固定 */ PVOID NextSendNetBufferListsHandler = *(PVOID*)((char*)miniBlock + 0x16c); ndis_hook_info.MiniBlock = miniBlock; ndis_hook_info.PMiniBlockNextSndHandler = (PVOID*)((char*)miniBlock + 0x16c); ndis_hook_info.NextSendNetBufferListsHandler = NextSendNetBufferListsHandler; KdPrint(("miniBlock: %x %x\n", miniBlock, NextSendNetBufferListsHandler)); } else { KdPrint(("ndisFindMiniportOnGlobalList failed!\n")); } } /* 进行NDIS60的HOOK处理 */ if (ndis_hook_info.POpenBlockReceiveHandler) *ndis_hook_info.POpenBlockReceiveHandler = HookReceiveNetBuferLists; if (ndis_hook_info.PMiniBlockNextSndHandler) *ndis_hook_info.PMiniBlockNextSndHandler = HookSendNetBufferLists; return 0; }
WDK7600编译,Windows7 旗舰版SP1测试通过