峥嵘岁月

joshua_yu的网络空间

用户操作
[即时聊天] [发私信] [加为好友]
俞峥ID:joshua_yu
106082次访问,排名851好友6人,关注者16
人生总有些阶段,新的起点,新的心情,没有好也没有坏,生活总是辩证而真实地存在,感谢所有人!
joshua_yu的文章
原创 44 篇
翻译 2 篇
转载 42 篇
评论 32 篇
joshua的公告
联系方式: QQ:404271575 MSN:joshua_yu@263.net
最近评论
TE:安高科技:http://www.amgotech.com
bluehouse1985:Linux 环境下的多核调试
— Intel + Totalview 强强联合!
目前,在软件开发行业,各种性能优异的调试工具层出不穷。但是,它们中的绝大部分都只支持windows环境。即使能支持linux平台,操作起来也很不方便。因此,对于长期在linux上编写程序的开发人员来说,如何调试就成了一个令人头痛的问题!Intel软件 和 Total……
sap99:www.sap99.com/,SAP99资料多多

SAP免费资料下载
http://www.sap99.com

有很多的学习资料,推荐一下,
wBlf_www:请问我在过滤函数中截获所有收发数据包,会否有漏包的现象,我发现通过web发邮件,截获的数据不能恢复出邮件发出的状态(邮件包括内容和多个附件)。
wBlf_www:请问我在过滤函数中截获所有收发数据包,会否有漏包的现象,我发现通过web发邮件,截获的数据不能恢复出邮件发出的状态(邮件包括内容和多个附件)。
文章分类
收藏
    相册
    08年第一期儿子照片
    过年
    交大新面貌
    我的可爱儿子
    周末烧烤之众生相
    关注的Blog
    EVA的回收站
    joyfire的space
    Kendiv的专栏
    PJF的Blog
    WebCrazy的Blog
    孟言的blog
    野路子(http://wulujia.com)
    铁卷大成天下
    网络收藏夹
    China CISSP论坛(文档保护)
    China Uniix
    developerWorks Linux 专栏
    docshow
    linux伊甸园
    OSR在线论坛
    PKI论坛
    reactos
    rootkit论坛
    Sysinternals论坛
    中国Linux公社
    中国Linux论坛
    协议分析网论坛
    安全焦点
    看雪技术学院论坛
    驱动开发网
    存档
    软件项目交易
    订阅我的博客
    XML聚合  FeedSky
    订阅到鲜果
    订阅到Google
    订阅到抓虾
    订阅到BlogLines
    订阅到Yahoo
    订阅到GouGou
    订阅到飞鸽
    订阅到Rojo
    订阅到newsgator
    订阅到netvibes

    转载 NDIS Hook的框架代码收藏

    新一篇: 基于IMD的包过滤防火墙原理与实现 | 旧一篇: 对PassThru中的Protocol.c的注释

    //
    //Protocol Wrapper Version 1.05
    //Author: gjp
    //email: gjpland@netease.com
    //


    #include "NdisHook.h"
    #include "HookRule.h"

    #pragma pack(push)
    #pragma pack(1)
    typedef struct _HOOK_CONTEXT_STRUCT
    {
    //runtime code
    ubyte code1_0x58; //0x58 | pop eax | pop caller IP from stack to eax
    ubyte code2_0x68; //0x68 | push IMM | push our hook context address
    struct _HOOK_CONTEXT_STRUCT *m_pHookContext;//point this
    ubyte code3_0x50; //0x50 | push eax | push caller IP from eax to stack
    ubyte code4_0xE9; //0xE9 | jmp HookProc | jump our hook proc
    udword m_pHookProcOffset;

    //our context data

    PVOID m_pOriginalProc;
    PVOID m_pHookProc;
    PVOID m_pBindAdaptHandle;
    PVOID m_pProtocolContent;
    PVOID *m_ppOriginPtr;

    struct _HOOK_CONTEXT_STRUCT *m_pHookNext;

    }HOOK_CONTEXT_STRUCT;
    #pragma pack(pop)

    HOOK_CONTEXT_STRUCT *m_pOurAllOfHookContext = NULL;

    dword m_IsFilterEnabled = FALSE;
    NDIS_HANDLE m_ourPacketPoolHandle = NULL;
    NDIS_HANDLE m_ourBufferPoolHandle = NULL;
    PNDIS_PACKET m_ourPacketHandle = NULL;
    PNDIS_BUFFER m_ourBufferHandle = NULL;
    PVOID m_ourBuffer = NULL;

    void ReadPacket(PNDIS_PACKET Packet,PVOID pBuffer,udword dwBufSize);
    uword wswap(uword value);

    void HookUnload(void)
    {
    ReleaseHookFunc();

    if( m_ourBufferHandle )
    {
    NdisFreeBuffer(m_ourBufferHandle);
    m_ourBufferHandle = NULL;
    }
    if( m_ourBuffer )
    {
    NdisFreeMemory(m_ourBuffer,MAX_PACKET_SIZE,0);
    m_ourBuffer = NULL;
    }
    if( m_ourPacketHandle )
    {
    NdisFreePacket(m_ourPacketHandle);
    m_ourPacketHandle = NULL;
    }
    if( m_ourBufferPoolHandle )
    {
    NdisFreeBufferPool(m_ourBufferPoolHandle);
    m_ourBufferPoolHandle = NULL;
    }
    if( m_ourPacketPoolHandle )
    {
    NdisFreePacketPool(m_ourPacketPoolHandle);
    m_ourPacketPoolHandle = NULL;
    }
    return;
    }
    dword HookInit(void)
    {
    NTSTATUS status;

    m_ourPacketPoolHandle = NULL;
    NdisAllocatePacketPool(&status,&m_ourPacketPoolHandle,0xFFF,0x10);
    if( status != NDIS_STATUS_SUCCESS )
    return FALSE;

    m_ourBufferPoolHandle = NULL;
    NdisAllocateBufferPool(&status,&m_ourBufferPoolHandle,0x10);
    if( status != NDIS_STATUS_SUCCESS )
    return FALSE;

    m_ourBuffer = NULL;
    status = NdisAllocateMemoryWithTag(&m_ourBuffer,MAX_PACKET_SIZE,'NAMW');
    if( status != NDIS_STATUS_SUCCESS )
    return FALSE;

    m_ourBufferHandle = NULL;
    NdisAllocateBuffer(&status,&m_ourBufferHandle,m_ourBufferPoolHandle,m_ourBuffer,MAX_PACKET_SIZE);
    if( status != NDIS_STATUS_SUCCESS )
    return FALSE;

    m_ourPacketHandle = NULL;
    NdisAllocatePacket(&status,&m_ourPacketHandle,m_ourPacketPoolHandle);
    if( status != NDIS_STATUS_SUCCESS )
    return FALSE;

    NdisChainBufferAtFront(m_ourPacketHandle,m_ourBufferHandle);
    return TRUE;
    }

    typedef struct _NDIS41_PROTOCOL_CHARACTERISTICS
    {
    #ifdef __cplusplus
    NDIS40_PROTOCOL_CHARACTERISTICS Ndis40Chars;
    #else
    NDIS40_PROTOCOL_CHARACTERISTICS;
    #endif

    //
    // Start of NDIS 4.1 extensions.
    //

    CO_SEND_COMPLETE_HANDLER CoSendCompleteHandler;
    CO_STATUS_HANDLER CoStatusHandler;
    CO_RECEIVE_PACKET_HANDLER CoReceivePacketHandler;
    CO_REQUEST_HANDLER CoRequestHandler;
    CO_REQUEST_COMPLETE_HANDLER CoRequestCompleteHandler;

    } NDIS41_PROTOCOL_CHARACTERISTICS;

    dword HookProtocol(void)
    {
    //Default ndis version is 5.0
    NDIS_PROTOCOL_CHARACTERISTICS ourNPC;
    NDIS_STRING protoName = NDIS_STRING_CONST("HdFw_Slot");
    NDIS_STATUS Status;
    NDIS_HANDLE ourProtocolHandle = NULL;
    byte *ProtocolChain;
    dword offset;
    dword len;

    // NDIS_PROTOCOL_BLOCK *pNdisBlock = NULL;

    // pNdisBlock = pNdisBlock->NextProtocol;
    // pNdisBlock->NextProtocol = NULL;

    memset(&ourNPC,0,sizeof(NDIS_PROTOCOL_CHARACTERISTICS));


    if( m_dwMajorVersion == 0x03 )
    {
    len = sizeof(NDIS30_PROTOCOL_CHARACTERISTICS);
    //We must need at least ndis version 3.10
    ourNPC.MajorNdisVersion = 0x03;
    ourNPC.MinorNdisVersion = 0x0A;
    }
    else
    if( m_dwMajorVersion == 0x04 )
    {
    len = sizeof(NDIS40_PROTOCOL_CHARACTERISTICS);

    ourNPC.MajorNdisVersion = 0x04;
    ourNPC.MinorNdisVersion = 0x00;
    }
    else
    { //treat as version 5.0
    len = sizeof(NDIS50_PROTOCOL_CHARACTERISTICS);

    ourNPC.MajorNdisVersion = 0x05;
    ourNPC.MinorNdisVersion = 0x00;
    }

    ourNPC.Name = protoName;
    ourNPC.OpenAdapterCompleteHandler = PtOpenAdapterComplete;
    ourNPC.CloseAdapterCompleteHandler = PtCloseAdapterComplete;
    ourNPC.SendCompleteHandler = PtSendComplete;
    ourNPC.TransferDataCompleteHandler = PtTransferDataComplete;
    ourNPC.ResetCompleteHandler = PtResetComplete;
    ourNPC.RequestCompleteHandler = PtRequestComplete;
    ourNPC.ReceiveHandler = PtReceive;
    ourNPC.ReceiveCompleteHandler = PtReceiveComplete;
    ourNPC.StatusHandler = PtStatus;
    ourNPC.StatusCompleteHandler = PtStatusComplete;
    ourNPC.BindAdapterHandler = PtBindAdapter;
    ourNPC.UnbindAdapterHandler = PtUnbindAdapter;
    ourNPC.UnloadHandler = PtUnload;
    ourNPC.ReceivePacketHandler = PtReceivePacket;
    ourNPC.PnPEventHandler = PtPNPHandler;

    NdisRegisterProtocol(&Status,&ourProtocolHandle,&ourNPC,len);
    if( !NT_SUCCESS(Status) || ourProtocolHandle == NULL )
    return FALSE;

    //NdisRegisterProtocol return hand reference of NDIS_PROTOCOL_BLOCK;
    ProtocolChain = (byte *)ourProtocolHandle;
    while(1)
    {
    DebugInfoCount++;

    //Obtain pointer to next protocol link.
    if( m_dwMajorVersion == 0x03 )
    offset = 4;
    else
    if( m_dwMajorVersion == 0x04 )
    {
    if( m_dwMinorVersion == 0x01 )
    offset = 0x8C;
    else
    offset = 0x60;
    }
    else
    if( m_dwMajorVersion == 0x05 )
    //NDIS_PROTOCOL_BLOCK->NextProtocol
    offset = 0x10;
    else
    //Error
    break;

    ProtocolChain = ((byte **)(ProtocolChain + offset))[0];
    if( ProtocolChain == NULL )
    break;

    HookFuncBlock(ProtocolChain);
    }
    if( m_dwMajorVersion != 4 )
    NdisDeregisterProtocol(&Status,ourProtocolHandle);
    else
    {
    // ((byte *)ourProtocolHandle)[0x0C] = 0x01;
    // NdisDeregisterProtocol(&Status,ourProtocolHandle);
    }
    return TRUE;
    }
    // ProtocolContent
    // Version NextChain offset NDIS_PROTOCOL_CHARACTERISTICS offset BindingAdaptHandle offset
    // NDIS 3.XX 0x04 0x14 0x08
    // NDIS 4.XX 0x60 0x14 0x00
    // NDIS 4.01 0x8C 0x14 0x00
    // NDIS 5.XX 0x10 0x14 0x00


    //-----
    VOID HookProtocolSendPackets(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE MiniportAdapterContext,
    IN PPNDIS_PACKET PacketArray,
    IN UINT NumberOfPackets
    );

    NDIS_STATUS HookProtocolWanSend(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE MacBindingHandle,
    IN NDIS_HANDLE LinkHandle,
    IN PVOID Packet
    );
    NDIS_STATUS HookProtocolSend(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE MacBindingHandle,
    IN PNDIS_PACKET Packet
    );

    NDIS_STATUS HookProtocolReceive(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE ProtocolBindingContext,
    IN NDIS_HANDLE MacReceiveContext,
    IN PVOID HeaderBuffer,
    IN UINT HeaderBufferSize,
    IN PVOID LookAheadBuffer,
    IN UINT LookaheadBufferSize,
    IN UINT PacketSize
    );
    NDIS_STATUS HookWanReceive(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE NdisLinkHandle,
    IN PUCHAR Packet,
    IN ULONG PacketSize
    );
    INT HookProtocolReceivePacket(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE ProtocolBindingContext,
    IN PNDIS_PACKET Packet
    );

    VOID HookBindAdapterHandler(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    OUT PNDIS_STATUS Status,
    IN NDIS_HANDLE BindContext,
    IN PNDIS_STRING DeviceName,
    IN PVOID SystemSpecific1,
    IN PVOID SystemSpecific2);

    VOID HookSendComplete(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE ProtocolBindingContext,
    IN PNDIS_PACKET Packet,
    IN NDIS_STATUS Status
    );


    void ReleaseHookFunc(void)
    {

    HOOK_CONTEXT_STRUCT *pHookContext,*pNext;

    pHookContext = m_pOurAllOfHookContext;
    m_pOurAllOfHookContext = NULL;
    while(pHookContext)
    {
    pNext = pHookContext->m_pHookNext;
    pHookContext->m_ppOriginPtr[0] = pHookContext->m_pOriginalProc;
    ExFreePool(pHookContext);
    pHookContext = pNext;
    }
    return;
    }

    HOOK_CONTEXT_STRUCT *IsHookedNdisFunc(PVOID pAddr)
    {

    HOOK_CONTEXT_STRUCT *pHookContext;

    pHookContext = m_pOurAllOfHookContext;
    while(pHookContext)
    {
    if( pHookContext == pAddr )
    break;
    pHookContext = pHookContext->m_pHookNext;
    }
    return pHookContext;
    }
    HOOK_CONTEXT_STRUCT *IsHookedNdisFuncEx(PVOID *pAddr)
    {

    HOOK_CONTEXT_STRUCT *pHookContext;

    pHookContext = m_pOurAllOfHookContext;
    while(pHookContext)
    {
    if( pHookContext->m_ppOriginPtr == pAddr )
    break;
    pHookContext = pHookContext->m_pHookNext;
    }
    return pHookContext;
    }

    HOOK_CONTEXT_STRUCT *HookNdisFunc(PVOID pHookProc,PVOID *ppOrigProc,PVOID pBindAdaptHandle,PVOID pProtocolContent)
    {

    HOOK_CONTEXT_STRUCT *pHookContext;
    PVOID OrgFunc;

    pHookContext = IsHookedNdisFunc(ppOrigProc[0]);
    if( pHookContext )
    OrgFunc = pHookContext->m_pOriginalProc;
    else
    OrgFunc = ppOrigProc[0];
    if( OrgFunc == NULL )
    return NULL;

    pHookContext = IsHookedNdisFuncEx(ppOrigProc);
    if( pHookContext )
    return pHookContext;
    pHookContext = ExAllocatePoolWithTag(NonPagedPool,sizeof(HOOK_CONTEXT_STRUCT),'HCSP');
    if( pHookContext == NULL )
    return NULL;
    memset(pHookContext,0,sizeof(HOOK_CONTEXT_STRUCT));

    pHookContext->code1_0x58 = 0x58;
    pHookContext->code2_0x68 = 0x68;
    pHookContext->code3_0x50 = 0x50;
    pHookContext->code4_0xE9 = 0xE9;

    pHookContext->m_pHookContext = pHookContext;
    pHookContext->m_pHookProcOffset = ((udword)pHookProc) - (((udword)&pHookContext->m_pHookProcOffset) + sizeof(udword));
    pHookContext->m_pBindAdaptHandle = pBindAdaptHandle;
    pHookContext->m_pProtocolContent = pProtocolContent;
    pHookContext->m_pOriginalProc = OrgFunc;//ppOrigProc[0];
    pHookContext->m_ppOriginPtr = ppOrigProc;
    pHookContext->m_pHookProc = pHookProc;
    pHookContext->m_pHookNext = m_pOurAllOfHookContext;
    m_pOurAllOfHookContext = pHookContext;

    ppOrigProc[0] = pHookContext;
    return pHookContext;
    }

    typedef
    struct _NDIS40_OPEN_BLOCK
    {
    PNDIS_MAC_BLOCK MacHandle; // pointer to our MAC
    NDIS_HANDLE MacBindingHandle; // context when calling MacXX funcs
    PNDIS_ADAPTER_BLOCK AdapterHandle; // pointer to our adapter
    PNDIS_PROTOCOL_BLOCK ProtocolHandle; // pointer to our protocol
    NDIS_HANDLE ProtocolBindingContext;// context when calling ProtXX funcs
    PNDIS_OPEN_BLOCK AdapterNextOpen; // used by adapter's OpenQueue
    PNDIS_OPEN_BLOCK ProtocolNextOpen; // used by protocol's OpenQueue
    PFILE_OBJECT FileObject; // created by operating system
    BOOLEAN Closing; // TRUE when removing this struct
    BOOLEAN Unloading; // TRUE when processing unload
    NDIS_HANDLE CloseRequestHandle; // 0 indicates an internal close
    KSPIN_LOCK SpinLock; // guards Closing
    PNDIS_OPEN_BLOCK NextGlobalOpen;

    //
    // These are optimizations for getting to MAC routines. They are not
    // necessary, but are here to save a dereference through the MAC block.
    //

    SEND_HANDLER SendHandler;
    TRANSFER_DATA_HANDLER TransferDataHandler;

    //
    // These are optimizations for getting to PROTOCOL routines. They are not
    // necessary, but are here to save a dereference through the PROTOCOL block.
    //

    SEND_COMPLETE_HANDLER SendCompleteHandler;
    TRANSFER_DATA_COMPLETE_HANDLER TransferDataCompleteHandler;
    RECEIVE_HANDLER ReceiveHandler;
    RECEIVE_COMPLETE_HANDLER ReceiveCompleteHandler;

    //
    // Extentions to the OPEN_BLOCK since Product 1.
    //
    RECEIVE_HANDLER PostNt31ReceiveHandler;
    RECEIVE_COMPLETE_HANDLER PostNt31ReceiveCompleteHandler;

    //
    // NDIS 4.0 extensions
    //
    RECEIVE_PACKET_HANDLER ReceivePacketHandler;
    SEND_PACKETS_HANDLER SendPacketsHandler;

    //
    // Needed for PnP
    //
    UNICODE_STRING AdapterName; // Upcased name of the adapter we are bound to
    }NDIS40_OPEN_BLOCK,*PNDIS40_OPEN_BLOCK;

    void HookFuncBlock(byte *ProtocolContent)
    {

    PNDIS_PROTOCOL_CHARACTERISTICS pProChar;
    dword IsWan;
    NDIS_STRING WanString = NDIS_STRING_CONST("NDISWAN");
    NDIS_STRING DeviceWanString = NDIS_STRING_CONST("\\DEVICE\\NDISWAN");

    NDIS_STRING TcpipString = NDIS_STRING_CONST("Tcpip");
    NDIS_STRING TcpArpString = NDIS_STRING_CONST("TCPIP_WANARP");
    NDIS_STRING RasArpString = NDIS_STRING_CONST("RASARP");

    if( ProtocolContent == NULL )
    return;
    //Get pointer to NDIS_PROTOCOL_CHARACTERISTICS from protocol content
    pProChar = (PNDIS_PROTOCOL_CHARACTERISTICS)(ProtocolContent + 0x14);

    if( KeGetCurrentIrql() == PASSIVE_LEVEL )
    {
    //Check protocol name whether is Wan Lan protocol so that we can correctly hook our function
    if( !RtlCompareUnicodeString(&pProChar->Name,&WanString,TRUE) ||
    !RtlCompareUnicodeString(&pProChar->Name,&DeviceWanString,TRUE) )
    {
    IsWan = 1;
    }
    else
    IsWan = 0;

    //We r only interest in following protocol
    if( !(!RtlCompareUnicodeString(&pProChar->Name,&TcpipString,TRUE) ||
    !RtlCompareUnicodeString(&pProChar->Name,&TcpArpString,TRUE) ||
    !RtlCompareUnicodeString(&pProChar->Name,&RasArpString,TRUE)) )
    {
    return;
    }
    }
    else
    IsWan = 0;

    //
    if( !IsWan )
    {
    HookNdisFunc(HookProtocolReceive,(PVOID *)&pProChar->ReceiveHandler,NULL,ProtocolContent);

    //{{added by gjp 6.24
    // __asm int 3;
    // HookNdisFunc(HookSendComplete,(PVOID *)&pProChar->SendCompleteHandler,NULL,ProtocolContent);
    //}}
    }
    else
    HookNdisFunc(HookWanReceive,(PVOID *)&pProChar->WanReceiveHandler,NULL,ProtocolContent);

    if(pProChar->MajorNdisVersion > 0x03 )
    {
    HookNdisFunc(HookProtocolReceivePacket,(PVOID *)&pProChar->ReceivePacketHandler,NULL,ProtocolContent);
    HookNdisFunc(HookBindAdapterHandler,(PVOID *)&pProChar->BindAdapterHandler,NULL,ProtocolContent);

    }

    //pProChar->Name;
    //We should obtain and save BindAdaptHandle in order to pass it to NdisTransferData
    //BindAdaptHandle is pNdisOpenBlock
    if( m_dwMajorVersion == 0x05 )
    {
    PNDIS_OPEN_BLOCK pNdisOpenBlock;

    pNdisOpenBlock = ((PNDIS_OPEN_BLOCK *)ProtocolContent)[0];
    while(pNdisOpenBlock)
    {
    //__asm int 3;
    if( !IsWan )
    {
    HookNdisFunc(HookProtocolSend,(PVOID *)&pNdisOpenBlock->SendHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookProtocolReceive,(PVOID *)&pNdisOpenBlock->PostNt31ReceiveHandler,pNdisOpenBlock,ProtocolContent);
    //{{added by gjp 6.24
    // __asm int 3;
    // HookNdisFunc(HookSendComplete,(PVOID *)&pNdisOpenBlock->SendCompleteHandler,pNdisOpenBlock,ProtocolContent);
    //}}
    }
    else
    {
    HookNdisFunc(HookProtocolWanSend,(PVOID *)&pNdisOpenBlock->WanSendHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookWanReceive,(PVOID *)&pNdisOpenBlock->WanReceiveHandler,pNdisOpenBlock,ProtocolContent);
    }
    HookNdisFunc(HookProtocolReceive,(PVOID *)&pNdisOpenBlock->ReceiveHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookProtocolReceivePacket,(PVOID *)&pNdisOpenBlock->ReceivePacketHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookProtocolSendPackets,(PVOID *)&pNdisOpenBlock->SendPacketsHandler,pNdisOpenBlock,ProtocolContent);
    pNdisOpenBlock = pNdisOpenBlock->ProtocolNextOpen;
    }
    }
    else
    if( m_dwMajorVersion == 0x04 )
    {
    PNDIS40_OPEN_BLOCK pNdisOpenBlock;
    pNdisOpenBlock = ((PNDIS40_OPEN_BLOCK *)ProtocolContent)[0];

    while(pNdisOpenBlock)
    {
    if( !IsWan )
    {
    HookNdisFunc(HookProtocolSend,(PVOID *)&pNdisOpenBlock->SendHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookProtocolReceive,(PVOID *)&pNdisOpenBlock->PostNt31ReceiveHandler,pNdisOpenBlock,ProtocolContent);
    }
    else
    {
    HookNdisFunc(HookProtocolWanSend,(PVOID *)&pNdisOpenBlock->SendHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookWanReceive,(PVOID *)&pNdisOpenBlock->PostNt31ReceiveHandler,pNdisOpenBlock,ProtocolContent);
    }

    HookNdisFunc(HookProtocolReceive,(PVOID *)&pNdisOpenBlock->ReceiveHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookProtocolReceivePacket,(PVOID *)&pNdisOpenBlock->ReceivePacketHandler,pNdisOpenBlock,ProtocolContent);
    HookNdisFunc(HookProtocolSendPackets,(PVOID *)&pNdisOpenBlock->SendPacketsHandler,pNdisOpenBlock,ProtocolContent);
    pNdisOpenBlock = (PNDIS40_OPEN_BLOCK)pNdisOpenBlock->ProtocolNextOpen;
    }
    // HookNdisFunc(HookProtocolReceivePacket,(PVOID *)&pNdisOpenBlock->ReceivePacketHandler,pNdisOpenBlock,ProtocolContent);

    }
    else
    if( m_dwMajorVersion == 0x03 )
    {//Unknown information of ndis3.0 NDIS_OPEN_BLOCK struct

    }
    return;
    }
    void CheckSendHandle(HOOK_CONTEXT_STRUCT *pOurContext)
    {
    HOOK_CONTEXT_STRUCT *pHookContext;

    if( pOurContext == NULL ||
    pOurContext->m_pBindAdaptHandle == NULL )
    return;

    if( m_dwMajorVersion == 5 )
    {
    PNDIS_OPEN_BLOCK pNdisOpenBlock;

    pNdisOpenBlock = (PNDIS_OPEN_BLOCK)pOurContext->m_pBindAdaptHandle;

    pHookContext = (HOOK_CONTEXT_STRUCT *)pNdisOpenBlock->SendHandler;
    if( pHookContext )
    {
    if( !(pHookContext->m_ppOriginPtr == (PVOID *)&pNdisOpenBlock->SendHandler
    && pHookContext->m_pHookProc == (PVOID)HookProtocolSend) )
    {

    pHookContext = IsHookedNdisFuncEx((PVOID *)&pNdisOpenBlock->SendHandler);
    if( pHookContext )
    {
    if( pHookContext->m_pOriginalProc == (PVOID)pNdisOpenBlock->SendHandler)
    {
    pNdisOpenBlock->SendHandler = (SEND_HANDLER)pHookContext;
    }
    }
    }
    }

    pHookContext = (HOOK_CONTEXT_STRUCT *)pNdisOpenBlock->SendPacketsHandler;
    if( pHookContext )
    {
    if( !(pHookContext->m_ppOriginPtr == (PVOID *)&pNdisOpenBlock->SendPacketsHandler
    && pHookContext->m_pHookProc == (PVOID)HookProtocolSendPackets) )
    {

    pHookContext = IsHookedNdisFuncEx((PVOID *)&pNdisOpenBlock->SendPacketsHandler);
    if( pHookContext )
    {
    if( pHookContext->m_pOriginalProc == (PVOID)pNdisOpenBlock->SendPacketsHandler)
    {
    pNdisOpenBlock->SendPacketsHandler = (SEND_PACKETS_HANDLER)pHookContext;
    }
    }
    }
    }
    }
    else
    if( m_dwMajorVersion == 4 )
    {
    PNDIS40_OPEN_BLOCK pNdisOpenBlock;
    pNdisOpenBlock = (PNDIS40_OPEN_BLOCK)pOurContext->m_pBindAdaptHandle;

    pHookContext = (HOOK_CONTEXT_STRUCT *)pNdisOpenBlock->SendHandler;
    if( pHookContext )
    {
    if( !(pHookContext->m_ppOriginPtr == (PVOID *)&pNdisOpenBlock->SendHandler
    && pHookContext->m_pHookProc == (PVOID)HookProtocolSend) )
    {

    pHookContext = IsHookedNdisFuncEx((PVOID *)&pNdisOpenBlock->SendHandler);
    if( pHookContext )
    {
    if( pHookContext->m_pOriginalProc == (PVOID)pNdisOpenBlock->SendHandler)
    {
    pNdisOpenBlock->SendHandler = (SEND_HANDLER)pHookContext;
    }
    }
    }
    }

    pHookContext = (HOOK_CONTEXT_STRUCT *)pNdisOpenBlock->SendPacketsHandler;
    if( pHookContext )
    {
    if( !(pHookContext->m_ppOriginPtr == (PVOID *)&pNdisOpenBlock->SendPacketsHandler
    && pHookContext->m_pHookProc == (PVOID)HookProtocolSendPackets) )
    {

    pHookContext = IsHookedNdisFuncEx((PVOID *)&pNdisOpenBlock->SendPacketsHandler);
    if( pHookContext )
    {
    if( pHookContext->m_pOriginalProc == (PVOID)pNdisOpenBlock->SendPacketsHandler)
    {
    pNdisOpenBlock->SendPacketsHandler = (SEND_PACKETS_HANDLER)pHookContext;
    }
    }
    }
    }
    }
    return;
    }

    dword HookFilterBuffer(HOOK_CONTEXT_STRUCT *pOurContext,PVOID pBuffer,udword PacketSize,dword isOutgoing)
    {
    NTSTATUS status;
    dword result = TRUE;

    switch(wswap(((PETHHDR)pBuffer)->h_proto))
    {
    case ETH_P_IP:
    {
    if( isOutgoing )
    TotalSendBytes += PacketSize;
    else
    TotalReceiveBytes += PacketSize;
    TotalIPPackets++;
    result = AnalyzeIP( (PIPHdr)(&((byte *)pBuffer)[sizeof(ETHHDR)]),PacketSize - sizeof(ETHHDR), isOutgoing);
    break;
    }
    case ETH_P_ARP:
    TotalARPPackets++;
    break;
    case ETH_P_RARP:
    break;
    default:
    TotalOtherPackets++;
    break;
    }
    return result;
    }

    dword HookFilterReceivePacket(HOOK_CONTEXT_STRUCT *pOurContext,udword TotalPacketSize,PVOID pHeadBuffer,udword dwHeadSize,PNDIS_PACKET pPacket,dword isOutgoing)
    {
    dword PacketSize;
    PVOID pBuffer = NULL;
    NTSTATUS status;
    PNDIS_BUFFER firstBuffer,nextBuffer;
    dword result = TRUE;
    byte *pBuf;

    NdisQueryPacket(pPacket,NULL,NULL,NULL,&PacketSize);
    if( /*!PacketSize ||*/ PacketSize + dwHeadSize < sizeof(ETHHDR) )
    return TRUE;


    status = NdisAllocateMemoryWithTag(&pBuffer,PacketSize + dwHeadSize,'NAMW');
    if( status != NDIS_STATUS_SUCCESS || pBuffer == NULL )
    return TRUE;//FALSE;
    //obtain content from the packet

    pBuf = (byte *)pBuffer;
    NdisMoveMemory(pBuf,pHeadBuffer,dwHeadSize);
    ReadPacket(pPacket,&pBuf[dwHeadSize],PacketSize);

    result = HookFilterBuffer(pOurContext,pBuffer,TotalPacketSize + dwHeadSize,isOutgoing);
    NdisFreeMemory(pBuffer,PacketSize + dwHeadSize,0);
    return result;
    }

    // Filter Packet
    // return 0 = block this packet

    dword HookFilterPacket(HOOK_CONTEXT_STRUCT *pOurContext,PNDIS_PACKET pPacket,dword isOutgoing)
    {
    dword PacketSize;
    PVOID pBuffer = NULL;
    NTSTATUS status;
    PNDIS_BUFFER firstBuffer,nextBuffer;
    dword result = TRUE;

    NdisQueryPacket(pPacket,NULL,NULL,NULL,&PacketSize);
    if( /*!PacketSize ||*/ PacketSize < sizeof(ETHHDR) )
    return TRUE;


    status = NdisAllocateMemoryWithTag(&pBuffer,PacketSize,'NAMW');
    if( status != NDIS_STATUS_SUCCESS || pBuffer == NULL )
    return TRUE;//FALSE;
    //obtain content from the packet
    ReadPacket(pPacket,pBuffer,PacketSize);

    result = HookFilterBuffer(pOurContext,pBuffer,PacketSize,isOutgoing);
    NdisFreeMemory(pBuffer,PacketSize,0);
    return result;
    }

    __declspec( naked )
    uword wswap(uword value)
    {
    __asm
    {
    movzx eax,byte ptr [esp + 5];
    mov ah ,byte ptr [esp + 4];
    ret 4
    }
    }

    void ReadPacket(PNDIS_PACKET Packet,PVOID pBuffer,udword dwBufSize)
    {
    PVOID virtualAddress;
    PNDIS_BUFFER firstBuffer, nextBuffer;
    ULONG totalLength;
    UINT len;
    PVOID pBuf = NULL;
    dword count = 0;

    NdisQueryPacket(Packet, NULL, NULL, &firstBuffer, NULL);
    while( firstBuffer != NULL)
    {
    //NdisQueryBufferSafe can't use in wdm1.0
    // NdisQueryBufferSafe(firstBuffer, &virtualAddress,
    // &len, 16 );
    NdisQueryBuffer(firstBuffer, &virtualAddress,
    &len);
    if(!virtualAddress)
    {
    //
    // System is running low on memory resources.
    // So fail the read.
    //
    break;
    }
    if( count + len > dwBufSize )
    break;
    NdisMoveMemory(&((byte *)pBuffer)[count],virtualAddress,len);
    count += len;
    NdisGetNextBuffer(firstBuffer, &nextBuffer);
    firstBuffer = nextBuffer;
    }
    return;
    }

    //----
    VOID HookProtocolSendPackets(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE MiniportAdapterContext,
    IN PPNDIS_PACKET PacketArray,
    IN UINT NumberOfPackets
    )
    {
    udword x;

    PPNDIS_PACKET FilterPacketArray;
    UINT NumberOfFilterPackets;

    if( pOurContext )
    {

    if( NumberOfPackets == 0 )
    {
    ((SEND_PACKETS_HANDLER)pOurContext->m_pOriginalProc)(
    MiniportAdapterContext,
    PacketArray,
    NumberOfPackets);
    return;
    }

    FilterPacketArray = ExAllocatePoolWithTag(NonPagedPool,sizeof(PNDIS_PACKET) * NumberOfPackets,'HFPA');
    if( FilterPacketArray == NULL )
    {
    ((SEND_PACKETS_HANDLER)pOurContext->m_pOriginalProc)(
    MiniportAdapterContext,
    PacketArray,
    NumberOfPackets);
    return;
    }

    for(NumberOfFilterPackets = 0,x = 0; x < NumberOfPackets; x++ )
    {

    if( HookFilterPacket(pOurContext,PacketArray[x],TRUE) )
    {
    FilterPacketArray[NumberOfFilterPackets++] = PacketArray[x];
    }
    }
    if( NumberOfFilterPackets )
    {
    ((SEND_PACKETS_HANDLER)pOurContext->m_pOriginalProc)(
    MiniportAdapterContext,
    FilterPacketArray,
    NumberOfFilterPackets);
    }
    ExFreePool(FilterPacketArray);
    }
    return;
    }

    NDIS_STATUS HookProtocolWanSend(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE MacBindingHandle,
    IN NDIS_HANDLE LinkHandle,
    IN PVOID Packet
    )
    {
    if( pOurContext )
    {
    return ((WAN_SEND_HANDLER)pOurContext->m_pOriginalProc)(
    MacBindingHandle,
    LinkHandle,
    Packet);
    }
    return NDIS_STATUS_SUCCESS;
    }

    NDIS_STATUS HookProtocolSend(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE MacBindingHandle,
    IN PNDIS_PACKET Packet
    )
    {
    // udword PacketSize;
    NTSTATUS status = NDIS_STATUS_SUCCESS;

    if( pOurContext )
    {
    if( HookFilterPacket(pOurContext,Packet,TRUE) )
    {
    status = ((SEND_HANDLER)pOurContext->m_pOriginalProc)(
    MacBindingHandle,
    Packet);
    }
    else
    status = NDIS_STATUS_NOT_ACCEPTED;
    }
    return status;
    }

    INT HookProtocolReceivePacket(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE ProtocolBindingContext,
    IN PNDIS_PACKET Packet
    )
    {
    NTSTATUS status = NDIS_STATUS_SUCCESS;

    if( pOurContext )
    {
    CheckSendHandle(pOurContext);

    if( HookFilterPacket(pOurContext,Packet,FALSE) )
    {
    status = ((RECEIVE_PACKET_HANDLER)pOurContext->m_pOriginalProc)(
    ProtocolBindingContext,
    Packet);
    }
    else
    status = NDIS_STATUS_NOT_ACCEPTED;
    }
    return status;
    }

    NDIS_STATUS HookWanReceive(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE NdisLinkHandle,
    IN PUCHAR Packet,
    IN ULONG PacketSize
    )
    {

    if( pOurContext )
    {
    return ((WAN_RECEIVE_HANDLER)pOurContext->m_pOriginalProc)(
    NdisLinkHandle,
    Packet,
    PacketSize);
    }
    return NDIS_STATUS_SUCCESS;
    }

    NDIS_STATUS HookProtocolReceive(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE ProtocolBindingContext,
    IN NDIS_HANDLE MacReceiveContext,
    IN PVOID HeaderBuffer,
    IN UINT HeaderBufferSize,
    IN PVOID LookAheadBuffer,
    IN UINT LookAheadBufferSize,
    IN UINT PacketSize
    )
    {
    NTSTATUS status = NDIS_STATUS_SUCCESS;

    if( pOurContext )
    {

    CheckSendHandle(pOurContext);
    // TotalReceiveBytes += PacketSize;

    if( pOurContext->m_pBindAdaptHandle )
    {
    udword len = 0;

    if( PacketSize > LookAheadBufferSize )
    {
    NdisTransferData(&status,pOurContext->m_pBindAdaptHandle,MacReceiveContext,0,PacketSize,m_ourPacketHandle,&len);
    }
    else
    {
    NdisMoveMemory(m_ourBuffer,LookAheadBuffer,PacketSize);
    }

    if( status == NDIS_STATUS_SUCCESS )
    {
    TotalTransferPackets++;

    if( !HookFilterReceivePacket(pOurContext,PacketSize,HeaderBuffer,HeaderBufferSize,m_ourPacketHandle,FALSE) )
    //if( !HookFilterPacket(pOurContext,m_ourPacketHandle,FALSE) )
    return NDIS_STATUS_NOT_ACCEPTED;
    }
    else
    if( status == NDIS_STATUS_PENDING )
    //Warning: Here An Error will be occured.
    TotalTransferPendingPackets++;
    else
    TotalTransferErrorPackets++;

    }
    else
    {
    TotalUnbindTransferPackets++;
    }
    status = ((RECEIVE_HANDLER)pOurContext->m_pOriginalProc)(
    ProtocolBindingContext,
    MacReceiveContext,
    HeaderBuffer,
    HeaderBufferSize,
    LookAheadBuffer,
    LookAheadBufferSize,
    PacketSize);
    }
    return status;
    }
    VOID HookBindAdapterHandler(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    OUT PNDIS_STATUS Status,
    IN NDIS_HANDLE BindContext,
    IN PNDIS_STRING DeviceName,
    IN PVOID SystemSpecific1,
    IN PVOID SystemSpecific2)
    {

    if( pOurContext )
    {
    ((BIND_HANDLER)pOurContext->m_pOriginalProc)(Status,BindContext,
    DeviceName,
    SystemSpecific1,
    SystemSpecific2);

    HookFuncBlock(pOurContext->m_pProtocolContent);
    TotalTransferErrorPackets++;
    }
    return;
    }

    VOID HookSendComplete(
    IN HOOK_CONTEXT_STRUCT *pOurContext,
    IN NDIS_HANDLE ProtocolBindingContext,
    IN PNDIS_PACKET Packet,
    IN NDIS_STATUS Status
    )
    {

    __asm int 3;
    ((SEND_COMPLETE_HANDLER)pOurContext->m_pOriginalProc)(
    ProtocolBindingContext,
    Packet,
    Status
    );
    return;
    }


    发表于 @ 2006年03月23日 15:06:00|评论(loading...)|编辑|收藏

    新一篇: 基于IMD的包过滤防火墙原理与实现 | 旧一篇: 对PassThru中的Protocol.c的注释

    评论:没有评论。

    发表评论  


    登录
    Csdn Blog version 3.1a
    Copyright © joshua