static BOOLEAN StaAllowToSendPacket(RTMP_ADAPTER *pAd, struct wifi_dev *wdev, PNDIS_PACKET pPacket, UCHAR *pWcid) { BOOLEAN allowToSend; if (!INFRA_ON(pAd) && !ADHOC_ON(pAd)) { return FALSE; } else { if (ADHOC_ON(pAd)) { RTMP_SET_PACKET_WCID(pPacket, MCAST_WCID); } if (INFRA_ON(pAd) && (0)) { MAC_TABLE_ENTRY *pEntry; PUCHAR pSrcBufVA = GET_OS_PKT_DATAPTR(pPacket); pEntry = MacTableLookup(pAd, pSrcBufVA); if (pEntry && (IS_ENTRY_DLS(pEntry))) { *pWcid = pEntry->wcid; } else { *pWcid = 0; } } else { *pWcid = 0; } allowToSend = TRUE; } return allowToSend; }
static INT CFG80211_VirtualIF_Close(struct net_device *dev_p) { struct rtmp_adapter *pAd; pAd = RTMP_OS_NETDEV_GET_PRIV(dev_p); ASSERT(pAd); DBGPRINT(RT_DEBUG_TRACE, ("%s: ===> %s\n", __FUNCTION__, RTMP_OS_NETDEV_GET_DEVNAME(dev_p))); RTMP_OS_NETDEV_STOP_QUEUE(dev_p); if (netif_carrier_ok(dev_p)) netif_carrier_off(dev_p); #ifdef CONFIG_STA_SUPPORT if (INFRA_ON(pAd)) AsicEnableBssSync(pAd); else if (ADHOC_ON(pAd)) AsicEnableIbssSync(pAd); #else else AsicDisableSync(pAd); #endif //VIRTUAL_IF_DOWN(pAd); RT_MOD_DEC_USE_COUNT(); return 0; }
static VOID MeshCtrlMcsTimeoutAction( IN PRTMP_ADAPTER pAd, IN MLME_QUEUE_ELEM *Elem) { MESH_CTRL_STATE *pCurrState = &(pAd->MeshTab.CtrlCurrentState); DBGPRINT(RT_DEBUG_TRACE, ("%s: Get Mcs evt when UCG.\n", __FUNCTION__)); if (!INFRA_ON(pAd) && !ADHOC_ON(pAd)) { /*SET_MESH_CHANNEL(pAd); */ pAd->CommonCfg.Channel = pAd->MeshTab.MeshChannel; #ifdef DOT11_N_SUPPORT N_ChannelCheck(pAd); #endif /* DOT11_N_SUPPORT */ AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel); pAd->MeshTab.CPI = pAd->MeshTab.NewCPI; } else pAd->MeshTab.MeshChannel = pAd->CommonCfg.Channel; RTMPSetTimer(&pAd->MeshTab.PldTimer, PLD_TIME); *pCurrState = MESH_CTRL_ACTIVATED; }
VOID WscSendEapFragAck( IN PRTMP_ADAPTER pAdapter, IN PWSC_CTRL pWscControl, IN PMAC_TABLE_ENTRY pEntry) { if (pEntry == NULL) { ASSERT(pEntry!=NULL); return; } if (IS_ENTRY_CLIENT(pEntry)) { pWscControl->bWscLastOne = TRUE; if (pAdapter->OpMode == OPMODE_AP) WscSendMessage(pAdapter, WSC_OPCODE_FRAG_ACK, NULL, 0, pWscControl, AP_MODE, EAP_CODE_REQ); else { if (ADHOC_ON(pAdapter) && (pWscControl->WscConfMode == WSC_REGISTRAR)) WscSendMessage(pAdapter, WSC_OPCODE_FRAG_ACK, NULL, 0, pWscControl, STA_MODE, EAP_CODE_REQ); else WscSendMessage(pAdapter, WSC_OPCODE_FRAG_ACK, NULL, 0, pWscControl, STA_MODE, EAP_CODE_RSP); } } else if (IS_ENTRY_APCLI(pEntry)) WscSendMessage(pAdapter, WSC_OPCODE_FRAG_ACK, NULL, 0, pWscControl, AP_CLIENT_MODE, EAP_CODE_REQ); }
static INT CFG80211_VirtualIF_Close(PNET_DEV dev_p) { VOID *pAdSrc; pAdSrc = RTMP_OS_NETDEV_GET_PRIV(dev_p); ASSERT(pAdSrc); PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)pAdSrc; #ifdef RT_CFG80211_P2P_SUPPORT if (dev_p->ieee80211_ptr->iftype == RT_CMD_80211_IFTYPE_P2P_CLIENT) { DBGPRINT(RT_DEBUG_TRACE, ("CFG80211_VirtualIF_Close\n")); CFG80211OS_ScanEnd(pAd->pCfg80211_CB, TRUE); RT_MOD_DEC_USE_COUNT(); return ApCli_Close(pAd, dev_p); } #endif /* RT_CFG80211_P2P_SUPPORT */ #ifdef CONFIG_SNIFFER_SUPPORT #ifdef CONFIG_AP_SUPPORT if(dev_p->ieee80211_ptr->iftype == RT_CMD_80211_IFTYPE_MONITOR) { pAd->ApCfg.BssType = BSS_INFRA; AsicSetRxFilter(pAd); } #endif /*CONFIG_AP_SUPPORT*/ #endif /*CONFIG_SNIFFER_SUPPORT*/ DBGPRINT(RT_DEBUG_TRACE, ("%s: ===> %s\n", __FUNCTION__, RTMP_OS_NETDEV_GET_DEVNAME(dev_p))); RTMP_OS_NETDEV_STOP_QUEUE(dev_p); if (netif_carrier_ok(dev_p)) netif_carrier_off(dev_p); #ifdef CONFIG_STA_SUPPORT if (INFRA_ON(pAd)) AsicEnableBssSync(pAd); else if (ADHOC_ON(pAd)) AsicEnableIbssSync(pAd); #else else AsicDisableSync(pAd); #endif //VIRTUAL_IF_DOWN(pAd); RT_MOD_DEC_USE_COUNT(); return 0; }
static INT CFG80211_VirtualIF_Close(PNET_DEV dev_p) { VOID *pAdSrc; pAdSrc = RTMP_OS_NETDEV_GET_PRIV(dev_p); ASSERT(pAdSrc); PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)pAdSrc; if ((dev_p->ieee80211_ptr->iftype == RT_CMD_80211_IFTYPE_P2P_CLIENT) #ifdef CFG80211_MULTI_STA || (dev_p->ieee80211_ptr->iftype == RT_CMD_80211_IFTYPE_STATION) #endif /* CFG80211_MULTI_STA */ ) { DBGPRINT(RT_DEBUG_TRACE, ("CFG80211_VirtualIF_Close\n")); CFG80211OS_ScanEnd(pAd->pCfg80211_CB, TRUE); if (pAd->cfg80211_ctrl.FlgCfg80211Scanning) pAd->cfg80211_ctrl.FlgCfg80211Scanning = FALSE; RT_MOD_DEC_USE_COUNT(); return ApCli_Close(pAd, dev_p); } DBGPRINT(RT_DEBUG_TRACE, ("%s: ===> %s\n", __FUNCTION__, RTMP_OS_NETDEV_GET_DEVNAME(dev_p))); RTMP_OS_NETDEV_STOP_QUEUE(dev_p); if (netif_carrier_ok(dev_p)) netif_carrier_off(dev_p); if (INFRA_ON(pAd)) AsicEnableBssSync(pAd, pAd->CommonCfg.BeaconPeriod); else if (ADHOC_ON(pAd)) AsicEnableIbssSync(pAd); else AsicDisableSync(pAd); //VIRTUAL_IF_DOWN(pAd); RT_MOD_DEC_USE_COUNT(); return 0; }
/* ======================================================================== Routine Description: Caller ensures we has 802.11n support. Calls at setting HT from AP/STASetinformation Arguments: pAd - Pointer to our adapter phymode - ======================================================================== */ VOID RTMPSetHT( IN RTMP_ADAPTER *pAd, IN OID_SET_HT_PHYMODE *pHTPhyMode) { UCHAR RxStream = pAd->CommonCfg.RxStream; #ifdef CONFIG_AP_SUPPORT INT apidx; #endif /* CONFIG_AP_SUPPORT */ #ifdef CONFIG_MULTI_CHANNEL #if defined(RT_CFG80211_SUPPORT) && defined(CONFIG_AP_SUPPORT) BSS_STRUCT *pMbss = &pAd->ApCfg.MBSSID[CFG_GO_BSSID_IDX]; struct wifi_dev *wdev = &pMbss->wdev; #endif /* defined(RT_CFG80211_SUPPORT) && defined(CONFIG_AP_SUPPORT) */ #endif /* CONFIG_MULTI_CHANNEL */ INT bw; RT_HT_CAPABILITY *rt_ht_cap = &pAd->CommonCfg.DesiredHtPhy; HT_CAPABILITY_IE *ht_cap= &pAd->CommonCfg.HtCapability; #ifdef CONFIG_AP_SUPPORT /* sanity check for extention channel */ if (CHAN_PropertyCheck(pAd, pAd->CommonCfg.Channel, CHANNEL_NO_FAT_BELOW | CHANNEL_NO_FAT_ABOVE) == TRUE) { /* only 20MHz is allowed */ pHTPhyMode->BW = 0; } else if (pHTPhyMode->ExtOffset == EXTCHA_BELOW) { /* extension channel below this channel is not allowed */ if (CHAN_PropertyCheck(pAd, pAd->CommonCfg.Channel, CHANNEL_NO_FAT_BELOW) == TRUE) { pHTPhyMode->ExtOffset = EXTCHA_ABOVE; } } else if (pHTPhyMode->ExtOffset == EXTCHA_ABOVE) { /* extension channel above this channel is not allowed */ if (CHAN_PropertyCheck(pAd, pAd->CommonCfg.Channel, CHANNEL_NO_FAT_ABOVE) == TRUE) { pHTPhyMode->ExtOffset = EXTCHA_BELOW; } } #endif /* CONFIG_AP_SUPPORT */ MTWF_LOG(DBG_CAT_ALL, DBG_SUBCAT_ALL, DBG_LVL_TRACE, ("RTMPSetHT : HT_mode(%d), ExtOffset(%d), MCS(%d), BW(%d), STBC(%d), SHORTGI(%d)\n", pHTPhyMode->HtMode, pHTPhyMode->ExtOffset, pHTPhyMode->MCS, pHTPhyMode->BW, pHTPhyMode->STBC, pHTPhyMode->SHORTGI)); /* Don't zero supportedHyPhy structure.*/ RTMPZeroMemory(ht_cap, sizeof(HT_CAPABILITY_IE)); RTMPZeroMemory(&pAd->CommonCfg.AddHTInfo, sizeof(pAd->CommonCfg.AddHTInfo)); RTMPZeroMemory(&pAd->CommonCfg.NewExtChanOffset, sizeof(pAd->CommonCfg.NewExtChanOffset)); RTMPZeroMemory(rt_ht_cap, sizeof(RT_HT_CAPABILITY)); if (pAd->CommonCfg.bRdg) { ht_cap->ExtHtCapInfo.PlusHTC = 1; ht_cap->ExtHtCapInfo.RDGSupport = 1; } else { ht_cap->ExtHtCapInfo.PlusHTC = 0; ht_cap->ExtHtCapInfo.RDGSupport = 0; } ht_cap->HtCapParm.MaxRAmpduFactor = pAd->chipCap.AMPDUFactor; rt_ht_cap->MaxRAmpduFactor = pAd->chipCap.AMPDUFactor; MTWF_LOG(DBG_CAT_ALL, DBG_SUBCAT_ALL, DBG_LVL_TRACE, ("RTMPSetHT : RxBAWinLimit = %d\n", pAd->CommonCfg.BACapability.field.RxBAWinLimit)); /* Mimo power save, A-MSDU size, */ rt_ht_cap->AmsduEnable = (USHORT)pAd->CommonCfg.BACapability.field.AmsduEnable; rt_ht_cap->AmsduSize = (UCHAR)pAd->CommonCfg.BACapability.field.AmsduSize; rt_ht_cap->MimoPs = (UCHAR)pAd->CommonCfg.BACapability.field.MMPSmode; rt_ht_cap->MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity; ht_cap->HtCapInfo.AMsduSize = (USHORT)pAd->CommonCfg.BACapability.field.AmsduSize; ht_cap->HtCapInfo.MimoPs = (USHORT)pAd->CommonCfg.BACapability.field.MMPSmode; if (pAd->CommonCfg.ht_ldpc && (pAd->chipCap.phy_caps & fPHY_CAP_LDPC)) ht_cap->HtCapInfo.ht_rx_ldpc = 1; else ht_cap->HtCapInfo.ht_rx_ldpc = 0; ht_cap->HtCapParm.MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity; MTWF_LOG(DBG_CAT_ALL, DBG_SUBCAT_ALL, DBG_LVL_TRACE, ("RTMPSetHT : AMsduSize = %d, MimoPs = %d, MpduDensity = %d, MaxRAmpduFactor = %d\n", rt_ht_cap->AmsduSize, rt_ht_cap->MimoPs, rt_ht_cap->MpduDensity, rt_ht_cap->MaxRAmpduFactor)); if(pHTPhyMode->HtMode == HTMODE_GF) { ht_cap->HtCapInfo.GF = 1; rt_ht_cap->GF = 1; } else rt_ht_cap->GF = 0; /* Decide Rx MCSSet*/ switch (RxStream) { case 3: ht_cap->MCSSet[2] = 0xff; case 2: ht_cap->MCSSet[1] = 0xff; case 1: default: ht_cap->MCSSet[0] = 0xff; break; } if (pAd->CommonCfg.bForty_Mhz_Intolerant && (pHTPhyMode->BW == BW_40)) { pHTPhyMode->BW = BW_20; ht_cap->HtCapInfo.Forty_Mhz_Intolerant = 1; } // TODO: shiang-6590, how about the "bw" when channel 14 for JP region??? //CFG_TODO bw = BW_20; if(pHTPhyMode->BW == BW_40) { ht_cap->MCSSet[4] = 0x1; /* MCS 32*/ ht_cap->HtCapInfo.ChannelWidth = 1; if (pAd->CommonCfg.Channel <= 14) ht_cap->HtCapInfo.CCKmodein40 = 1; rt_ht_cap->ChannelWidth = 1; pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth = 1; pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset = (pHTPhyMode->ExtOffset == EXTCHA_BELOW)? (EXTCHA_BELOW): EXTCHA_ABOVE; /* Set Regsiter for extension channel position.*/ AsicSetCtrlCh(pAd, pHTPhyMode->ExtOffset); /* Turn on BBP 40MHz mode now only as AP . */ /* Sta can turn on BBP 40MHz after connection with 40MHz AP. Sta only broadcast 40MHz capability before connection.*/ if ((pAd->OpMode == OPMODE_AP) || INFRA_ON(pAd) || ADHOC_ON(pAd) ) { bbp_set_ctrlch(pAd, pHTPhyMode->ExtOffset); #ifdef GREENAP_SUPPORT if (pAd->ApCfg.bGreenAPActive == 1) bw = BW_20; else #endif /* GREENAP_SUPPORT */ bw = BW_40; } } else { ht_cap->HtCapInfo.ChannelWidth = 0; rt_ht_cap->ChannelWidth = 0; pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth = 0; pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset = EXTCHA_NONE; pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel; /* Turn on BBP 20MHz mode by request here.*/ bw = BW_20; } #ifdef DOT11_VHT_AC if (pHTPhyMode->BW == BW_40 && pAd->CommonCfg.vht_bw == VHT_BW_80 && pAd->CommonCfg.vht_cent_ch) bw = BW_80; #endif /* DOT11_VHT_AC */ #ifdef CONFIG_MULTI_CHANNEL #if defined(RT_CFG80211_SUPPORT) && defined(CONFIG_AP_SUPPORT) if ((wdev->bw == BW_20) && (wdev->channel != 0)) bbp_set_bw(pAd, wdev->bw); else if (INFRA_ON(pAd)) bbp_set_bw(pAd, pAd->StaCfg.wdev.bw); else #endif /* defined(RT_CFG80211_SUPPORT) && defined(CONFIG_AP_SUPPORT) */ #endif /* CONFIG_MULTI_CHANNEL */ bbp_set_bw(pAd, bw); if(pHTPhyMode->STBC == STBC_USE) { if (pAd->Antenna.field.TxPath >= 2) { ht_cap->HtCapInfo.TxSTBC = 1; rt_ht_cap->TxSTBC = 1; } else { ht_cap->HtCapInfo.TxSTBC = 0; rt_ht_cap->TxSTBC = 0; } /* RxSTBC 0: not support, 1: support for 1SS 2: support for 1SS, 2SS 3: support for 1SS, 2SS, 3SS */ if (pAd->Antenna.field.RxPath >= 1) { ht_cap->HtCapInfo.RxSTBC = 1; rt_ht_cap->RxSTBC = 1; } else { ht_cap->HtCapInfo.RxSTBC = 0; rt_ht_cap->RxSTBC = 0; } } else { rt_ht_cap->TxSTBC = 0; rt_ht_cap->RxSTBC = 0; } if(pHTPhyMode->SHORTGI == GI_400) { ht_cap->HtCapInfo.ShortGIfor20 = 1; //ht_cap->HtCapInfo.ShortGIfor40 = 1; rt_ht_cap->ShortGIfor20 = 1; if(pHTPhyMode->BW == BW_40) { ht_cap->HtCapInfo.ShortGIfor40 = 1; rt_ht_cap->ShortGIfor40 = 1; } else { ht_cap->HtCapInfo.ShortGIfor40 = 0; rt_ht_cap->ShortGIfor40 = 0; } } else { ht_cap->HtCapInfo.ShortGIfor20 = 0; ht_cap->HtCapInfo.ShortGIfor40 = 0; rt_ht_cap->ShortGIfor20 = 0; rt_ht_cap->ShortGIfor40 = 0; } /* We support link adaptation for unsolicit MCS feedback, set to 2.*/ pAd->CommonCfg.AddHTInfo.ControlChan = pAd->CommonCfg.Channel; /* 1, the extension channel above the control channel. */ /* EDCA parameters used for AP's own transmission*/ if (pAd->CommonCfg.APEdcaParm.bValid == FALSE) set_default_ap_edca_param(pAd); AsicSetEdcaParm(pAd, &pAd->CommonCfg.APEdcaParm); #ifdef CONFIG_AP_SUPPORT IF_DEV_CONFIG_OPMODE_ON_AP(pAd) { for (apidx = 0; apidx < pAd->ApCfg.BssidNum; apidx++) RTMPSetIndividualHT(pAd, apidx); #ifdef WDS_SUPPORT for (apidx = 0; apidx < MAX_WDS_ENTRY; apidx++) RTMPSetIndividualHT(pAd, apidx + MIN_NET_DEVICE_FOR_WDS); #endif /* WDS_SUPPORT */ #ifdef APCLI_SUPPORT for (apidx = 0; apidx < MAX_APCLI_NUM; apidx++) RTMPSetIndividualHT(pAd, apidx + MIN_NET_DEVICE_FOR_APCLI); #endif /* APCLI_SUPPORT */ } #endif /* CONFIG_AP_SUPPORT */ }
VOID RT28xxUsbMlmeRadioOFF( IN PRTMP_ADAPTER pAd) { WPDMA_GLO_CFG_STRUC GloCfg; UINT32 Value, i; DBGPRINT(RT_DEBUG_TRACE,("RT28xxUsbMlmeRadioOFF()\n")); if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF)) return; // Set LED RTMPSetLED(pAd, LED_RADIO_OFF); // Set Radio off flag RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF); #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { // Link down first if any association exists if (INFRA_ON(pAd) || ADHOC_ON(pAd)) LinkDown(pAd, FALSE); RTMPusecDelay(10000); //========================================== // Clean up old bss table BssTableInit(&pAd->ScanTab); } #endif // CONFIG_STA_SUPPORT // // Disable MAC Tx/Rx RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value); Value &= (0xfffffff3); RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value); // MAC_SYS_CTRL => value = 0x0 => 40mA RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, 0); // PWR_PIN_CFG => value = 0x0 => 40mA RTMP_IO_WRITE32(pAd, PWR_PIN_CFG, 0); // TX_PIN_CFG => value = 0x0 => 20mA RTMP_IO_WRITE32(pAd, TX_PIN_CFG, 0); if (pAd->CommonCfg.BBPCurrentBW == BW_40) { // Must using 40MHz. AsicTurnOffRFClk(pAd, pAd->CommonCfg.CentralChannel); } else { // Must using 20MHz. AsicTurnOffRFClk(pAd, pAd->CommonCfg.Channel); } // Waiting for DMA idle i = 0; do { RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word); if ((GloCfg.field.TxDMABusy == 0) && (GloCfg.field.RxDMABusy == 0)) break; RTMPusecDelay(1000); }while (i++ < 100); #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) AsicSendCommandToMcu(pAd, 0x30, 0xff, 0xff, 0x02); #endif // CONFIG_STA_SUPPORT // }
VOID RT28xxUsbMlmeRadioOFF( IN PRTMP_ADAPTER pAd) { WPDMA_GLO_CFG_STRUC GloCfg; UINT32 Value, i; DBGPRINT(RT_DEBUG_TRACE,("RT28xxUsbMlmeRadioOFF()\n")); if (RTMP_TEST_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF)) return; RTMPSetLED(pAd, LED_RADIO_OFF); RTMP_SET_FLAG(pAd, fRTMP_ADAPTER_RADIO_OFF); { if (INFRA_ON(pAd) || ADHOC_ON(pAd)) LinkDown(pAd, FALSE); RTMPusecDelay(10000); BssTableInit(&pAd->ScanTab); } if (pAd->CommonCfg.BBPCurrentBW == BW_40) { AsicTurnOffRFClk(pAd, pAd->CommonCfg.CentralChannel); } else { AsicTurnOffRFClk(pAd, pAd->CommonCfg.Channel); } RTUSBReadMACRegister(pAd, WPDMA_GLO_CFG, &GloCfg.word); GloCfg.field.EnableTxDMA = 0; GloCfg.field.EnableRxDMA = 0; RTUSBWriteMACRegister(pAd, WPDMA_GLO_CFG, GloCfg.word); i = 0; do { RTMP_IO_READ32(pAd, WPDMA_GLO_CFG, &GloCfg.word); if ((GloCfg.field.TxDMABusy == 0) && (GloCfg.field.RxDMABusy == 0)) break; RTMPusecDelay(1000); }while (i++ < 100); RTMP_IO_READ32(pAd, MAC_SYS_CTRL, &Value); Value &= (0xfffffff3); RTMP_IO_WRITE32(pAd, MAC_SYS_CTRL, Value); AsicSendCommandToMcu(pAd, 0x30, 0xff, 0xff, 0x02); }
VOID MlmeADDBAAction( IN PRTMP_ADAPTER pAd, IN MLME_QUEUE_ELEM *Elem) { MLME_ADDBA_REQ_STRUCT *pInfo; UCHAR Addr[6]; PUCHAR pOutBuffer = NULL; NDIS_STATUS NStatus; ULONG Idx; FRAME_ADDBA_REQ Frame; ULONG FrameLen; BA_ORI_ENTRY *pBAEntry = NULL; pInfo = (MLME_ADDBA_REQ_STRUCT *)Elem->Msg; NdisZeroMemory(&Frame, sizeof(FRAME_ADDBA_REQ)); if(MlmeAddBAReqSanity(pAd, Elem->Msg, Elem->MsgLen, Addr)) { NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory if(NStatus != NDIS_STATUS_SUCCESS) { DBGPRINT(RT_DEBUG_TRACE,("BA - MlmeADDBAAction() allocate memory failed \n")); return; } // 1. find entry Idx = pAd->MacTab.Content[pInfo->Wcid].BAOriWcidArray[pInfo->TID]; if (Idx == 0) { MlmeFreeMemory(pAd, pOutBuffer); DBGPRINT(RT_DEBUG_ERROR,("BA - MlmeADDBAAction() can't find BAOriEntry \n")); return; } else { pBAEntry =&pAd->BATable.BAOriEntry[Idx]; } #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { if (ADHOC_ON(pAd) #ifdef QOS_DLS_SUPPORT || (IS_ENTRY_DLS(&pAd->MacTab.Content[pInfo->Wcid])) #endif // QOS_DLS_SUPPORT // ) ActHeaderInit(pAd, &Frame.Hdr, pInfo->pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid); else ActHeaderInit(pAd, &Frame.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pInfo->pAddr); } #endif // CONFIG_STA_SUPPORT // Frame.Category = CATEGORY_BA; Frame.Action = ADDBA_REQ; Frame.BaParm.AMSDUSupported = 0; Frame.BaParm.BAPolicy = IMMED_BA; Frame.BaParm.TID = pInfo->TID; Frame.BaParm.BufSize = pInfo->BaBufSize; Frame.Token = pInfo->Token; Frame.TimeOutValue = pInfo->TimeOutValue; Frame.BaStartSeq.field.FragNum = 0; Frame.BaStartSeq.field.StartSeq = pAd->MacTab.Content[pInfo->Wcid].TxSeq[pInfo->TID]; *(USHORT *)(&Frame.BaParm) = cpu2le16(*(USHORT *)(&Frame.BaParm)); Frame.TimeOutValue = cpu2le16(Frame.TimeOutValue); Frame.BaStartSeq.word = cpu2le16(Frame.BaStartSeq.word); MakeOutgoingFrame(pOutBuffer, &FrameLen, sizeof(FRAME_ADDBA_REQ), &Frame, END_OF_ARGS); MiniportMMRequest(pAd, (MGMT_USE_QUEUE_FLAG | MapUserPriorityToAccessCategory[pInfo->TID]), pOutBuffer, FrameLen); MlmeFreeMemory(pAd, pOutBuffer); DBGPRINT(RT_DEBUG_TRACE, ("BA - Send ADDBA request. StartSeq = %x, FrameLen = %ld. BufSize = %d\n", Frame.BaStartSeq.field.StartSeq, FrameLen, Frame.BaParm.BufSize)); }
VOID PeerProbeReqAction( IN PRTMP_ADAPTER pAd, IN MLME_QUEUE_ELEM *Elem) { UCHAR Addr2[MAC_ADDR_LEN]; CHAR Ssid[MAX_LEN_OF_SSID]; UCHAR SsidLen; #ifdef DOT11_N_SUPPORT UCHAR HtLen, AddHtLen, NewExtLen; #endif HEADER_802_11 ProbeRspHdr; NDIS_STATUS NStatus; PUCHAR pOutBuffer = NULL; ULONG FrameLen = 0; LARGE_INTEGER FakeTimestamp; UCHAR DsLen = 1, IbssLen = 2; UCHAR LocalErpIe[3] = {IE_ERP, 1, 0}; BOOLEAN Privacy; USHORT CapabilityInfo; UCHAR RSNIe = IE_WPA; if (! ADHOC_ON(pAd)) return; if (PeerProbeReqSanity(pAd, Elem->Msg, Elem->MsgLen, Addr2, Ssid, &SsidLen)) { if ((SsidLen == 0) || SSID_EQUAL(Ssid, SsidLen, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen)) { NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); if (NStatus != NDIS_STATUS_SUCCESS) return; Privacy = (pAd->StaCfg.WepStatus == Ndis802_11Encryption1Enabled) || (pAd->StaCfg.WepStatus == Ndis802_11Encryption2Enabled) || (pAd->StaCfg.WepStatus == Ndis802_11Encryption3Enabled); CapabilityInfo = CAP_GENERATE(0, 1, Privacy, (pAd->CommonCfg.TxPreamble == Rt802_11PreambleShort), 0, 0); MakeOutgoingFrame(pOutBuffer, &FrameLen, sizeof(HEADER_802_11), &ProbeRspHdr, TIMESTAMP_LEN, &FakeTimestamp, 2, &pAd->CommonCfg.BeaconPeriod, 2, &CapabilityInfo, 1, &SsidIe, 1, &pAd->CommonCfg.SsidLen, pAd->CommonCfg.SsidLen, pAd->CommonCfg.Ssid, 1, &SupRateIe, 1, &pAd->StaActive.SupRateLen, pAd->StaActive.SupRateLen, pAd->StaActive.SupRate, 1, &DsIe, 1, &DsLen, 1, &pAd->CommonCfg.Channel, 1, &IbssIe, 1, &IbssLen, 2, &pAd->StaActive.AtimWin, END_OF_ARGS); if (pAd->StaActive.ExtRateLen) { ULONG tmp; MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp, 3, LocalErpIe, 1, &ExtRateIe, 1, &pAd->StaActive.ExtRateLen, pAd->StaActive.ExtRateLen, &pAd->StaActive.ExtRate, END_OF_ARGS); FrameLen += tmp; } if (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPANone) { ULONG tmp; MakeOutgoingFrame(pOutBuffer + FrameLen, &tmp, 1, &RSNIe, 1, &pAd->StaCfg.RSNIE_Len, pAd->StaCfg.RSNIE_Len, pAd->StaCfg.RSN_IE, END_OF_ARGS); FrameLen += tmp; } #ifdef DOT11_N_SUPPORT if (pAd->CommonCfg.PhyMode >= PHY_11ABGN_MIXED) { ULONG TmpLen; UCHAR BROADCOM[4] = {0x0, 0x90, 0x4c, 0x33}; HtLen = sizeof(pAd->CommonCfg.HtCapability); AddHtLen = sizeof(pAd->CommonCfg.AddHTInfo); NewExtLen = 1; if (pAd->bBroadComHT == TRUE) { MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen, 1, &WpaIe, 4, &BROADCOM[0], pAd->MlmeAux.HtCapabilityLen, &pAd->MlmeAux.HtCapability, END_OF_ARGS); } else { MakeOutgoingFrame(pOutBuffer + FrameLen, &TmpLen, 1, &HtCapIe, 1, &HtLen, sizeof(HT_CAPABILITY_IE), &pAd->CommonCfg.HtCapability, 1, &AddHtInfoIe, 1, &AddHtLen, sizeof(ADD_HT_INFO_IE), &pAd->CommonCfg.AddHTInfo, 1, &NewExtChanIe, 1, &NewExtLen, sizeof(NEW_EXT_CHAN_IE), &pAd->CommonCfg.NewExtChanOffset, END_OF_ARGS); } FrameLen += TmpLen; } #endif MiniportMMRequest(pAd, 0, pOutBuffer, FrameLen); MlmeFreeMemory(pAd, pOutBuffer); } } }
/* ========================================================================== Description: send DELBA and delete BaEntry if any Parametrs: Elem - MLME message MLME_DELBA_REQ_STRUCT IRQL = DISPATCH_LEVEL ========================================================================== */ void MlmeDELBAAction(RTMP_ADAPTER *pAd, MLME_QUEUE_ELEM *Elem) { MLME_DELBA_REQ_STRUCT *pInfo; PUCHAR pOutBuffer = NULL, pOutBuffer2 = NULL; ULONG Idx; FRAME_DELBA_REQ Frame; ULONG FrameLen; FRAME_BAR FrameBar; MAC_TABLE_ENTRY *pEntry = NULL; struct wifi_dev *wdev; pInfo = (MLME_DELBA_REQ_STRUCT *)Elem->Msg; /* must send back DELBA */ NdisZeroMemory(&Frame, sizeof(FRAME_DELBA_REQ)); DBGPRINT(RT_DEBUG_TRACE, ("==> MlmeDELBAAction(), Initiator(%d) \n", pInfo->Initiator)); if (MlmeDelBAReqSanity(pAd, Elem->Msg, Elem->MsgLen) && VALID_WCID(pInfo->Wcid)) { pOutBuffer = MlmeAllocateMemory(); if (!pOutBuffer) { return; } pOutBuffer2 = MlmeAllocateMemory(); if (!pOutBuffer2) { MlmeFreeMemory(pOutBuffer); return; } /* SEND BAR (Send BAR to refresh peer reordering buffer.) */ pEntry = &pAd->MacTab.Content[pInfo->Wcid]; if (!pEntry->wdev) { DBGPRINT(RT_DEBUG_ERROR, ("%s():No binding wdev for wcid(%d)\n", __FUNCTION__, pInfo->Wcid)); MlmeFreeMemory(pOutBuffer); MlmeFreeMemory(pOutBuffer2); return; } wdev = pEntry->wdev; Idx = pEntry->BAOriWcidArray[pInfo->TID]; #ifdef APCLI_SUPPORT #endif /* APCLI_SUPPORT */ BarHeaderInit(pAd, &FrameBar, pEntry->Addr, wdev->if_addr); FrameBar.StartingSeq.field.FragNum = 0; /* make sure sequence not clear in DEL funciton.*/ FrameBar.StartingSeq.field.StartSeq = pAd->MacTab.Content[pInfo->Wcid].TxSeq[pInfo->TID]; /* make sure sequence not clear in DEL funciton.*/ FrameBar.BarControl.TID = pInfo->TID; /* make sure sequence not clear in DEL funciton.*/ FrameBar.BarControl.ACKPolicy = IMMED_BA; /* make sure sequence not clear in DEL funciton.*/ FrameBar.BarControl.Compressed = 1; /* make sure sequence not clear in DEL funciton.*/ FrameBar.BarControl.MTID = 0; /* make sure sequence not clear in DEL funciton.*/ MakeOutgoingFrame(pOutBuffer2, &FrameLen, sizeof(FRAME_BAR), &FrameBar, END_OF_ARGS); MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer2, FrameLen); MlmeFreeMemory(pOutBuffer2); DBGPRINT(RT_DEBUG_TRACE, ("BA - MlmeDELBAAction() . Send BAR to refresh peer reordering buffer \n")); /* SEND DELBA FRAME*/ FrameLen = 0; //CFG_TODO #ifdef CONFIG_AP_SUPPORT IF_DEV_CONFIG_OPMODE_ON_AP(pAd) { #ifdef APCLI_SUPPORT #endif /* APCLI_SUPPORT */ ActHeaderInit(pAd, &Frame.Hdr, pEntry->Addr, pEntry->wdev->if_addr, pEntry->wdev->bssid); } #endif /* CONFIG_AP_SUPPORT */ #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { if (ADHOC_ON(pAd)) ActHeaderInit(pAd, &Frame.Hdr, pEntry->Addr, pAd->StaCfg.wdev.if_addr, pAd->StaCfg.wdev.bssid); else ActHeaderInit(pAd, &Frame.Hdr, pEntry->Addr, pAd->StaCfg.wdev.if_addr, pAd->StaCfg.wdev.bssid); } #endif /* CONFIG_STA_SUPPORT */ Frame.Category = CATEGORY_BA; Frame.Action = DELBA; Frame.DelbaParm.Initiator = pInfo->Initiator; Frame.DelbaParm.TID = pInfo->TID; Frame.ReasonCode = 39; /* Time Out*/ *(USHORT *)(&Frame.DelbaParm) = cpu2le16(*(USHORT *)(&Frame.DelbaParm)); Frame.ReasonCode = cpu2le16(Frame.ReasonCode); MakeOutgoingFrame(pOutBuffer, &FrameLen, sizeof(FRAME_DELBA_REQ), &Frame, END_OF_ARGS); MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen); MlmeFreeMemory(pOutBuffer); DBGPRINT(RT_DEBUG_TRACE, ("BA - MlmeDELBAAction() . 3 DELBA sent. Initiator(%d)\n", pInfo->Initiator)); }
/* ========================================================================== Description: Scan next channel ========================================================================== */ VOID ScanNextChannel( IN PRTMP_ADAPTER pAd) { HEADER_802_11 Hdr80211; PUCHAR pOutBuffer = NULL; NDIS_STATUS NStatus; ULONG FrameLen = 0; UCHAR SsidLen = 0, ScanType = pAd->MlmeAux.ScanType, BBPValue = 0; #ifdef CONFIG_STA_SUPPORT USHORT Status; PHEADER_802_11 pHdr80211; #endif // CONFIG_STA_SUPPORT // UINT ScanTimeIn5gChannel = SHORT_CHANNEL_TIME; #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { if (MONITOR_ON(pAd)) return; } #endif // CONFIG_STA_SUPPORT // #ifdef RALINK_ATE // Nothing to do in ATE mode. if (ATE_ON(pAd)) return; #endif // RALINK_ATE // if (pAd->MlmeAux.Channel == 0) { if ((pAd->CommonCfg.BBPCurrentBW == BW_40) && ( #ifdef CONFIG_STA_SUPPORT INFRA_ON(pAd) || ADHOC_ON(pAd) || #endif // CONFIG_STA_SUPPORT // (0))) { AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel); RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue); BBPValue &= (~0x18); BBPValue |= 0x10; RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue); DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to 40MHz channel %d, Total BSS[%02d]\n",pAd->CommonCfg.CentralChannel, pAd->ScanTab.BssNr)); } else { AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.Channel); DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to channel %d, Total BSS[%02d]\n",pAd->CommonCfg.Channel, pAd->ScanTab.BssNr)); } #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { /* If all peer Ad-hoc clients leave, driver would do LinkDown and LinkUp. In LinkUp, CommonCfg.Ssid would copy SSID from MlmeAux. To prevent SSID is zero or wrong in Beacon, need to recover MlmeAux.SSID here. */ if (ADHOC_ON(pAd)) { NdisZeroMemory(pAd->MlmeAux.Ssid, MAX_LEN_OF_SSID); pAd->MlmeAux.SsidLen = pAd->CommonCfg.SsidLen; NdisMoveMemory(pAd->MlmeAux.Ssid, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen); } // // To prevent data lost. // Send an NULL data with turned PSM bit on to current associated AP before SCAN progress. // Now, we need to send an NULL data with turned PSM bit off to AP, when scan progress done // if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) && (INFRA_ON(pAd))) { NStatus = MlmeAllocateMemory(pAd, (PVOID)&pOutBuffer); if (NStatus == NDIS_STATUS_SUCCESS) { pHdr80211 = (PHEADER_802_11) pOutBuffer; MgtMacHeaderInit(pAd, pHdr80211, SUBTYPE_NULL_FUNC, 1, pAd->CommonCfg.Bssid, pAd->CommonCfg.Bssid); pHdr80211->Duration = 0; pHdr80211->FC.Type = BTYPE_DATA; pHdr80211->FC.PwrMgmt = (pAd->StaCfg.Psm == PWR_SAVE); // Send using priority queue MiniportMMRequest(pAd, 0, pOutBuffer, sizeof(HEADER_802_11)); DBGPRINT(RT_DEBUG_TRACE, ("MlmeScanReqAction -- Send PSM Data frame\n")); MlmeFreeMemory(pAd, pOutBuffer); RTMPusecDelay(5000); } } pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE; Status = MLME_SUCCESS; MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_SCAN_CONF, 2, &Status, 0); RTMPSendWirelessEvent(pAd, IW_SCAN_COMPLETED_EVENT_FLAG, NULL, BSS0, 0); #ifdef LINUX #ifdef RT_CFG80211_SUPPORT RTEnqueueInternalCmd(pAd, CMDTHREAD_SCAN_END, NULL, 0); #endif // RT_CFG80211_SUPPORT // #endif // LINUX // } #endif // CONFIG_STA_SUPPORT // } else {
void PeerAddBAReqAction(struct rt_rtmp_adapter *pAd, struct rt_mlme_queue_elem *Elem) { /* 7.4.4.1 */ /*unsigned long Idx; */ u8 Status = 1; u8 pAddr[6]; struct rt_frame_addba_rsp ADDframe; u8 *pOutBuffer = NULL; int NStatus; struct rt_frame_addba_req * pAddreqFrame = NULL; /*u8 BufSize; */ unsigned long FrameLen; unsigned long *ptemp; struct rt_mac_table_entry *pMacEntry; DBGPRINT(RT_DEBUG_TRACE, ("%s ==> (Wcid = %d)\n", __func__, Elem->Wcid)); /*hex_dump("AddBAReq", Elem->Msg, Elem->MsgLen); */ /*ADDBA Request from unknown peer, ignore this. */ if (Elem->Wcid >= MAX_LEN_OF_MAC_TABLE) return; pMacEntry = &pAd->MacTab.Content[Elem->Wcid]; DBGPRINT(RT_DEBUG_TRACE, ("BA - PeerAddBAReqAction----> \n")); ptemp = (unsigned long *)Elem->Msg; /*DBGPRINT_RAW(RT_DEBUG_EMU, ("%08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x\n", *(ptemp), *(ptemp+1), *(ptemp+2), *(ptemp+3), *(ptemp+4), *(ptemp+5), *(ptemp+6), *(ptemp+7), *(ptemp+8))); */ if (PeerAddBAReqActionSanity(pAd, Elem->Msg, Elem->MsgLen, pAddr)) { if ((pAd->CommonCfg.bBADecline == FALSE) && IS_HT_STA(pMacEntry)) { pAddreqFrame = (struct rt_frame_addba_req *) (&Elem->Msg[0]); DBGPRINT(RT_DEBUG_OFF, ("Rcv Wcid(%d) AddBAReq\n", Elem->Wcid)); if (BARecSessionAdd (pAd, &pAd->MacTab.Content[Elem->Wcid], pAddreqFrame)) Status = 0; else Status = 38; /* more parameters have invalid values */ } else { Status = 37; /* the request has been declined. */ } } if (pAd->MacTab.Content[Elem->Wcid].ValidAsCLI) ASSERT(pAd->MacTab.Content[Elem->Wcid].Sst == SST_ASSOC); pAddreqFrame = (struct rt_frame_addba_req *) (&Elem->Msg[0]); /* 2. Always send back ADDBA Response */ NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); /*Get an unused nonpaged memory */ if (NStatus != NDIS_STATUS_SUCCESS) { DBGPRINT(RT_DEBUG_TRACE, ("ACTION - PeerBAAction() allocate memory failed \n")); return; } NdisZeroMemory(&ADDframe, sizeof(struct rt_frame_addba_rsp)); /* 2-1. Prepare ADDBA Response frame. */ { if (ADHOC_ON(pAd)) ActHeaderInit(pAd, &ADDframe.Hdr, pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid); else ActHeaderInit(pAd, &ADDframe.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAddr); } ADDframe.Category = CATEGORY_BA; ADDframe.Action = ADDBA_RESP; ADDframe.Token = pAddreqFrame->Token; /* What is the Status code?? need to check. */ ADDframe.StatusCode = Status; ADDframe.BaParm.BAPolicy = IMMED_BA; ADDframe.BaParm.AMSDUSupported = 0; ADDframe.BaParm.TID = pAddreqFrame->BaParm.TID; ADDframe.BaParm.BufSize = min(((u8)pAddreqFrame->BaParm.BufSize), (u8)pAd->CommonCfg.BACapability.field.RxBAWinLimit); if (ADDframe.BaParm.BufSize == 0) { ADDframe.BaParm.BufSize = 64; } ADDframe.TimeOutValue = 0; /*pAddreqFrame->TimeOutValue; */ *(u16 *) (&ADDframe.BaParm) = cpu2le16(*(u16 *) (&ADDframe.BaParm)); ADDframe.StatusCode = cpu2le16(ADDframe.StatusCode); ADDframe.TimeOutValue = cpu2le16(ADDframe.TimeOutValue); MakeOutgoingFrame(pOutBuffer, &FrameLen, sizeof(struct rt_frame_addba_rsp), &ADDframe, END_OF_ARGS); MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen); MlmeFreeMemory(pAd, pOutBuffer); DBGPRINT(RT_DEBUG_TRACE, ("%s(%d): TID(%d), BufSize(%d) <== \n", __func__, Elem->Wcid, ADDframe.BaParm.TID, ADDframe.BaParm.BufSize)); }
static INT CFG80211_DummyP2pIf_Close( IN PNET_DEV dev_p) { struct wireless_dev *wdev = dev_p->ieee80211_ptr; #ifdef RT_CFG80211_P2P_STATIC_CONCURRENT_DEVICE VOID *pAdSrc; pAdSrc = RTMP_OS_NETDEV_GET_PRIV(dev_p); ASSERT(pAdSrc); PRTMP_ADAPTER pAd = (PRTMP_ADAPTER)pAdSrc; PCFG80211_CTRL cfg80211_ctrl = &pAd->cfg80211_ctrl; BOOLEAN isGoOn = FALSE; UINT apidx = 1; struct wifi_dev *Wdev; #endif /* RT_CFG80211_P2P_STATIC_CONCURRENT_DEVICE */ if (!wdev) return -EINVAL; #ifdef RT_CFG80211_P2P_STATIC_CONCURRENT_DEVICE if (pAd->flg_apcli_init) { DBGPRINT(RT_DEBUG_TRACE, ("ApCli_Close\n")); CFG80211OS_ScanEnd(pAd->pCfg80211_CB, TRUE); // RT_MOD_DEC_USE_COUNT(); ApCli_Close(pAd, dev_p); } DBGPRINT(RT_DEBUG_TRACE, ("%s: ===> %s\n", __FUNCTION__, RTMP_OS_NETDEV_GET_DEVNAME(dev_p))); RTMP_OS_NETDEV_STOP_QUEUE(dev_p); if (INFRA_ON(pAd)) AsicEnableBssSync(pAd,100); else if (ADHOC_ON(pAd)) AsicEnableIbssSync(pAd); else AsicDisableSync(pAd); //VIRTUAL_IF_DOWN(pAd); if (cfg80211_ctrl->dummy_p2p_net_dev) { //iverson if (isGoOn) { Wdev = &pAd->ApCfg.MBSSID[apidx].wdev; wdev_bcn_buf_deinit(pAd, &pAd->ApCfg.MBSSID[apidx].bcn_buf); rtmp_wdev_idx_unreg(pAd, Wdev); Wdev->if_dev = NULL; } else if (pAd->flg_apcli_init) { Wdev = &pAd->ApCfg.ApCliTab[MAIN_MBSSID].wdev; OPSTATUS_CLEAR_FLAG(pAd, fOP_AP_STATUS_MEDIA_STATE_CONNECTED); cfg80211_disconnected(dev_p, 0, NULL, 0, GFP_KERNEL); CFG80211OS_ScanEnd(pAd->pCfg80211_CB, TRUE); NdisZeroMemory(pAd->ApCfg.ApCliTab[MAIN_MBSSID].CfgApCliBssid, MAC_ADDR_LEN); // RtmpOSNetDevDetach(dev_p); rtmp_wdev_idx_unreg(pAd, Wdev); pAd->flg_apcli_init = FALSE; // Wdev->if_dev = NULL; } } AsicSetBssid(pAd, pAd->cfg80211_ctrl.P2PCurrentAddress, 0x1); AsicSetBssid(pAd, pAd->CurrentAddress, 0x0); #endif /* RT_CFG80211_P2P_STATIC_CONCURRENT_DEVICE */ wdev->wiphy->interface_modes = (wdev->wiphy->interface_modes) & (~(BIT(NL80211_IFTYPE_P2P_CLIENT) | BIT(NL80211_IFTYPE_P2P_GO) #if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,7,0)) | BIT(RT_CMD_80211_IFTYPE_P2P_DEVICE) #endif /* LINUX_VERSION_CODE: 3.7.0 */ )); #ifdef RT_CFG80211_P2P_STATIC_CONCURRENT_DEVICE RT_MOD_DEC_USE_COUNT(); #endif /* RT_CFG80211_P2P_STATIC_CONCURRENT_DEVICE */ return 0; }
/* ======================================================================== Routine Description: Caller ensures we has 802.11n support. Calls at setting HT from AP/STASetinformation Arguments: pAd - Pointer to our adapter phymode - ======================================================================== */ VOID RTMPSetHT( IN RTMP_ADAPTER *pAd, IN OID_SET_HT_PHYMODE *pHTPhyMode) { UCHAR RxStream = pAd->CommonCfg.RxStream; #ifdef CONFIG_AP_SUPPORT int apidx; #endif /* CONFIG_AP_SUPPORT */ int bw; RT_HT_CAPABILITY *rt_ht_cap = &pAd->CommonCfg.DesiredHtPhy; HT_CAPABILITY_IE *ht_cap= &pAd->CommonCfg.HtCapability; #ifdef CONFIG_AP_SUPPORT /* sanity check for extention channel */ if (CHAN_PropertyCheck(pAd, pAd->CommonCfg.Channel, CHANNEL_NO_FAT_BELOW | CHANNEL_NO_FAT_ABOVE) == TRUE) { /* only 20MHz is allowed */ pHTPhyMode->BW = 0; } else if (pHTPhyMode->ExtOffset == EXTCHA_BELOW) { /* extension channel below this channel is not allowed */ if (CHAN_PropertyCheck(pAd, pAd->CommonCfg.Channel, CHANNEL_NO_FAT_BELOW) == TRUE) { pHTPhyMode->ExtOffset = EXTCHA_ABOVE; } } else if (pHTPhyMode->ExtOffset == EXTCHA_ABOVE) { /* extension channel above this channel is not allowed */ if (CHAN_PropertyCheck(pAd, pAd->CommonCfg.Channel, CHANNEL_NO_FAT_ABOVE) == TRUE) { pHTPhyMode->ExtOffset = EXTCHA_BELOW; } } #endif /* CONFIG_AP_SUPPORT */ DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetHT : HT_mode(%d), ExtOffset(%d), MCS(%d), BW(%d), STBC(%d), SHORTGI(%d)\n", pHTPhyMode->HtMode, pHTPhyMode->ExtOffset, pHTPhyMode->MCS, pHTPhyMode->BW, pHTPhyMode->STBC, pHTPhyMode->SHORTGI)); /* Don't zero supportedHyPhy structure.*/ RTMPZeroMemory(ht_cap, sizeof(HT_CAPABILITY_IE)); RTMPZeroMemory(&pAd->CommonCfg.AddHTInfo, sizeof(pAd->CommonCfg.AddHTInfo)); RTMPZeroMemory(&pAd->CommonCfg.NewExtChanOffset, sizeof(pAd->CommonCfg.NewExtChanOffset)); RTMPZeroMemory(rt_ht_cap, sizeof(RT_HT_CAPABILITY)); if (pAd->CommonCfg.bRdg) { ht_cap->ExtHtCapInfo.PlusHTC = 1; ht_cap->ExtHtCapInfo.RDGSupport = 1; } else { ht_cap->ExtHtCapInfo.PlusHTC = 0; ht_cap->ExtHtCapInfo.RDGSupport = 0; } if (RxStream == 1) { ht_cap->HtCapParm.MaxRAmpduFactor = 2; rt_ht_cap->MaxRAmpduFactor = 2; } else { ht_cap->HtCapParm.MaxRAmpduFactor = 3; rt_ht_cap->MaxRAmpduFactor = 3; } DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetHT : RxBAWinLimit = %d\n", pAd->CommonCfg.BACapability.field.RxBAWinLimit)); /* Mimo power save, A-MSDU size, */ rt_ht_cap->AmsduEnable = (USHORT)pAd->CommonCfg.BACapability.field.AmsduEnable; rt_ht_cap->AmsduSize = (UCHAR)pAd->CommonCfg.BACapability.field.AmsduSize; rt_ht_cap->MimoPs = (UCHAR)pAd->CommonCfg.BACapability.field.MMPSmode; rt_ht_cap->MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity; ht_cap->HtCapInfo.AMsduSize = (USHORT)pAd->CommonCfg.BACapability.field.AmsduSize; ht_cap->HtCapInfo.MimoPs = (USHORT)pAd->CommonCfg.BACapability.field.MMPSmode; ht_cap->HtCapParm.MpduDensity = (UCHAR)pAd->CommonCfg.BACapability.field.MpduDensity; DBGPRINT(RT_DEBUG_TRACE, ("RTMPSetHT : AMsduSize = %d, MimoPs = %d, MpduDensity = %d, MaxRAmpduFactor = %d\n", rt_ht_cap->AmsduSize, rt_ht_cap->MimoPs, rt_ht_cap->MpduDensity, rt_ht_cap->MaxRAmpduFactor)); if(pHTPhyMode->HtMode == HTMODE_GF) { ht_cap->HtCapInfo.GF = 1; rt_ht_cap->GF = 1; } else rt_ht_cap->GF = 0; /* Decide Rx MCSSet*/ switch (RxStream) { case 3: ht_cap->MCSSet[2] = 0xff; case 2: ht_cap->MCSSet[1] = 0xff; case 1: default: ht_cap->MCSSet[0] = 0xff; break; } if (pAd->CommonCfg.bForty_Mhz_Intolerant && (pHTPhyMode->BW == BW_40)) { pHTPhyMode->BW = BW_20; ht_cap->HtCapInfo.Forty_Mhz_Intolerant = 1; } // TODO: shiang-6590, how about the "bw" when channel 14 for JP region??? bw = BW_20; if(pHTPhyMode->BW == BW_40) { ht_cap->MCSSet[4] = 0x1; /* MCS 32*/ ht_cap->HtCapInfo.ChannelWidth = 1; if (pAd->CommonCfg.Channel <= 14) ht_cap->HtCapInfo.CCKmodein40 = 1; rt_ht_cap->ChannelWidth = 1; pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth = 1; pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset = (pHTPhyMode->ExtOffset == EXTCHA_BELOW)? (EXTCHA_BELOW): EXTCHA_ABOVE; /* Set Regsiter for extension channel position.*/ rtmp_mac_set_ctrlch(pAd, pHTPhyMode->ExtOffset); /* Turn on BBP 40MHz mode now only as AP . */ /* Sta can turn on BBP 40MHz after connection with 40MHz AP. Sta only broadcast 40MHz capability before connection.*/ if ((pAd->OpMode == OPMODE_AP) || INFRA_ON(pAd) || ADHOC_ON(pAd) ) { rtmp_bbp_set_ctrlch(pAd, pHTPhyMode->ExtOffset); #ifdef GREENAP_SUPPORT if (pAd->ApCfg.bGreenAPActive == 1) bw = BW_20; else #endif /* GREENAP_SUPPORT */ bw = BW_40; } } else { ht_cap->HtCapInfo.ChannelWidth = 0; rt_ht_cap->ChannelWidth = 0; pAd->CommonCfg.AddHTInfo.AddHtInfo.RecomWidth = 0; pAd->CommonCfg.AddHTInfo.AddHtInfo.ExtChanOffset = EXTCHA_NONE; pAd->CommonCfg.CentralChannel = pAd->CommonCfg.Channel; /* Turn on BBP 20MHz mode by request here.*/ bw = BW_20; } #ifdef DOT11_VHT_AC if (pHTPhyMode->BW == BW_40 && pAd->CommonCfg.vht_bw == VHT_BW_80 && pAd->CommonCfg.vht_cent_ch) bw = BW_80; #endif /* DOT11_VHT_AC */ rtmp_bbp_set_bw(pAd, bw); if(pHTPhyMode->STBC == STBC_USE) { if (pAd->Antenna.field.TxPath >= 2) { ht_cap->HtCapInfo.TxSTBC = 1; rt_ht_cap->TxSTBC = 1; } else { ht_cap->HtCapInfo.TxSTBC = 0; rt_ht_cap->TxSTBC = 0; } /* RxSTBC 0: not support, 1: support for 1SS 2: support for 1SS, 2SS 3: support for 1SS, 2SS, 3SS */ if (pAd->Antenna.field.RxPath >= 1) { ht_cap->HtCapInfo.RxSTBC = 1; rt_ht_cap->RxSTBC = 1; } else { ht_cap->HtCapInfo.RxSTBC = 0; rt_ht_cap->RxSTBC = 0; } } else { rt_ht_cap->TxSTBC = 0; rt_ht_cap->RxSTBC = 0; } if(pHTPhyMode->SHORTGI == GI_400) { ht_cap->HtCapInfo.ShortGIfor20 = 1; ht_cap->HtCapInfo.ShortGIfor40 = 1; rt_ht_cap->ShortGIfor20 = 1; rt_ht_cap->ShortGIfor40 = 1; } else { ht_cap->HtCapInfo.ShortGIfor20 = 0; ht_cap->HtCapInfo.ShortGIfor40 = 0; rt_ht_cap->ShortGIfor20 = 0; rt_ht_cap->ShortGIfor40 = 0; } /* We support link adaptation for unsolicit MCS feedback, set to 2.*/ pAd->CommonCfg.AddHTInfo.ControlChan = pAd->CommonCfg.Channel; /* 1, the extension channel above the control channel. */ /* EDCA parameters used for AP's own transmission*/ if (pAd->CommonCfg.APEdcaParm.bValid == FALSE) { pAd->CommonCfg.APEdcaParm.bValid = TRUE; pAd->CommonCfg.APEdcaParm.Aifsn[0] = 3; pAd->CommonCfg.APEdcaParm.Aifsn[1] = 7; pAd->CommonCfg.APEdcaParm.Aifsn[2] = 1; pAd->CommonCfg.APEdcaParm.Aifsn[3] = 1; pAd->CommonCfg.APEdcaParm.Cwmin[0] = 4; pAd->CommonCfg.APEdcaParm.Cwmin[1] = 4; pAd->CommonCfg.APEdcaParm.Cwmin[2] = 3; pAd->CommonCfg.APEdcaParm.Cwmin[3] = 2; pAd->CommonCfg.APEdcaParm.Cwmax[0] = 6; pAd->CommonCfg.APEdcaParm.Cwmax[1] = 10; pAd->CommonCfg.APEdcaParm.Cwmax[2] = 4; pAd->CommonCfg.APEdcaParm.Cwmax[3] = 3; pAd->CommonCfg.APEdcaParm.Txop[0] = 0; pAd->CommonCfg.APEdcaParm.Txop[1] = 0; pAd->CommonCfg.APEdcaParm.Txop[2] = 94; pAd->CommonCfg.APEdcaParm.Txop[3] = 47; } AsicSetEdcaParm(pAd, &pAd->CommonCfg.APEdcaParm); #ifdef TXBF_SUPPORT if (pAd->chipCap.FlgHwTxBfCap) { /* Set ETxBF */ setETxBFCap(pAd, &ht_cap->TxBFCap); /* Check ITxBF */ pAd->CommonCfg.RegTransmitSetting.field.ITxBfEn &= rtmp_chk_itxbf_calibration(pAd); /* Apply to ASIC */ rtmp_asic_set_bf(pAd); } #endif /* TXBF_SUPPORT */ #ifdef CONFIG_AP_SUPPORT IF_DEV_CONFIG_OPMODE_ON_AP(pAd) { for (apidx = 0; apidx < pAd->ApCfg.BssidNum; apidx++) RTMPSetIndividualHT(pAd, apidx); #ifdef WDS_SUPPORT for (apidx = 0; apidx < MAX_WDS_ENTRY; apidx++) RTMPSetIndividualHT(pAd, apidx + MIN_NET_DEVICE_FOR_WDS); #endif /* WDS_SUPPORT */ #ifdef APCLI_SUPPORT for (apidx = 0; apidx < MAX_APCLI_NUM; apidx++) RTMPSetIndividualHT(pAd, apidx + MIN_NET_DEVICE_FOR_APCLI); #endif /* APCLI_SUPPORT */ } #endif /* CONFIG_AP_SUPPORT */ }
VOID PeerBeacon( IN PRTMP_ADAPTER pAd, IN MLME_QUEUE_ELEM *Elem) { UCHAR Bssid[MAC_ADDR_LEN], Addr2[MAC_ADDR_LEN]; CHAR Ssid[MAX_LEN_OF_SSID]; CF_PARM CfParm; UCHAR SsidLen, MessageToMe=0, BssType, Channel, NewChannel, index=0; UCHAR DtimCount=0, DtimPeriod=0, BcastFlag=0; USHORT CapabilityInfo, AtimWin, BeaconPeriod; LARGE_INTEGER TimeStamp; USHORT TbttNumToNextWakeUp; UCHAR Erp; UCHAR SupRate[MAX_LEN_OF_SUPPORTED_RATES], ExtRate[MAX_LEN_OF_SUPPORTED_RATES]; UCHAR SupRateLen, ExtRateLen; UCHAR CkipFlag; USHORT LenVIE; UCHAR AironetCellPowerLimit; EDCA_PARM EdcaParm; QBSS_LOAD_PARM QbssLoad; QOS_CAPABILITY_PARM QosCapability; ULONG RalinkIe; UCHAR VarIE[MAX_VIE_LEN]; NDIS_802_11_VARIABLE_IEs *pVIE = NULL; HT_CAPABILITY_IE HtCapability; ADD_HT_INFO_IE AddHtInfo; UCHAR HtCapabilityLen, PreNHtCapabilityLen; UCHAR AddHtInfoLen; UCHAR NewExtChannelOffset = 0xff; #ifdef RALINK_ATE if (ATE_ON(pAd)) { return; } #endif if (!(INFRA_ON(pAd) || ADHOC_ON(pAd) )) return; pVIE = (PNDIS_802_11_VARIABLE_IEs) VarIE; pVIE->Length = 0; RTMPZeroMemory(&HtCapability, sizeof(HtCapability)); RTMPZeroMemory(&AddHtInfo, sizeof(ADD_HT_INFO_IE)); if (PeerBeaconAndProbeRspSanity(pAd, Elem->Msg, Elem->MsgLen, Elem->Channel, Addr2, Bssid, Ssid, &SsidLen, &BssType, &BeaconPeriod, &Channel, &NewChannel, &TimeStamp, &CfParm, &AtimWin, &CapabilityInfo, &Erp, &DtimCount, &DtimPeriod, &BcastFlag, &MessageToMe, SupRate, &SupRateLen, ExtRate, &ExtRateLen, &CkipFlag, &AironetCellPowerLimit, &EdcaParm, &QbssLoad, &QosCapability, &RalinkIe, &HtCapabilityLen, &PreNHtCapabilityLen, &HtCapability, &AddHtInfoLen, &AddHtInfo, &NewExtChannelOffset, &LenVIE, pVIE)) { BOOLEAN is_my_bssid, is_my_ssid; ULONG Bssidx, Now; BSS_ENTRY *pBss; CHAR RealRssi = RTMPMaxRssi(pAd, ConvertToRssi(pAd, Elem->Rssi0, RSSI_0), ConvertToRssi(pAd, Elem->Rssi1, RSSI_1), ConvertToRssi(pAd, Elem->Rssi2, RSSI_2)); is_my_bssid = MAC_ADDR_EQUAL(Bssid, pAd->CommonCfg.Bssid)? TRUE : FALSE; is_my_ssid = SSID_EQUAL(Ssid, SsidLen, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen)? TRUE:FALSE; if ((! is_my_ssid) && (! is_my_bssid)) return; if (pAd->Mlme.CntlMachine.CurrState == CNTL_WAIT_DISASSOC) return; #ifdef DOT11_N_SUPPORT if (AddHtInfoLen != 0) Channel = AddHtInfo.ControlChan; if ((HtCapabilityLen > 0) || (PreNHtCapabilityLen > 0)) HtCapabilityLen = SIZE_HT_CAP_IE; #endif Bssidx = BssTableSearch(&pAd->ScanTab, Bssid, Channel); if (Bssidx == BSS_NOT_FOUND) { Bssidx = BssTableSetEntry(pAd, &pAd->ScanTab, Bssid, Ssid, SsidLen, BssType, BeaconPeriod, &CfParm, AtimWin, CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen, &HtCapability, &AddHtInfo,HtCapabilityLen,AddHtInfoLen,NewExtChannelOffset, Channel, RealRssi, TimeStamp, CkipFlag, &EdcaParm, &QosCapability, &QbssLoad, LenVIE, pVIE); if (Bssidx == BSS_NOT_FOUND) return; NdisMoveMemory(pAd->ScanTab.BssEntry[Bssidx].PTSF, &Elem->Msg[24], 4); NdisMoveMemory(&pAd->ScanTab.BssEntry[Bssidx].TTSF[0], &Elem->TimeStamp.u.LowPart, 4); NdisMoveMemory(&pAd->ScanTab.BssEntry[Bssidx].TTSF[4], &Elem->TimeStamp.u.LowPart, 4); } if ((pAd->CommonCfg.bIEEE80211H == 1) && (NewChannel != 0) && (Channel != NewChannel)) { AsicSwitchChannel(pAd, 1, FALSE); AsicLockChannel(pAd, 1); LinkDown(pAd, FALSE); MlmeQueueInit(&pAd->Mlme.Queue); BssTableInit(&pAd->ScanTab); RTMPusecDelay(1000000); for (index = 0 ; index < pAd->ChannelListNum; index++) { if (pAd->ChannelList[index].Channel == NewChannel) { pAd->ScanTab.BssEntry[Bssidx].Channel = NewChannel; pAd->CommonCfg.Channel = NewChannel; AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.Channel); DBGPRINT(RT_DEBUG_TRACE, ("PeerBeacon - STA receive channel switch announcement IE (New Channel =%d)\n", NewChannel)); break; } } if (index >= pAd->ChannelListNum) { DBGPRINT_ERR(("PeerBeacon(can not find New Channel=%d in ChannelList[%d]\n", pAd->CommonCfg.Channel, pAd->ChannelListNum)); } } if ((! is_my_bssid) && ADHOC_ON(pAd)) { INT i; if (pAd->StaCfg.WepStatus != pAd->ScanTab.BssEntry[Bssidx].WepStatus) { return; } for (i = 0; i < 6; i++) { if (Bssid[i] > pAd->CommonCfg.Bssid[i]) { DBGPRINT(RT_DEBUG_TRACE, ("SYNC - merge to the IBSS with bigger BSSID=%02x:%02x:%02x:%02x:%02x:%02x\n", Bssid[0], Bssid[1], Bssid[2], Bssid[3], Bssid[4], Bssid[5])); AsicDisableSync(pAd); COPY_MAC_ADDR(pAd->CommonCfg.Bssid, Bssid); AsicSetBssid(pAd, pAd->CommonCfg.Bssid); MakeIbssBeacon(pAd); AsicEnableIbssSync(pAd); is_my_bssid = TRUE; break; } else if (Bssid[i] < pAd->CommonCfg.Bssid[i]) break; } } NdisGetSystemUpTime(&Now); pBss = &pAd->ScanTab.BssEntry[Bssidx]; pBss->Rssi = RealRssi; pBss->LastBeaconRxTime = Now; if (is_my_bssid) { RXWI_STRUC RxWI; pAd->StaCfg.DtimCount = DtimCount; pAd->StaCfg.DtimPeriod = DtimPeriod; pAd->StaCfg.LastBeaconRxTime = Now; RxWI.RSSI0 = Elem->Rssi0; RxWI.RSSI1 = Elem->Rssi1; RxWI.RSSI2 = Elem->Rssi2; Update_Rssi_Sample(pAd, &pAd->StaCfg.RssiSample, &RxWI); if (AironetCellPowerLimit != 0xFF) { ChangeToCellPowerLimit(pAd, AironetCellPowerLimit); } else { pAd->CommonCfg.TxPowerPercentage = pAd->CommonCfg.TxPowerDefault; } if (ADHOC_ON(pAd) && (CAP_IS_IBSS_ON(CapabilityInfo))) { UCHAR MaxSupportedRateIn500Kbps = 0; UCHAR idx; MAC_TABLE_ENTRY *pEntry; for (idx=0; idx<SupRateLen; idx++) { if (MaxSupportedRateIn500Kbps < (SupRate[idx] & 0x7f)) MaxSupportedRateIn500Kbps = SupRate[idx] & 0x7f; } for (idx=0; idx<ExtRateLen; idx++) { if (MaxSupportedRateIn500Kbps < (ExtRate[idx] & 0x7f)) MaxSupportedRateIn500Kbps = ExtRate[idx] & 0x7f; } pEntry = MacTableLookup(pAd, Addr2); if ((ADHOC_ON(pAd) && (Elem->Wcid == RESERVED_WCID)) || (pEntry && ((pEntry->LastBeaconRxTime + ADHOC_ENTRY_BEACON_LOST_TIME) < Now))) { if (pEntry == NULL) pEntry = MacTableInsertEntry(pAd, Addr2, BSS0, FALSE); if (StaAddMacTableEntry(pAd, pEntry, MaxSupportedRateIn500Kbps, &HtCapability, HtCapabilityLen, &AddHtInfo, AddHtInfoLen, CapabilityInfo) == FALSE) { DBGPRINT(RT_DEBUG_TRACE, ("ADHOC - Add Entry failed.\n")); return; } if (pEntry && (Elem->Wcid == RESERVED_WCID)) { idx = pAd->StaCfg.DefaultKeyId; RTMP_STA_SECURITY_INFO_ADD(pAd, BSS0, idx, pEntry); } } if (pEntry && pEntry->ValidAsCLI) pEntry->LastBeaconRxTime = Now; if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED)) { OPSTATUS_SET_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED); pAd->IndicateMediaState = NdisMediaStateConnected; RTMP_IndicateMediaState(pAd); pAd->ExtraInfo = GENERAL_LINK_UP; AsicSetBssid(pAd, pAd->CommonCfg.Bssid); Bssidx = BssTableSearch(&pAd->ScanTab, Bssid, Channel); if (Bssidx == BSS_NOT_FOUND) { Bssidx = BssTableSetEntry(pAd, &pAd->ScanTab, Bssid, Ssid, SsidLen, BssType, BeaconPeriod, &CfParm, AtimWin, CapabilityInfo, SupRate, SupRateLen, ExtRate, ExtRateLen, &HtCapability, &AddHtInfo, HtCapabilityLen, AddHtInfoLen, NewExtChannelOffset, Channel, RealRssi, TimeStamp, 0, &EdcaParm, &QosCapability, &QbssLoad, LenVIE, pVIE); } DBGPRINT(RT_DEBUG_TRACE, ("ADHOC fOP_STATUS_MEDIA_STATE_CONNECTED.\n")); } } if (INFRA_ON(pAd)) { BOOLEAN bUseShortSlot, bUseBGProtection; bUseShortSlot = CAP_IS_SHORT_SLOT(CapabilityInfo); if (bUseShortSlot != OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_SHORT_SLOT_INUSED)) AsicSetSlotTime(pAd, bUseShortSlot); bUseBGProtection = (pAd->CommonCfg.UseBGProtection == 1) || ((pAd->CommonCfg.UseBGProtection == 0) && ERP_IS_USE_PROTECTION(Erp)); if (pAd->CommonCfg.Channel > 14) bUseBGProtection = FALSE; if (bUseBGProtection != OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED)) { if (bUseBGProtection) { OPSTATUS_SET_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED); AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, (OFDMSETPROTECT|CCKSETPROTECT|ALLN_SETPROTECT),FALSE,(pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent == 1)); } else { OPSTATUS_CLEAR_FLAG(pAd, fOP_STATUS_BG_PROTECTION_INUSED); AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, (OFDMSETPROTECT|CCKSETPROTECT|ALLN_SETPROTECT),TRUE,(pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent == 1)); } DBGPRINT(RT_DEBUG_WARN, ("SYNC - AP changed B/G protection to %d\n", bUseBGProtection)); } #ifdef DOT11_N_SUPPORT if ((AddHtInfoLen != 0) && ((AddHtInfo.AddHtInfo2.OperaionMode != pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode) || (AddHtInfo.AddHtInfo2.NonGfPresent != pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent))) { pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent = AddHtInfo.AddHtInfo2.NonGfPresent; pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode = AddHtInfo.AddHtInfo2.OperaionMode; if (pAd->MlmeAux.AddHtInfo.AddHtInfo2.NonGfPresent == 1) { AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, FALSE, TRUE); } else AsicUpdateProtect(pAd, pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode, ALLN_SETPROTECT, FALSE, FALSE); DBGPRINT(RT_DEBUG_TRACE, ("SYNC - AP changed N OperaionMode to %d\n", pAd->MlmeAux.AddHtInfo.AddHtInfo2.OperaionMode)); } #endif if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_SHORT_PREAMBLE_INUSED) && ERP_IS_USE_BARKER_PREAMBLE(Erp)) { MlmeSetTxPreamble(pAd, Rt802_11PreambleLong); DBGPRINT(RT_DEBUG_TRACE, ("SYNC - AP forced to use LONG preamble\n")); } if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED) && (EdcaParm.bValid == TRUE) && (EdcaParm.EdcaUpdateCount != pAd->CommonCfg.APEdcaParm.EdcaUpdateCount)) { DBGPRINT(RT_DEBUG_TRACE, ("SYNC - AP change EDCA parameters(from %d to %d)\n", pAd->CommonCfg.APEdcaParm.EdcaUpdateCount, EdcaParm.EdcaUpdateCount)); AsicSetEdcaParm(pAd, &EdcaParm); } NdisMoveMemory(&pAd->CommonCfg.APQbssLoad, &QbssLoad, sizeof(QBSS_LOAD_PARM)); NdisMoveMemory(&pAd->CommonCfg.APQosCapability, &QosCapability, sizeof(QOS_CAPABILITY_PARM)); } if ((INFRA_ON(pAd) && (pAd->StaCfg.Psm == PWR_SAVE)) || (pAd->CommonCfg.bAPSDForcePowerSave)) { UCHAR FreeNumber; if (MessageToMe) { #ifdef RTMP_MAC_PCI if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_PCIE_DEVICE)) { if (pAd->Antenna.field.RxPath > 1) RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, pAd->StaCfg.BBPR3); } #endif if (pAd->CommonCfg.bAPSDCapable && pAd->CommonCfg.APEdcaParm.bAPSDCapable && pAd->CommonCfg.bAPSDAC_BE && pAd->CommonCfg.bAPSDAC_BK && pAd->CommonCfg.bAPSDAC_VI && pAd->CommonCfg.bAPSDAC_VO) { pAd->CommonCfg.bNeedSendTriggerFrame = TRUE; } else RTMP_PS_POLL_ENQUEUE(pAd); } else if (BcastFlag && (DtimCount == 0) && OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM)) { #ifdef RTMP_MAC_PCI if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_PCIE_DEVICE)) { if (pAd->Antenna.field.RxPath > 1) RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, pAd->StaCfg.BBPR3); } #endif } else if ((pAd->TxSwQueue[QID_AC_BK].Number != 0) || (pAd->TxSwQueue[QID_AC_BE].Number != 0) || (pAd->TxSwQueue[QID_AC_VI].Number != 0) || (pAd->TxSwQueue[QID_AC_VO].Number != 0) || (RTMPFreeTXDRequest(pAd, QID_AC_BK, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) || (RTMPFreeTXDRequest(pAd, QID_AC_BE, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) || (RTMPFreeTXDRequest(pAd, QID_AC_VI, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) || (RTMPFreeTXDRequest(pAd, QID_AC_VO, TX_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS) || (RTMPFreeTXDRequest(pAd, QID_MGMT, MGMT_RING_SIZE - 1, &FreeNumber) != NDIS_STATUS_SUCCESS)) { #ifdef RTMP_MAC_PCI if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_PCIE_DEVICE)) { if (pAd->Antenna.field.RxPath > 1) RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R3, pAd->StaCfg.BBPR3); } #endif } else { if ((pAd->CommonCfg.bACMAPSDTr[QID_AC_VO]) || (pAd->CommonCfg.bACMAPSDTr[QID_AC_VI]) || (pAd->CommonCfg.bACMAPSDTr[QID_AC_BK]) || (pAd->CommonCfg.bACMAPSDTr[QID_AC_BE])) { } else { USHORT NextDtim = DtimCount; if (NextDtim == 0) NextDtim = DtimPeriod; TbttNumToNextWakeUp = pAd->StaCfg.DefaultListenCount; if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_RECEIVE_DTIM) && (TbttNumToNextWakeUp > NextDtim)) TbttNumToNextWakeUp = NextDtim; if (!OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_DOZE)) { pAd->ThisTbttNumToNextWakeUp = TbttNumToNextWakeUp; AsicSleepThenAutoWakeup(pAd, pAd->ThisTbttNumToNextWakeUp); } } } } } } }
VOID PeerAddBAReqAction( IN PRTMP_ADAPTER pAd, IN MLME_QUEUE_ELEM *Elem) { // 7.4.4.1 //ULONG Idx; UCHAR Status = 1; UCHAR pAddr[6]; FRAME_ADDBA_RSP ADDframe; PUCHAR pOutBuffer = NULL; NDIS_STATUS NStatus; PFRAME_ADDBA_REQ pAddreqFrame = NULL; //UCHAR BufSize; ULONG FrameLen; PULONG ptemp; PMAC_TABLE_ENTRY pMacEntry; DBGPRINT(RT_DEBUG_TRACE, ("%s ==> (Wcid = %d)\n", __FUNCTION__, Elem->Wcid)); //hex_dump("AddBAReq", Elem->Msg, Elem->MsgLen); //ADDBA Request from unknown peer, ignore this. if (Elem->Wcid >= MAX_LEN_OF_MAC_TABLE) return; pMacEntry = &pAd->MacTab.Content[Elem->Wcid]; DBGPRINT(RT_DEBUG_TRACE,("BA - PeerAddBAReqAction----> \n")); ptemp = (PULONG)Elem->Msg; //DBGPRINT_RAW(RT_DEBUG_EMU, ("%08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x:: %08x\n", *(ptemp), *(ptemp+1), *(ptemp+2), *(ptemp+3), *(ptemp+4), *(ptemp+5), *(ptemp+6), *(ptemp+7), *(ptemp+8))); if (PeerAddBAReqActionSanity(pAd, Elem->Msg, Elem->MsgLen, pAddr)) { if ((pAd->CommonCfg.bBADecline == FALSE) && IS_HT_STA(pMacEntry)) { pAddreqFrame = (PFRAME_ADDBA_REQ)(&Elem->Msg[0]); DBGPRINT(RT_DEBUG_OFF, ("Rcv Wcid(%d) AddBAReq\n", Elem->Wcid)); if (BARecSessionAdd(pAd, &pAd->MacTab.Content[Elem->Wcid], pAddreqFrame)) Status = 0; else Status = 38; // more parameters have invalid values } else { Status = 37; // the request has been declined. } } if (pAd->MacTab.Content[Elem->Wcid].ValidAsCLI) ASSERT(pAd->MacTab.Content[Elem->Wcid].Sst == SST_ASSOC); pAddreqFrame = (PFRAME_ADDBA_REQ)(&Elem->Msg[0]); // 2. Always send back ADDBA Response NStatus = MlmeAllocateMemory(pAd, &pOutBuffer); //Get an unused nonpaged memory if (NStatus != NDIS_STATUS_SUCCESS) { DBGPRINT(RT_DEBUG_TRACE,("ACTION - PeerBAAction() allocate memory failed \n")); return; } NdisZeroMemory(&ADDframe, sizeof(FRAME_ADDBA_RSP)); // 2-1. Prepare ADDBA Response frame. #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { if (ADHOC_ON(pAd)) ActHeaderInit(pAd, &ADDframe.Hdr, pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid); else #ifdef QOS_DLS_SUPPORT if (pAd->MacTab.Content[Elem->Wcid].ValidAsDls) ActHeaderInit(pAd, &ADDframe.Hdr, pAddr, pAd->CurrentAddress, pAd->CommonCfg.Bssid); else #endif // QOS_DLS_SUPPORT // ActHeaderInit(pAd, &ADDframe.Hdr, pAd->CommonCfg.Bssid, pAd->CurrentAddress, pAddr); } #endif // CONFIG_STA_SUPPORT // ADDframe.Category = CATEGORY_BA; ADDframe.Action = ADDBA_RESP; ADDframe.Token = pAddreqFrame->Token; // What is the Status code?? need to check. ADDframe.StatusCode = Status; ADDframe.BaParm.BAPolicy = IMMED_BA; ADDframe.BaParm.AMSDUSupported = 0; ADDframe.BaParm.TID = pAddreqFrame->BaParm.TID; ADDframe.BaParm.BufSize = min(((UCHAR)pAddreqFrame->BaParm.BufSize), (UCHAR)pAd->CommonCfg.BACapability.field.RxBAWinLimit); if (ADDframe.BaParm.BufSize == 0) { ADDframe.BaParm.BufSize = 64; } ADDframe.TimeOutValue = 0; //pAddreqFrame->TimeOutValue; *(USHORT *)(&ADDframe.BaParm) = cpu2le16(*(USHORT *)(&ADDframe.BaParm)); ADDframe.StatusCode = cpu2le16(ADDframe.StatusCode); ADDframe.TimeOutValue = cpu2le16(ADDframe.TimeOutValue); MakeOutgoingFrame(pOutBuffer, &FrameLen, sizeof(FRAME_ADDBA_RSP), &ADDframe, END_OF_ARGS); MiniportMMRequest(pAd, QID_AC_BE, pOutBuffer, FrameLen); MlmeFreeMemory(pAd, pOutBuffer); DBGPRINT(RT_DEBUG_TRACE, ("%s(%d): TID(%d), BufSize(%d) <== \n", __FUNCTION__, Elem->Wcid, ADDframe.BaParm.TID, ADDframe.BaParm.BufSize)); }
/* ========================================================================== Description: IRQL = DISPATCH_LEVEL ========================================================================== */ VOID PeerDeauthAction( IN PRTMP_ADAPTER pAd, IN PMLME_QUEUE_ELEM Elem) { UCHAR Addr1[MAC_ADDR_LEN]; UCHAR Addr2[MAC_ADDR_LEN]; UCHAR Addr3[MAC_ADDR_LEN]; USHORT Reason; BOOLEAN bDoIterate = FALSE; if (PeerDeauthSanity(pAd, Elem->Msg, Elem->MsgLen, Addr1, Addr2, Addr3, &Reason)) { if (INFRA_ON(pAd) && (MAC_ADDR_EQUAL(Addr1, pAd->CurrentAddress) || MAC_ADDR_EQUAL(Addr1, BROADCAST_ADDR)) && MAC_ADDR_EQUAL(Addr2, pAd->CommonCfg.Bssid) && MAC_ADDR_EQUAL(Addr3, pAd->CommonCfg.Bssid) ) { DBGPRINT(RT_DEBUG_TRACE,("AUTH_RSP - receive DE-AUTH from our AP (Reason=%d)\n", Reason)); if (Reason == REASON_4_WAY_TIMEOUT) RTMPSendWirelessEvent(pAd, IW_PAIRWISE_HS_TIMEOUT_EVENT_FLAG, NULL, 0, 0); if (Reason == REASON_GROUP_KEY_HS_TIMEOUT) RTMPSendWirelessEvent(pAd, IW_GROUP_HS_TIMEOUT_EVENT_FLAG, NULL, 0, 0); #ifdef WAPI_SUPPORT WAPI_InternalCmdAction(pAd, pAd->StaCfg.AuthMode, BSS0, Addr2, WAI_MLME_DISCONNECT); #endif // WAPI_SUPPORT // #ifdef NATIVE_WPA_SUPPLICANT_SUPPORT RtmpOSWrielessEventSend(pAd->net_dev, RT_WLAN_EVENT_CGIWAP, -1, NULL, NULL, 0); #endif // NATIVE_WPA_SUPPLICANT_SUPPORT // // send wireless event - for deauthentication RTMPSendWirelessEvent(pAd, IW_DEAUTH_EVENT_FLAG, NULL, BSS0, 0); #ifdef WPA_SUPPLICANT_SUPPORT if ((pAd->StaCfg.WpaSupplicantUP != WPA_SUPPLICANT_DISABLE) && (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2) && (pAd->StaCfg.PortSecured == WPA_802_1X_PORT_SECURED)) pAd->StaCfg.bLostAp = TRUE; #endif // WPA_SUPPLICANT_SUPPORT // /* Some customer would set AP1 & AP2 same SSID, AuthMode & EncrypType but different WPAPSK, therefore we need to do iterate here. */ if ((pAd->StaCfg.PortSecured == WPA_802_1X_PORT_NOT_SECURED) && ((pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPAPSK) || (pAd->StaCfg.AuthMode == Ndis802_11AuthModeWPA2PSK)) #ifdef WSC_STA_SUPPORT && (pAd->StaCfg.WscControl.WscState < WSC_STATE_LINK_UP) #endif // WSC_STA_SUPPORT // ) bDoIterate = TRUE; LinkDown(pAd, TRUE); if (bDoIterate) { pAd->MlmeAux.BssIdx++; IterateOnBssTab(pAd); } } #ifdef ADHOC_WPA2PSK_SUPPORT else if (ADHOC_ON(pAd) && (MAC_ADDR_EQUAL(Addr1, pAd->CurrentAddress) || MAC_ADDR_EQUAL(Addr1, BROADCAST_ADDR))) { MAC_TABLE_ENTRY *pEntry; pEntry = MacTableLookup(pAd, Addr2); if (pEntry && IS_ENTRY_CLIENT(pEntry)) MacTableDeleteEntry(pAd, pEntry->Aid, pEntry->Addr); DBGPRINT(RT_DEBUG_TRACE,("AUTH_RSP - receive DE-AUTH from %02x:%02x:%02x:%02x:%02x:%02x \n", PRINT_MAC(Addr2))); } #endif // ADHOC_WPA2PSK_SUPPORT // } else { DBGPRINT(RT_DEBUG_TRACE,("AUTH_RSP - PeerDeauthAction() sanity check fail\n")); } }
static INT scan_ch_restore(RTMP_ADAPTER *pAd, UCHAR OpMode) { #ifdef CONFIG_STA_SUPPORT USHORT Status; #endif /* CONFIG_STA_SUPPORT */ INT bw, ch; if (pAd->CommonCfg.BBPCurrentBW != pAd->hw_cfg.bbp_bw) { rtmp_bbp_set_bw(pAd, pAd->hw_cfg.bbp_bw); AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel); ch = pAd->CommonCfg.CentralChannel; } else { AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.Channel); ch = pAd->CommonCfg.Channel; } switch(pAd->CommonCfg.BBPCurrentBW) { case BW_80: bw = 80; break; case BW_40: bw = 40; break; case BW_10: bw = 10; break; case BW_20: default: bw =20; break; } DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to %dMHz channel %d, Total BSS[%02d]\n", bw, ch, pAd->ScanTab.BssNr)); #ifdef CONFIG_STA_SUPPORT if (OpMode == OPMODE_STA) { /* If all peer Ad-hoc clients leave, driver would do LinkDown and LinkUp. In LinkUp, CommonCfg.Ssid would copy SSID from MlmeAux. To prevent SSID is zero or wrong in Beacon, need to recover MlmeAux.SSID here. */ if (ADHOC_ON(pAd)) { NdisZeroMemory(pAd->MlmeAux.Ssid, MAX_LEN_OF_SSID); pAd->MlmeAux.SsidLen = pAd->CommonCfg.SsidLen; NdisMoveMemory(pAd->MlmeAux.Ssid, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen); } /* To prevent data lost. Send an NULL data with turned PSM bit on to current associated AP before SCAN progress. Now, we need to send an NULL data with turned PSM bit off to AP, when scan progress done */ if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) && (INFRA_ON(pAd))) { RTMPSendNullFrame(pAd, pAd->CommonCfg.TxRate, (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED) ? TRUE:FALSE), pAd->CommonCfg.bAPSDForcePowerSave ? PWR_SAVE : pAd->StaCfg.Psm); DBGPRINT(RT_DEBUG_TRACE, ("%s -- Send null frame\n", __FUNCTION__)); } #ifdef RT_CFG80211_SUPPORT if (pAd->ApCfg.ApCliTab[MAIN_MBSSID].Valid && RTMP_CFG80211_VIF_P2P_CLI_ON(pAd)) { DBGPRINT(RT_DEBUG_TRACE, ("CFG80211_NULL: PWR_ACTIVE SCAN_END\n")); RT_CFG80211_P2P_CLI_SEND_NULL_FRAME(pAd, PWR_ACTIVE); } #endif /* RT_CFG80211_SUPPORT */ /* keep the latest scan channel, could be 0 for scan complete, or other channel*/ pAd->StaCfg.LastScanChannel = pAd->MlmeAux.Channel; pAd->StaCfg.ScanChannelCnt = 0; /* Suspend scanning and Resume TxData for Fast Scanning*/ if ((pAd->MlmeAux.Channel != 0) && (pAd->StaCfg.bImprovedScan)) /* it is scan pending*/ { pAd->Mlme.SyncMachine.CurrState = SCAN_PENDING; Status = MLME_SUCCESS; DBGPRINT(RT_DEBUG_WARN, ("bFastRoamingScan ~~~ Get back to send data ~~~\n")); RTMPResumeMsduTransmission(pAd); } else { pAd->StaCfg.BssNr = pAd->ScanTab.BssNr; pAd->StaCfg.bImprovedScan = FALSE; pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE; Status = MLME_SUCCESS; MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_SCAN_CONF, 2, &Status, 0); RTMP_MLME_HANDLER(pAd); } } #endif /* CONFIG_STA_SUPPORT */ #ifdef CONFIG_AP_SUPPORT if (OpMode == OPMODE_AP) { #ifdef P2P_APCLI_SUPPORT /* P2P CLIENT in WSC Scan or Re-Connect scanning. */ if (P2P_CLI_ON(pAd) && (ApScanRunning(pAd) == TRUE)) { /*MlmeEnqueue(pAd, APCLI_CTRL_STATE_MACHINE, APCLI_CTRL_JOIN_REQ_TIMEOUT, 0, NULL, 0);*/ DBGPRINT(RT_DEBUG_INFO, ("%s:: Scan Done! reset APCLI CTRL State Machine!\n", __FUNCTION__)); pAd->ApCfg.ApCliTab[0].CtrlCurrState = APCLI_CTRL_DISCONNECTED; } #endif /* P2P_APCLI_SUPPORT */ pAd->Mlme.ApSyncMachine.CurrState = AP_SYNC_IDLE; RTMPResumeMsduTransmission(pAd); /* iwpriv set auto channel selection*/ /* scanned all channels*/ if (pAd->ApCfg.bAutoChannelAtBootup==TRUE) { pAd->CommonCfg.Channel = SelectBestChannel(pAd, pAd->ApCfg.AutoChannelAlg); pAd->ApCfg.bAutoChannelAtBootup = FALSE; #ifdef DOT11_N_SUPPORT N_ChannelCheck(pAd); #endif /* DOT11_N_SUPPORT */ APStop(pAd); APStartUp(pAd); } if (!((pAd->CommonCfg.Channel > 14) && (pAd->CommonCfg.bIEEE80211H == TRUE))) AsicEnableBssSync(pAd); } #endif /* CONFIG_AP_SUPPORT */ return TRUE; }
/* ========================================================================== Description: Scan next channel ========================================================================== */ VOID ScanNextChannel( IN PRTMP_ADAPTER pAd) { HEADER_802_11 Hdr80211; PUCHAR pOutBuffer = NULL; NDIS_STATUS NStatus; ULONG FrameLen = 0; UCHAR SsidLen = 0, ScanType = pAd->MlmeAux.ScanType, BBPValue = 0; #ifdef CONFIG_STA_SUPPORT USHORT Status; #endif // CONFIG_STA_SUPPORT // UINT ScanTimeIn5gChannel = SHORT_CHANNEL_TIME; BOOLEAN ScanPending = FALSE; #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { if (MONITOR_ON(pAd)) return; } ScanPending = ((pAd->StaCfg.bImprovedScan) && (pAd->StaCfg.ScanChannelCnt>=7)); #endif // CONFIG_STA_SUPPORT // #ifdef RALINK_ATE // Nothing to do in ATE mode. if (ATE_ON(pAd)) return; #endif // RALINK_ATE // if ((pAd->MlmeAux.Channel == 0) || ScanPending) { if ((pAd->CommonCfg.BBPCurrentBW == BW_40) #ifdef CONFIG_STA_SUPPORT && (INFRA_ON(pAd) || ADHOC_ON(pAd) || (pAd->OpMode == OPMODE_AP)) #endif // CONFIG_STA_SUPPORT // ) { AsicSwitchChannel(pAd, pAd->CommonCfg.CentralChannel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.CentralChannel); RTMP_BBP_IO_READ8_BY_REG_ID(pAd, BBP_R4, &BBPValue); BBPValue &= (~0x18); BBPValue |= 0x10; RTMP_BBP_IO_WRITE8_BY_REG_ID(pAd, BBP_R4, BBPValue); DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to 40MHz channel %d, Total BSS[%02d]\n",pAd->CommonCfg.CentralChannel, pAd->ScanTab.BssNr)); } else { AsicSwitchChannel(pAd, pAd->CommonCfg.Channel, FALSE); AsicLockChannel(pAd, pAd->CommonCfg.Channel); DBGPRINT(RT_DEBUG_TRACE, ("SYNC - End of SCAN, restore to channel %d, Total BSS[%02d]\n",pAd->CommonCfg.Channel, pAd->ScanTab.BssNr)); } #ifdef CONFIG_STA_SUPPORT IF_DEV_CONFIG_OPMODE_ON_STA(pAd) { /* If all peer Ad-hoc clients leave, driver would do LinkDown and LinkUp. In LinkUp, CommonCfg.Ssid would copy SSID from MlmeAux. To prevent SSID is zero or wrong in Beacon, need to recover MlmeAux.SSID here. */ if (ADHOC_ON(pAd)) { NdisZeroMemory(pAd->MlmeAux.Ssid, MAX_LEN_OF_SSID); pAd->MlmeAux.SsidLen = pAd->CommonCfg.SsidLen; NdisMoveMemory(pAd->MlmeAux.Ssid, pAd->CommonCfg.Ssid, pAd->CommonCfg.SsidLen); } // // To prevent data lost. // Send an NULL data with turned PSM bit on to current associated AP before SCAN progress. // Now, we need to send an NULL data with turned PSM bit off to AP, when scan progress done // if (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_MEDIA_STATE_CONNECTED) && (INFRA_ON(pAd))) { RTMPSendNullFrame(pAd, pAd->CommonCfg.TxRate, (OPSTATUS_TEST_FLAG(pAd, fOP_STATUS_WMM_INUSED) ? TRUE:FALSE)); DBGPRINT(RT_DEBUG_TRACE, ("%s -- Send PSM Data frame\n", __FUNCTION__)); } // keep the latest scan channel, could be 0 for scan complete, or other channel pAd->StaCfg.LastScanChannel = pAd->MlmeAux.Channel; pAd->StaCfg.ScanChannelCnt = 0; // Suspend scanning and Resume TxData for Fast Scanning if ((pAd->MlmeAux.Channel != 0) && (pAd->StaCfg.bImprovedScan)) // it is scan pending { pAd->Mlme.SyncMachine.CurrState = SCAN_PENDING; Status = MLME_SUCCESS; DBGPRINT(RT_DEBUG_WARN, ("bFastRoamingScan ~~~~~~~~~~~~~ Get back to send data ~~~~~~~~~~~~~\n")); RTMPResumeMsduTransmission(pAd); } else { pAd->StaCfg.BssNr = pAd->ScanTab.BssNr; pAd->StaCfg.bImprovedScan = FALSE; pAd->Mlme.SyncMachine.CurrState = SYNC_IDLE; Status = MLME_SUCCESS; MlmeEnqueue(pAd, MLME_CNTL_STATE_MACHINE, MT2_SCAN_CONF, 2, &Status, 0); RTMPSendWirelessEvent(pAd, IW_SCAN_COMPLETED_EVENT_FLAG, NULL, BSS0, 0); #ifdef WPA_SUPPLICANT_SUPPORT RtmpOSWrielessEventSend(pAd, SIOCGIWSCAN, -1, NULL, NULL, 0); #endif // WPA_SUPPLICANT_SUPPORT // } #ifdef LINUX #ifdef RT_CFG80211_SUPPORT RTEnqueueInternalCmd(pAd, CMDTHREAD_SCAN_END, NULL, 0); #endif // RT_CFG80211_SUPPORT // #endif // LINUX // } #endif // CONFIG_STA_SUPPORT // } else {