Ejemplo n.º 1
0
bool Encapsulate80211Frame ( struct PACKETxID* ptid, 
                             DOT11RFC1042ENCAP& wheader, 
                             UCHAR * addr, int len ) 
{
    bool bRet = true;
    
//	DOT11RFC1042ENCAP wheader = { 0 };
    PETHERNET_HEADER  eheader;
    eheader = (PETHERNET_HEADER)addr;

    // Three address format with ap mode
    if ( OpMode == CLIENT_MODE ) {
        wheader.MacHeader.Address1 = bssid;
        wheader.MacHeader.Address2 = eheader->srcAddr;
        wheader.MacHeader.Address3 = eheader->destAddr;
        wheader.MacHeader.FrameControl.Type    = FRAME_DATA;
        wheader.MacHeader.FrameControl.Subtype = SUBT_DATA;
        wheader.MacHeader.FrameControl.ToDS  = 1;	// to DS
        wheader.MacHeader.FrameControl.Retry = 1;
    } else {
        wheader.MacHeader.Address1 = eheader->destAddr;
        wheader.MacHeader.Address2 = eheader->srcAddr;
        wheader.MacHeader.Address3 = adhoc_bssid;
        wheader.MacHeader.FrameControl.Type = FRAME_DATA;
        wheader.MacHeader.FrameControl.Subtype = SUBT_DATA;
        wheader.MacHeader.FrameControl.Retry = 1;
    }
    //		wheader.MacHeader.DurationID = 20 + (8*(len + 4)*1000 / gDataRateK); 
    
    // Kun: SequenceControl includes fragment seq
    //
    wheader.MacHeader.SequenceControl.usValue = (SendSeQ << 4);
    wheader.SNAP.DSAP = 0xAA;
    wheader.SNAP.SSAP = 0xAA;
    wheader.SNAP.Control = 0x03;
    wheader.Type = eheader->Type;
    
    SendSeQ++;
        
    ptid->m_status = PACKET_NOT_MOD;
    ptid->m_needack = !(ETH_IS_BROADCAST(eheader->destAddr.Address) || 
                        ETH_IS_MULTICAST(eheader->destAddr.Address));
    
    return bRet;
}
void CTXVirtQueue::UpdateTXStats(const CNB &NB, CTXDescriptor &Descriptor)
{
    auto &HeadersArea = Descriptor.HeadersAreaAccessor();
    PVOID EthHeader = HeadersArea.EthHeader();

    //TODO: Statistics must be atomic
    auto BytesSent = NB.GetDataLength();
    auto NBL = NB.GetParentNBL();

    m_Context->Statistics.ifHCOutOctets += BytesSent;

    if (ETH_IS_BROADCAST(EthHeader))
    {
        m_Context->Statistics.ifHCOutBroadcastOctets += BytesSent;
        m_Context->Statistics.ifHCOutBroadcastPkts++;
    }
    else if (ETH_IS_MULTICAST(EthHeader))
    {
        m_Context->Statistics.ifHCOutMulticastOctets += BytesSent;
        m_Context->Statistics.ifHCOutMulticastPkts++;
    }
    else
    {
        m_Context->Statistics.ifHCOutUcastOctets += BytesSent;
        m_Context->Statistics.ifHCOutUcastPkts++;
    }

    if (NBL->IsLSO())
    {
        m_Context->extraStatistics.framesLSO++;

        auto EthHeaders = Descriptor.HeadersAreaAccessor().EthHeadersAreaVA();
        auto TCPHdr = reinterpret_cast<TCPHeader *>(RtlOffsetToPointer(EthHeaders, NBL->TCPHeaderOffset()));

        NBL->UpdateLSOTxStats(NB.GetDataLength() - NBL->TCPHeaderOffset() - TCP_HEADER_LENGTH(TCPHdr));
    }
    else if (NBL->IsTcpCSO() || NBL->IsUdpCSO())
    {
        m_Context->extraStatistics.framesCSOffload++;
    }
}
Ejemplo n.º 3
0
ULONG
tapGetNetBufferFrameType(__in PNET_BUFFER NetBuffer)
/*++

Routine Description:

    Reads the network frame's destination address to determine the type
    (broadcast, multicast, etc)

    Runs at IRQL <= DISPATCH_LEVEL.

Arguments:

    NetBuffer                 The NB to examine

Return Value:

    NDIS_PACKET_TYPE_BROADCAST
    NDIS_PACKET_TYPE_MULTICAST
    NDIS_PACKET_TYPE_DIRECTED

--*/
{
  PETH_HEADER ethernetHeader;

  ethernetHeader = (PETH_HEADER)NdisGetDataBuffer(NetBuffer, sizeof(ETH_HEADER), NULL, 1, 0);

  ASSERT(ethernetHeader);

  if (ETH_IS_BROADCAST(ethernetHeader->dest)) {
    return NDIS_PACKET_TYPE_BROADCAST;
  } else if (ETH_IS_MULTICAST(ethernetHeader->dest)) {
    return NDIS_PACKET_TYPE_MULTICAST;
  } else {
    return NDIS_PACKET_TYPE_DIRECTED;
  }
}
Ejemplo n.º 4
0
bool ProcessDot11Frame(UCHAR *frameBuf, ULONG frameBufSize )
{
    
    PDOT11RFC1042ENCAP pWlanHeader = (PDOT11RFC1042ENCAP)frameBuf;
        
    if (pWlanHeader->MacHeader.FrameControl.Type    == FRAME_DATA && 
        pWlanHeader->MacHeader.FrameControl.Subtype == SUBT_DATA ) 
    {

        static USHORT CurRecvSeqNo = 0xffff;

        int fTargetFrame = 0;
        
        // Try to send some ACK
        if ( (memcmp( MACAddress.Address, 
                     pWlanHeader->MacHeader.Address1.Address, 
                     MAC_ADDRESS_LENGTH) == 0) )
        {
            DataFrameAck11(pWlanHeader, frameBufSize);
            UpdateLastRate();
            PlotText ( "mac event", "receive a packet - seq (%d) size (%d) rate (%u).................................",
                pWlanHeader->MacHeader.SequenceControl.SequenceNumber,
                frameBufSize,
                lastRate
            );

            fTargetFrame = 1;
        }
        
        if ( fTargetFrame ||
             ETH_IS_BROADCAST (pWlanHeader->MacHeader.Address1.Address) )
        {
            UpdateLastRate();
            nDataPacketRcvCnt ++;
            
            if (CurRecvSeqNo  != pWlanHeader->MacHeader.SequenceControl.SequenceNumber 
                && pWlanHeader->MacHeader.SequenceControl.FragmentNumber == 0 ) {			
                if ( frameBufSize < sizeof(DOT11RFC1042ENCAP)) {
                    return S_OK;
                }
                
                CurRecvSeqNo   = pWlanHeader->MacHeader.SequenceControl.SequenceNumber;
                MAC_ADDRESS			destAddr;
                MAC_ADDRESS			srcAddr;
                UINT16				Type;
                ULONG				Offset;
                PETHERNET_HEADER	pEthernetHeader;

                /* ad hoc mode
                destAddr = pWlanHeader->MacHeader.Address1;
                srcAddr  = pWlanHeader->MacHeader.Address2;


                lastMACDst   = pWlanHeader->MacHeader.Address1;
                lastMACSrc   = pWlanHeader->MacHeader.Address2;
                lastMACBssid = pWlanHeader->MacHeader.Address3;
                */

                /* AP mode */
                if ( OpMode == CLIENT_MODE ) {
                    destAddr = pWlanHeader->MacHeader.Address1;
                    srcAddr  = pWlanHeader->MacHeader.Address3;
                    Type     = pWlanHeader->Type;

                    lastMACDst   = pWlanHeader->MacHeader.Address1;
                    lastMACSrc   = pWlanHeader->MacHeader.Address3;
                    lastMACBssid = pWlanHeader->MacHeader.Address2;
                } else {
                    destAddr = pWlanHeader->MacHeader.Address1;
                    srcAddr  = pWlanHeader->MacHeader.Address2;
                    Type     = pWlanHeader->Type;					
                    
                    lastMACDst	 = pWlanHeader->MacHeader.Address1;
                    lastMACSrc	 = pWlanHeader->MacHeader.Address2;
                    lastMACBssid = pWlanHeader->MacHeader.Address3;
                }

                Offset   = sizeof(DOT11RFC1042ENCAP) - sizeof(ETHERNET_HEADER);
                pEthernetHeader = (PETHERNET_HEADER)(frameBuf + Offset);
                pEthernetHeader->destAddr = destAddr;
                pEthernetHeader->srcAddr = srcAddr;
                pEthernetHeader->Type = Type;

                PlotText ( "mac event", "Indicate packet seq (%d)", 
                    CurRecvSeqNo );

                HRESULT hr;
                hr = SoraUIndicateRxPacket(frameBuf + Offset, frameBufSize - Offset - 4 ); // remove FCS

                UpdateEnergy ();
                return SUCCEEDED(hr);
            }
        }
        else {
            nInterferenceCnt ++;
        }
    }
    else
    if (pWlanHeader->MacHeader.FrameControl.Type == FRAME_CTRL &&
        pWlanHeader->MacHeader.FrameControl.Subtype == SUBT_ACK) {
        
        if (LastPACKETxID) {
            if (memcmp(MACAddress.Address, 
                pWlanHeader->MacHeader.Address1.Address,
                MAC_ADDRESS_LENGTH))
                return true;

            struct PACKETxID* ptid;
            ptid = LastPACKETxID;
            LastPACKETxID = NULL;

            nAckRcvCnt ++;
            
            if ( ptid->m_packet ) {
                SoraUCompleteTxPacket(ptid->m_packet, 
                    STATUS_SUCCESS);
            }
            
            debug_printf("Complete Send Packet: [%08x], TxID: [%d], TX succeed\n", 
                ptid->m_packet, 
                ptid->m_tid.m_txid[0]);
            
            switch(ptid->m_status) {
            case PACKET_CAN_TX:
                FreeTxResource(&ptid->m_tid);
                break;
            default:
                break;
            }
            free(ptid);
        }
    }
    else
    if (pWlanHeader->MacHeader.FrameControl.Type    == FRAME_MAN &&
        pWlanHeader->MacHeader.FrameControl.Subtype == SUBT_BEACON)
    {
        ProcessBeacon ((PDOT11_MAC_BEACON)pWlanHeader);
    }
    else 
    if (pWlanHeader->MacHeader.FrameControl.Type    == FRAME_MAN )
    {
        if ( memcmp( MACAddress.Address, pWlanHeader->MacHeader.Address1.Address, MAC_ADDRESS_LENGTH) == 0 )
        {
            if ( pWlanHeader->MacHeader.FrameControl.Subtype == SUBT_AUTH ) // auth
            {
                DataFrameAck11 ( pWlanHeader, frameBufSize );

                if ( assoState == ASSO_NONE ) {
                    assoState = ASSO_AUTH;
                }
            } else if ( pWlanHeader->MacHeader.FrameControl.Subtype == SUBT_ASSO ) // asso
            {
                DataFrameAck11 ( pWlanHeader, frameBufSize );

                if ( assoState == ASSO_AUTH || 
                     assoState == ASSO_NONE 
                ) {
                    assoState = ASSO_DONE;
                }
            } else if ( pWlanHeader->MacHeader.FrameControl.Subtype == SUBT_DEASSO || // deassociate
                        pWlanHeader->MacHeader.FrameControl.Subtype == SUBT_DEAUTH )  // deauth
            {
                assoState = ASSO_NONE;  
            }
        }	
    }

    return true;
}
Ejemplo n.º 5
0
BOOLEAN
NICIsPacketAcceptable(
    IN PMP_ADAPTER Adapter,
    IN PUCHAR   pDstMac
    )
/*++

Routine Description:

    Check if the destination address of a received packet
    matches the receive criteria of our adapter.
    
Arguments:

    Adapter    - pointer to the adapter structure
    pDstMac - Destination MAC address to compare


Return Value:

    True or False

--*/
{
    UINT            AddrCompareResult;
    ULONG           PacketFilter;
    BOOLEAN         bPacketMatch;
    BOOLEAN         bIsMulticast, bIsBroadcast;

    PacketFilter = Adapter->PacketFilter;

    bIsMulticast = ETH_IS_MULTICAST(pDstMac);
    bIsBroadcast = ETH_IS_BROADCAST(pDstMac);

    //
    // Handle the directed packet case first.
    //
    if (!bIsMulticast)
    {
        //
        // If the Adapter is not in promisc. mode, check if
        // the destination MAC address matches the local
        // address.
        //
        if ((PacketFilter & NDIS_PACKET_TYPE_PROMISCUOUS) == 0)
        {
            ETH_COMPARE_NETWORK_ADDRESSES_EQ(Adapter->CurrentAddress,
                                             pDstMac,
                                             &AddrCompareResult);

            bPacketMatch = ((AddrCompareResult == 0) &&
                           ((PacketFilter & NDIS_PACKET_TYPE_DIRECTED) != 0));
        }
        else
        {
            bPacketMatch = TRUE;
        }
     }
     else
     {
        //
        // Multicast or broadcast packet.
        //

        //
        // Indicate if the filter is set to promisc mode ...
        //
        if ((PacketFilter & NDIS_PACKET_TYPE_PROMISCUOUS)
                ||

            //
            // or if this is a broadcast packet and the filter
            // is set to receive all broadcast packets...
            //
            (bIsBroadcast &&
             (PacketFilter & NDIS_PACKET_TYPE_BROADCAST))
                ||

            //
            // or if this is a multicast packet, and the filter is
            // either set to receive all multicast packets, or
            // set to receive specific multicast packets. In the
            // latter case, indicate receive only if the destn
            // MAC address is present in the list of multicast
            // addresses set on the Adapter.
            //
            (!bIsBroadcast &&
             ((PacketFilter & NDIS_PACKET_TYPE_ALL_MULTICAST) ||
              ((PacketFilter & NDIS_PACKET_TYPE_MULTICAST) &&
               NICIsMulticastMatch(Adapter, pDstMac))))
           )
        {
            bPacketMatch = TRUE;
        }
        else
        {
            //
            // No protocols above are interested in this
            // multicast/broadcast packet.
            //
            bPacketMatch = FALSE;
        }
    }

    return (bPacketMatch);
}
Ejemplo n.º 6
0
/*
SdrLLSendPacket transforms NDIS packet and enqueue it in MAC send queue.

History:
    3/Nov/2009: Created by senxiang
*/
VOID SdrLLSendPacket(PSDR_CONTEXT SDRContext, PNDIS_PACKET_OR_NBL pNBSPacket)
{
    PMDL                pEthBuffer          = NULL;
    PMDL                pWlanBuffer         = NULL;
    PDLCB               pDLCB               = NULL;
    ULONG               Dot11HeaderSize     = 0;
    PUCHAR              pDot11HeaderVa      = NULL;
    PMAC                pMac                = (PMAC)SDRContext->Mac;
    PLL                 lnk                 = (PLL)SDRContext->LinkLayer;
    PSEND_QUEUE_MANAGER pSendQueueManager   = GET_SEND_QUEUE_MANAGER(pMac);
    PNET_BUFFER         pCurrentNB          = NET_BUFFER_LIST_FIRST_NB(pNBSPacket);

    ULONG               NetBufferCount      = GetNetBufferCount(pNBSPacket);
    LIST_ENTRY          DLCBList;

    BOOL                fSufficientDLCBs    = GetNFreeDLCB(&DLCBList, pSendQueueManager, NetBufferCount);
    DbgPrint("[LL_Send] %d net buffer in the NBL\n", NetBufferCount);

    if(pCurrentNB == NULL || !fSufficientDLCBs)
    {
        DbgPrint("[Error] Get NetBuffer failed, PACKET DROPPED\n");
        NicDropPacket((PMP_ADAPTER)SDRContext->Nic, pNBSPacket);
        return;
    }

    NET_BUFFER_LIST_STATUS(pNBSPacket) = NDIS_STATUS_SUCCESS; //init its status to success

    while(pCurrentNB)
    {
        //Get MDL
        ASSERT(!IsListEmpty(&DLCBList));
        pDLCB = CONTAINING_RECORD(RemoveHeadList(&DLCBList), DLCB, List);
        pDLCB->pNdisPktOrNBL = (PVOID)pNBSPacket;
        pDLCB->bLastNB = !(NET_BUFFER_NEXT_NB(pCurrentNB));

        lnk->CurSendSeqNo.SequenceNumber++;

        pEthBuffer = NET_BUFFER_CURRENT_MDL(pCurrentNB);
        if(pEthBuffer == NULL)
        {
            pDLCB->PacketBase.pMdl = NULL;
            DbgPrint("[Error] Get MDL failed, PACKET DROPPED\n");
        }
        else
        {
            EthToWlan(pEthBuffer,
                      &pWlanBuffer,
                      &Dot11HeaderSize,
                      &pDot11HeaderVa,
                      lnk->CurSendSeqNo.usValue,
                      NET_BUFFER_CURRENT_MDL_OFFSET(pCurrentNB));
            pDLCB->PacketType = PACKET_NEED_ACK;
            if(pDot11HeaderVa &&
                    (ETH_IS_BROADCAST(&((PDOT11RFC1042ENCAP)pDot11HeaderVa)->MacHeader.Address1)
                     || ETH_IS_MULTICAST(&((PDOT11RFC1042ENCAP)pDot11HeaderVa)->MacHeader.Address1)))
            {
                pDLCB->PacketType = PACKET_NOT_NEED_ACK;
            }

            //Config DLCB
            pDLCB->Dot11HeaderSize          = Dot11HeaderSize;
            pDLCB->pDot11HeaderVa           = pDot11HeaderVa;
            pDLCB->PacketBase.pMdl          = pWlanBuffer;

            pDLCB->PacketBase.PacketSize    = NET_BUFFER_DATA_LENGTH(pCurrentNB) + sizeof(DOT11RFC1042ENCAP) - sizeof(ETHERNET_HEADER);

            {   // we update the copied mdl length to packet length for baseband
                ULONG len = pDLCB->PacketBase.PacketSize;
                PMDL mdl = pDLCB->PacketBase.pMdl;
                while(mdl) {
                    if (mdl->ByteCount > len) {
                        mdl->ByteCount = len;
                        break;
                    }
                    else if (mdl->ByteCount < len) {
                        len-= mdl->ByteCount;
                        mdl = mdl->Next;
                        continue;
                    }
                    else
                        break;
                }
            }

            pDLCB->PacketBase.Reserved1     = CalcMDLChainCRC32(pWlanBuffer);
            pDLCB->RetryCount               = 0;
            pDLCB->bSendOK                  = FALSE;
        }

        SafeEnqueue(pSendQueueManager, SendSrcWaitList, pDLCB);
        InterlockedIncrement(&pSendQueueManager->nSrcPacket);

        //Notify send thread
        NIC_NOTIFY_SEND_THREAD(pMac);

        //Get next NetBuffer
        pCurrentNB = NET_BUFFER_NEXT_NB(pCurrentNB);
    }

}
Ejemplo n.º 7
0
VOID
Hw11ReadRegistryConfiguration(
    __in  PHW                     Hw,
    __in  NDIS_HANDLE             ConfigurationHandle
    )
{
    NDIS_STATUS                 ndisStatus = NDIS_STATUS_SUCCESS;
    PUCHAR                      NetworkAddress;
    UINT                        Length;

    // TODO: These should be read from the registry
    Hw->RegInfo.RTSThreshold = 2347;
    Hw->RegInfo.FragmentationThreshold = 2346;
    Hw->RegInfo.BeaconPeriod = 100;

    Hw->RegInfo.NumRXBuffersUpperLimit = HW11_MAX_RX_MSDUS;
    Hw->RegInfo.NumRXBuffersLowerBase = HW11_MIN_RX_MSDUS;
    
    //
    // read all the non-hardware specific registry values 
    //
    MpReadRegistry((PVOID)Hw, ConfigurationHandle, HWRegTable, HW_NUM_REG_PARAMS);

    //
    // Read NetworkAddress registry value. Use it as the current address if any.
    //
    if (ConfigurationHandle != NULL) 
    {
        NdisReadNetworkAddress(&ndisStatus,
                               (void **)&NetworkAddress,
                               &Length,
                               ConfigurationHandle);

        //
        // If there is a valid NetworkAddress override in registry,use it 
        //
        if ((ndisStatus == NDIS_STATUS_SUCCESS) && (Length == sizeof(DOT11_MAC_ADDRESS))) 
        {
            // Dont use multicast/broadcast or 00* addresses
            if (!ETH_IS_MULTICAST(NetworkAddress) && !ETH_IS_BROADCAST(NetworkAddress)) 
            {
                if ((NetworkAddress[0] == 0x00) &&
                    (NetworkAddress[1] == 0x00) &&
                    (NetworkAddress[2] == 0x00) &&
                    (NetworkAddress[3] == 0x00) &&
                    (NetworkAddress[4] == 0x00) &&
                    (NetworkAddress[5] == 0x00)) 
                {   
                    // Network addr = 00 00 00 00 00 00
                    Hw->RegInfo.AddressOverrideEnabled = FALSE;
                }
                else if ((NetworkAddress[0] & 0x02) != 0x02)
                {
                    // Not a locally administered address
                    Hw->RegInfo.AddressOverrideEnabled = FALSE;
                }
                else
                {
                    ETH_COPY_NETWORK_ADDRESS(Hw->RegInfo.OverrideAddress,NetworkAddress);
                    Hw->RegInfo.AddressOverrideEnabled = TRUE;
                }
            }
        }

        ndisStatus = NDIS_STATUS_SUCCESS;

    }

}