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

📄 dot11smeaplib.c

📁 PNE 3.3 wlan source code, running at more than vxworks6.x version
💻 C
📖 第 1 页 / 共 5 页
字号:
                }                        *(UINT32 *)data = ((UINT32)(!pBss->showSsidInBeacon)) |                ((UINT32)(!pBss->respondBcastSsid) << 1);            status = OK;            break;        /**************************************************************        * WIOCSDTIMRATE: Sets the current DTIM interval and updates the AP        **************************************************************/        case WIOCSDTIMRATE:            pDot11->sme->dtimPeriod = *(UINT32 *)data;            status = pDot11->sme->reset(pDot11);            break;        /**************************************************************        * EIOCSAUTHCALLBACK - (legacy) Sets the authentication callback        **************************************************************/        case EIOCSAUTHCALLBACK:            status = pDot11->sme->endIoctl((END_OBJ *)pDot11,                                                    WIOCSAUTHCALLBACK,                                                    data);            break;        /**************************************************************        * WIOCS80211D - Enable or disable 802.11d mode        **************************************************************/        case WIOCS80211D:            pDot11->sme->multiDomainEnabled = (BOOL)data;            status = pDot11->sme->reset(pDot11);            break;                    default:            status = EINVAL;            break;        }    return status;    }/***************************************************************************** dot11SmeApRawSend - Packet transmission wrapper function** This routine is a wrapper function used by the AP.  The AP SME initialization* replaces the HDD's rawPacketSend() with this routine, which performs various* AP-specific options and checks on an egress packet before passing it to the* HDD's rawPacketSend(), a pointer to which is stored in the AP_OBJ.** RETURNS: OK or the return from hdd->rawPacketSend().  Either way, the packet*          is consumed.** ERRNO: N/A*/LOCAL STATUS dot11SmeApRawSend    (    DOT11_FW * pDot11,            /* Pointer to dot11 root object */    M_BLK_ID pMBlk,               /* MBlk containing egress packet */    int rate,                     /* Rate at which to send */    int keyIndex                  /* Encryption key to use */    )    {    DOT11_AP_OBJ * pAp;           /* Ptr to AP specific data */    DOT11_HEADER * pHeader;       /* pointer to 802.11 header */    DOT11_KSL_ENTRY * pKsl;       /* KSL Entry for destination */    STATUS status;        pAp = &pDot11->sme->type.ap;    pHeader = (DOT11_HEADER *)pMBlk->mBlkHdr.mData;    /* If this is a data packet, check if this is a unicast or multicast     packet.  If unicast, it must be to an associated station.  If multicast,     let it transmit */    pKsl = pDot11->sme->ksl.lookup(pDot11, pHeader->addr1);        if ((DOT11_LE_TO_CPU_16(pHeader->frameCtrl) & DOT11_FCTL_TYPE_MASK)          == DOT11_FTYPE_DATA)        {        if (((pKsl == NULL) || (!pKsl->type.sta.associated)) && (!(DOT11_IS_MCAST(pHeader->addr1))))            {            DOT11_LOG(DOT11_DEBUG_INFO, DOT11_AREA_SME,                      ("dot11SmeApRawSend: KSL entry " DOT11_MAC_ADDR_STR                        " not found for dest.\n", DOT11_MAC_ADDR(pHeader->addr1)));            /* Drop the packet */            netMblkClChainFree(pMBlk);            return ERROR;            }        }        /* Quick exit to the HDD rawPacketSet() if there are no stations in     power management */    if ((!dot11SmeApPmActive(pDot11)) ||         (DOT11_FTYPE(DOT11_LE_TO_CPU_16(pHeader->frameCtrl)) ==          DOT11_TYPE_PROBE_RESP))        {        DOT11_LOG(DOT11_DEBUG_FLOOD, DOT11_AREA_SME,                  ("dot11SmeApRawSend: Normal send\n",                   0,1,2,3,4,5));        status = pAp->origRawPacketSend(pDot11, pMBlk, rate, keyIndex);        }    /* Split into two different cases for unicast and for multicast packets */    else if (DOT11_IS_MCAST(pHeader->addr1))        {        /* Multicast and broadcast packets should be added to the DTIM queue        to be sent out after the beacon.  This is a function of the HDD         performed by dtimPacketAdd() */        DOT11_LOG(DOT11_DEBUG_INFO, DOT11_AREA_SME,                  ("dot11SmeApRawSend: CAB enqueue\n",                   0,1,2,3,4,5));                /* Packet will be freed regardless of success */        status = pDot11->hdd->dtimPacketAdd(pDot11, pMBlk,                                             rate, keyIndex);        }    else /* Is a unicast packet */        {        /* Quick exit if this station does not have a KSL entry or isn't          under power management.  In all these cases, We assume the HDD knows         what it is doing. */        if ((pKsl == NULL) || (!pKsl->type.sta.powerManaged))            {            DOT11_LOG(DOT11_DEBUG_INFO, DOT11_AREA_SME,                      ("dot11SmeApRawSend: Normal send (PM)\n",                       0,1,2,3,4,5));            return pAp->origRawPacketSend(pDot11, pMBlk, rate, keyIndex);            }                /* Add the packet to the PS-POLL queue for this station */        DOT11_LOG(DOT11_DEBUG_INFO, DOT11_AREA_SME,                  ("dot11SmeApRawSend: PSPOLL enqueue\n",                   0,1,2,3,4,5));                if (pDot11->sme->ksl.lock(pDot11) == ERROR)            {            DOT11_LOG(DOT11_DEBUG_ERROR, DOT11_AREA_SME,                      ("dot11SmeApRawSend: Cannot get KSL lock\n",                       0,1,2,3,4,5));                        return pAp->origRawPacketSend(pDot11, pMBlk, rate, keyIndex);            }                /* Insert at tail of queue.  Check for the special case where there         are no packets on the queue. */        pMBlk->mBlkHdr.mNextPkt = NULL;        if (pKsl->type.sta.pmQueueHead == NULL)            {            pKsl->type.sta.pmQueueHead = pMBlk;            pKsl->type.sta.pmQueueTail = pMBlk;            }        else /* Insert at tail */            {            pKsl->type.sta.pmQueueTail->mBlkHdr.mNextPkt = pMBlk;            pKsl->type.sta.pmQueueTail = pMBlk;            }                /* Release the KSL lock now that we are done adding items */        if (pDot11->sme->ksl.unlock(pDot11) == ERROR)            {            DOT11_LOG(DOT11_DEBUG_ERROR, DOT11_AREA_SME,                      ("dot11SmeApRawSend: Cannot release KSL lock\n",                       0,1,2,3,4,5));                        return ERROR;            }        status = OK;        /* Modify the TIM bit in the beacon header.  The TIVB semaphore is        taken and released in the function*/        if(dot11SmeApTivbChange(pDot11, pKsl->type.sta.aid, TRUE,                                 pKsl->pBss) != OK)            {            DOT11_LOG(DOT11_DEBUG_ERROR, DOT11_AREA_SME,                      ("dot11SmeApRawSend: Error setting TIVB bit.  "                       "Flushing.\n",                       0,1,2,3,4,5));            /* Get rid of all entires in this KSL entry, so that they aren't             stuck there if the station decides to leave */            (void)dot11SmeApPmFlush(pDot11, pKsl, DOT11_PM_FLUSH);            }        }        return status;     }/***************************************************************************** dot11SmeApTivbChange - Sets/clears a bit in the TIVB** This routine sets or clears a bit in the Traffic Indication Virtual Bitmap * and adjusts the start and stop pointers appropriately** RETURNS: OK or ERROR** ERRNO: N/A*/LOCAL STATUS dot11SmeApTivbChange    (    DOT11_FW * pDot11,           /* Ptr to DOT11 framework root obj */    int aid,                     /* AID to modify */    BOOL set,                    /* True to set, False to clear */    DOT11_BSS * pBss             /* Bss in which to change */    )    {    int tivbByte;                /* Byte to set in the TIVB */    int tivbBit;                 /* Bit to set in the TIVB */    int i;                       /* Generic counter */    DOT11_AP_OBJ * pAp;          /* Ptr to AP data */    pAp = &pDot11->sme->type.ap;    tivbByte = aid >> 3;         /* There are eight bits to a byte */    tivbBit = aid & 0x7;    DOT11_LOG(DOT11_DEBUG_INFO, DOT11_AREA_SME,              ("dot11SmeApTivbChange: Started to %s AID %d.  Byte = %d, "               "bit = %d   (prevStart = %d, prevStop=%d)\n",                (int)(set?"SET":"CLEAR"),aid,tivbByte,tivbBit,pBss->tivbStart,               pBss->tivbStop));    if (semTake(pBss->tivbSem, DOT11_TIVB_SEM_TIMEOUT) != OK)        {        DOT11_LOG(DOT11_DEBUG_ERROR, DOT11_AREA_SME,                  ("dot11SmeApTivbChange: Unable to get TIVB semaphore!\n",                   0,0,0,0,0,0));        return ERROR;        }    if (set)        {        /* If we're setting a bit, we need to make sure that the bit is in the        area between the start and stop marks.  If not, expand the start and/or        stop marks to encompass the bit */        pBss->tivb[tivbByte] |= _BIT(tivbBit);        if (tivbByte > (pBss->tivbStop - 1))            {            pBss->tivbStop = tivbByte + 1;            }        if (pBss->tivbStart > tivbByte)            {            pBss->tivbStart = tivbByte;            }        DOT11_LOG(DOT11_DEBUG_INFO, DOT11_AREA_SME,                  ("dot11SmeApTivbChange: Bit %d set in byte %d  (start=%d "                   "stop = %d)\n",tivbBit, tivbByte, pBss->tivbStart,                    pBss->tivbStop,0,0));        }    else        {        /* When clearing a bit, the algorithm is more complicated.  There is        one special case and four specific cases as shown below: */                /* First clear the bit under question */        pBss->tivb[tivbByte] &= ~(_BIT(tivbBit));                    /*0.  If there are other bits set in our byte, no adjustment of start.         stop is necessary. */        if (pBss->tivb[tivbByte] == 0)            {            /* Too bad - there are no other bits in this byte, so we have to            adjust tivbStart/tivbStop in some way. */                        /* 1. Check if this was the only byte set in the bitmap.  If so,             then just clear start and stop to indicate no bits set */            if ((pBss->tivbStart == tivbByte) &&                 (pBss->tivbStop == (tivbByte + 1)))                {                pBss->tivbStart = 0;                pBss->tivbStop = 1;                }            /* 2.  If there are other bytes set on both sides of this byte,             no adjustment is necessary */            else if ((pBss->tivbStart < tivbByte) &&                      (pBss->tivbStop > (tivbByte + 1)))                {                /* Do nothing */                }            /* 3. If this is the lowest byte that is set, then we need to             search upwards for the next lowest byte and change tivbStart */            else if ((pBss->tivbStart == tivbByte) &&                      (pBss->tivbStop > (tivbByte + 1)))                {                for (i = tivbByte; i <= pBss->tivbStop; i++)                    {                    if (pBss->tivb[i] != 0)                        {                        pBss->tivbStart = i;                        break;                        }                    }                /* If we found nothing then there was an error in the table                and there are no other bits. */                if (i == pBss->tivbStop)                    {                    pBss->tivbStart = 0;                    pBss->tivbStop = 1;                    }                }            /* 4. If this is the highest byte that is set, then we search             downwards for the next highest byte and change ticbStop*/            else if ((pBss->tivbStart < tivbByte) &&                      (pBss->tivbStop == (tivbByte + 1)))                {                for (i = tivbByte; i >= (pBss->tivbStart - 1); i--)                    {                    if (pBss->tivb[i] != 0)                        {                        pBss->tivbStop = i + 1;                        break;                        }                    }                /* If we found nothing then there was an error in the table                and there are no other bits. */                if (i == pBss->tivbStart - 1)                    {                    pBss->tivbStart = 0;                    pBss->tivbStop = 1;                    }                }            else                {                /* Something is wrong - we shouldn't have gotten here.  Do a                 brute force recalculation */                pBss->tivbStart = -1;                pBss->tivbStop = 1;                                for (i=0; i<D

⌨️ 快捷键说明

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