⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 filterrtns.cpp

📁 James Antognini和Tom Divine提供的PASSTHRU的编成实例。
💻 CPP
字号:
/**************************************************************************************************/      
/*                                                                                                */      
/* Copyright (C) 2003, James Antognini, antognini@mindspring.com.                                 */
/*                                                                                                */      
/**************************************************************************************************/      

#ifdef __cplusplus  // C++ conversion
extern "C"
{
#endif

#include <ndis.h>
#include "passthru.h"
#include "PktHdr.h"                                   
#include "WMIFunc.h"                                   
                                                   
#ifdef __cplusplus  // C++ conversion
}
#endif

#define JADrvNm         "JApassthru"     
#define JADrvRtnsName   "FilterRtns"       
#define JADrvRtnsVer    "1.01"           

#pragma comment(exestr,                               /* ja, 04.10.2003. */  \
                JADrvNm " " JADrvRtnsName " v" JADrvRtnsVer " compiled on " __DATE__ " at " __TIME__)    

/**************************************************************************************************/      
/*                                                                                                */      
/**************************************************************************************************/      
extern "C"
NDIS_STATUS                                                        
FilterPacket(                                         
             PADAPT               pAdapt,             // Address of adapter structure.
             PNDIS_PACKET         pPktDesc,           // Address of NDIS_PACKET, if available.  NULL if not.
             PUCHAR               pPayload,           // Address of packet payload if NDIS_PACKET is NULL.  Must contain at least the ethernet header and, 
                                                      //   if the type is IP, the IP header or, if the type is ARP or RARP, the ARP or RARP structure.
             BOOLEAN              bSend,              // TRUE if Send, FALSE if Receive.
             PBOOLEAN             pBDecision          // Address of boolean variable, whose value will be:  TRUE => drop packet and FALSE => do not drop.
                                                      //   But this is meaningful only if returned status is NDIS_STATUS_SUCCESS.
            )
{
 NDIS_STATUS             status = NDIS_STATUS_SUCCESS;
 #define                 szPayloadCopy ETH_MAX_PACKET_SIZE
 UCHAR                   PayloadCopy[szPayloadCopy];  // Area to receive packet payload if NDIS_PACKET provided.
 pEthHdr                 pETH;
 pIPHdr                  pIPH;
 ULONG const             LoopLim = 5;
 ULONG                   i,
                         ulUsed,
                         IPAddr,
                         ulOrigPayload;
 int                     lowIdx,
                         highIdx,
                         midPt;
 PPassthruIPAddrArray    pAddrArr;
 BOOLEAN                 bGotStorage = FALSE;
 #define                 szLclStorage 256
 union                                                // Area in stack to receive IP-address array, if the latter can be accommodated.
   {
    PassthruIPAddrArray  lclIPArray;
    char                 stuff[szLclStorage];         // EnsurelclIPArray is padded out to szLclStorage.
   };

 *pBDecision = FALSE;                                 // Default action is not to drop the packet.

 do                                                   // Big 'do' group.
   {
    if (NULL!=pPktDesc)                               // NDIS_PACKET provided?
      GetPktPayload(pPktDesc,                         // Copy payload
                    PayloadCopy,                      //   to area.
                    szPayloadCopy,                    // Amount of space in area.
                    &ulOrigPayload                    // Return number of bytes in packet.
                   );

    else
      NdisMoveMemory(PayloadCopy,                     // An IP packet (on ethernet) comprises the ethernet header + the IP header/body.  An ARP or RARP packet
                     pPayload,                        // similarly comprises the ethernet header and the ARP or RARP body.  Since the mapped IP header is 20
                     sizeof(EthHdr)+sizeof(IPHdr)     // bytes and an ARP or RARP is 28 bytes, an amount = sizeof(EthHdr)+sizeof(IPHdr) is safely copied.
                    );

    pETH = (pEthHdr)PayloadCopy;                      // Point to ethernet header.

    if (EthHTypeIP!=RtlUshortByteSwap(pETH->Type))    // No IP header?
      break;                                          // Leave big 'do' group and do nothing more.

    pIPH = (pIPHdr)(PayloadCopy + sizeof(EthHdr));    // Point to IP header in copy of payload.

    if (TRUE==bSend)                                  // Send operation?
      IPAddr = pIPH->DestinationAddress;              // Use destination IP address.
    else
      IPAddr = pIPH->SourceAddress;                   // Use source IP address.

    for (i = 0; i < LoopLim; i ++)                    // Try several times to get current IP-address array, with ever-increasing amounts of working storage.
      {
       if (0==i)                                      // First try?
         {                                            // Use storage on the stack.
          ulUsed = szLclStorage;
          pAddrArr = (PPassthruIPAddrArray)&lclIPArray;
         }
       else
         {                                            // Use dynamically obtained storage.
          ulUsed *= 2;                                // Double size from first iteration or size previously indicated as needed.

          status =                                    // Get working storage.
            NdisAllocateMemoryWithTag((PVOID*)&pAddrArr, ulUsed, TAG);

          if (NDIS_STATUS_FAILURE==status)            // A problem?
            {
             DBGPRINT(("FilterPacket():  Failed to get memory for IP address array for adapter at 0x%08x!\n", pAdapt));
             status = NDIS_STATUS_RESOURCES;
             goto done;
            }

          bGotStorage = TRUE;                         // Remember got working storage.
         }

       status = PassthruWMIGetAddrArray(              // (Try to) get copy of IP-address array.
                                        pAdapt,
                                        &ulUsed,      // Variable with size of provided area.  Will be updated with size actually used or size needed.
                                        pAddrArr      // Area to receive IP-address array structure.
                                       );

       if (NDIS_STATUS_SUCCESS==status)               // Success?
         break;                                       // Leave 'for' group.

       if (i+1==LoopLim)                              // At loop limit?
         {
          DBGPRINT(("FilterPacket():  Failed to get array last time, status 0x%08x!\n", status));
          status = NDIS_STATUS_FAILURE;
          goto done;
         }

       if (TRUE==bGotStorage)                         // Got working storage?
         {
          NdisFreeMemory(pAddrArr, ulUsed, 0);
          bGotStorage = FALSE;
         }
      }                                               // End 'for' try to get current IP-address array.

//  PUCHAR pC = (PUCHAR)&IPAddr;
//  DBGPRINT(("FilterPacket():  IP address = %d.%d.%d.%d\n", *pC, *(pC+1), *(pC+2), *(pC+3)));
//  DumpMem((char*)PayloadCopy, ulOrigPayload>=64 ? 64: ulOrigPayload, FALSE, 1);

    for (                                             // Go through the IP addresses in a binary search.
         lowIdx = 0,
           highIdx = pAddrArr->NumberElements - 1;
         lowIdx <= highIdx;
         /* No iteration action. */
        )
      {
       midPt = (lowIdx + highIdx)/2;                  // Calculate mid-point.

       if (IPAddr==pAddrArr->IPAddrArray[midPt])      // A hit?
         {
          *pBDecision = TRUE;                         // Indicate packet to be dropped.
          break;
         }

       if (IPAddr<pAddrArr->IPAddrArray[midPt])       // Is the target less than the mid-point?
         highIdx = midPt - 1;                         // Yes, adjust "right boundary."
       else
         lowIdx = midPt + 1;                          // No, adjust "left boundary."
      }                                               // End 'for' binary search.
   } while(0);                                        // End big 'do' group.

done:
 if (TRUE==bGotStorage)                               // Got working storage?
   NdisFreeMemory(pAddrArr, ulUsed, 0);

 return status;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -