2 ** $Id: //Department/DaVinci/BRANCHES/MT6620_WIFI_DRIVER_V2_3/mgmt/rlm_obss.c#2 $
15 * 07 17 2012 yuche.tsai
17 * Compile no error before trial run.
21 * Avoid possible OBSS scan when BSS is switched
25 * Add RLM and CNM debug message for XLOG
28 * [WCXRP00001058] [All Wi-Fi][Driver] Fix sta_rec's phyTypeSet and OBSS scan in AP mode
29 * Regulation class is changed to 81 in 20_40_coexistence action frame
32 * [WCXRP00000634] [MT6620 Wi-Fi][Driver][FW] 2nd BSS will not support 40MHz bandwidth for concurrency
36 * [WCXRP00000606] [MT6620 Wi-Fi][Driver][FW] Fix klocwork warning
40 * [WCXRP00000384] [MT6620 Wi-Fi][Driver][FW] Handle 20/40 action frame in AP mode and stop ampdu timer when sta_rec is freed
41 * Process received 20/40 coexistence action frame for AP mode
44 * [WCXRP00000358] [MT6620 Wi-Fi][Driver] Provide concurrent information for each module
45 * Refine function when rcv a 20/40M public action frame
48 * [WCXRP00000354] [MT6620 Wi-Fi][Driver][FW] Follow NVRAM bandwidth setting
49 * Use SCO of BSS_INFO to replace user-defined setting variables
52 * [WCXRP00000354] [MT6620 Wi-Fi][Driver][FW] Follow NVRAM bandwidth setting
53 * User-defined bandwidth is for 2.4G and 5G individually
56 * [WCXRP00000052] [MT6620 Wi-Fi][Driver] Eliminate Linux Compile Warning
57 * use definition macro to replace hard-coded constant
61 * Change conditional compiling options for BOW
65 * Always update Beacon content if FW sync OBSS info
69 * Support RLM initail channel of Ad-hoc, P2P and BOW
73 * Migrate RLM code to host from FW
75 * 07 26 2010 yuche.tsai
77 * Fix compile error while enabling WiFi Direct function.
79 * 07 21 2010 yuche.tsai
81 * Add P2P Scan & Scan Result Parsing & Saving.
85 * [WPD00003833] [MT6620 and MT5931] Driver migration - move to new repository.
88 * [WPD00003841][LITE Driver] Migrate RLM/CNM to host driver
89 * Check draft RLM code for HT cap
92 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
93 * Process 20/40 coexistence public action frame in AP mode
96 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
97 * First draft support for 20/40M bandwidth for AP mode
100 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
101 * g_aprBssInfo[] depends on CFG_SUPPORT_P2P and CFG_SUPPORT_BOW
103 * 04 13 2010 cm.chang
104 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
105 * Add more ASSERT to check exception
107 * 04 07 2010 cm.chang
108 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
109 * Add virtual test for OBSS scan
111 * 03 30 2010 cm.chang
112 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
113 * Support 2.4G OBSS scan
115 * 03 03 2010 cm.chang
116 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
117 * To support CFG_SUPPORT_BCM_STP
119 * 02 13 2010 cm.chang
120 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
121 * Support PCO in STA mode
123 * 02 12 2010 cm.chang
124 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
125 * Use bss info array for concurrent handle
127 * 02 05 2010 kevin.huang
128 * [BORA00000603][WIFISYS] [New Feature] AAA Module Support
129 * Add AAA Module Support, Revise Net Type to Net Type Index for array lookup
131 * 01 25 2010 cm.chang
132 * [BORA00000018]Integrate WIFI part into BORA for the 1st time
133 * Support protection and bandwidth switch
136 /*******************************************************************************
137 * C O M P I L E R F L A G S
138 ********************************************************************************
141 /*******************************************************************************
142 * E X T E R N A L R E F E R E N C E S
143 ********************************************************************************
147 /*******************************************************************************
149 ********************************************************************************
152 /*******************************************************************************
154 ********************************************************************************
157 /*******************************************************************************
158 * P U B L I C D A T A
159 ********************************************************************************
162 /*******************************************************************************
163 * P R I V A T E D A T A
164 ********************************************************************************
167 /*******************************************************************************
169 ********************************************************************************
172 /*******************************************************************************
173 * F U N C T I O N D E C L A R A T I O N S
174 ********************************************************************************
176 static VOID
rlmObssScanTimeout(P_ADAPTER_T prAdapter
, UINT_32 u4Data
);
178 /*******************************************************************************
180 ********************************************************************************
183 /*----------------------------------------------------------------------------*/
191 /*----------------------------------------------------------------------------*/
192 VOID
rlmObssInit(P_ADAPTER_T prAdapter
)
194 P_BSS_INFO_T prBssInfo
;
197 RLM_NET_FOR_EACH(ucNetIdx
) {
198 prBssInfo
= &prAdapter
->rWifiVar
.arBssInfo
[ucNetIdx
];
201 cnmTimerInitTimer(prAdapter
, &prBssInfo
->rObssScanTimer
,
202 rlmObssScanTimeout
, (UINT_32
) prBssInfo
);
203 } /* end of RLM_NET_FOR_EACH */
206 /*----------------------------------------------------------------------------*/
214 /*----------------------------------------------------------------------------*/
215 BOOLEAN
rlmObssUpdateChnlLists(P_ADAPTER_T prAdapter
, P_SW_RFB_T prSwRfb
)
220 /*----------------------------------------------------------------------------*/
228 /*----------------------------------------------------------------------------*/
229 VOID
rlmObssScanDone(P_ADAPTER_T prAdapter
, P_MSG_HDR_T prMsgHdr
)
231 P_MSG_SCN_SCAN_DONE prScanDoneMsg
;
232 P_BSS_INFO_T prBssInfo
;
233 P_MSDU_INFO_T prMsduInfo
;
234 P_ACTION_20_40_COEXIST_FRAME prTxFrame
;
235 UINT_16 i
, u2PayloadLen
;
239 prScanDoneMsg
= (P_MSG_SCN_SCAN_DONE
) prMsgHdr
;
240 prBssInfo
= &prAdapter
->rWifiVar
.arBssInfo
[prScanDoneMsg
->ucNetTypeIndex
];
243 DBGLOG(RLM
, INFO
, ("OBSS Scan Done (NetIdx=%d, Mode=%d)\n",
244 prScanDoneMsg
->ucNetTypeIndex
, prBssInfo
->eCurrentOPMode
));
246 cnmMemFree(prAdapter
, prMsgHdr
);
248 #if CFG_ENABLE_WIFI_DIRECT
250 if ((prAdapter
->fgIsP2PRegistered
) &&
251 (IS_NET_ACTIVE(prAdapter
, prBssInfo
->ucNetTypeIndex
)) &&
252 (prBssInfo
->eCurrentOPMode
== OP_MODE_ACCESS_POINT
)) {
258 if (prBssInfo
->eCurrentOPMode
!= OP_MODE_INFRASTRUCTURE
||
259 !RLM_NET_PARAM_VALID(prBssInfo
) || prBssInfo
->u2ObssScanInterval
== 0) {
260 DBGLOG(RLM
, WARN
, ("OBSS Scan Done (NetIdx=%d) -- Aborted!!\n",
261 prBssInfo
->ucNetTypeIndex
));
265 /* To do: check 2.4G channel list to decide if obss mgmt should be
266 * sent to associated AP. Note: how to handle concurrent network?
267 * To do: invoke rlmObssChnlLevel() to decide if 20/40 BSS coexistence
268 * management frame is needed.
270 if ((prBssInfo
->auc2G_20mReqChnlList
[0] > 0 ||
271 prBssInfo
->auc2G_NonHtChnlList
[0] > 0) &&
272 (prMsduInfo
= (P_MSDU_INFO_T
) cnmMgtPktAlloc(prAdapter
,
273 MAC_TX_RESERVED_FIELD
+
274 PUBLIC_ACTION_MAX_LEN
)) != NULL
) {
276 DBGLOG(RLM
, INFO
, ("Send 20/40 coexistence mgmt(20mReq=%d, NonHt=%d)\n",
277 prBssInfo
->auc2G_20mReqChnlList
[0],
278 prBssInfo
->auc2G_NonHtChnlList
[0]));
280 prTxFrame
= (P_ACTION_20_40_COEXIST_FRAME
)
281 ((UINT_32
) (prMsduInfo
->prPacket
) + MAC_TX_RESERVED_FIELD
);
283 prTxFrame
->u2FrameCtrl
= MAC_FRAME_ACTION
;
284 COPY_MAC_ADDR(prTxFrame
->aucDestAddr
, prBssInfo
->aucBSSID
);
285 COPY_MAC_ADDR(prTxFrame
->aucSrcAddr
, prBssInfo
->aucOwnMacAddr
);
286 COPY_MAC_ADDR(prTxFrame
->aucBSSID
, prBssInfo
->aucBSSID
);
288 prTxFrame
->ucCategory
= CATEGORY_PUBLIC_ACTION
;
289 prTxFrame
->ucAction
= ACTION_PUBLIC_20_40_COEXIST
;
291 /* To do: find correct algorithm */
292 prTxFrame
->rBssCoexist
.ucId
= ELEM_ID_20_40_BSS_COEXISTENCE
;
293 prTxFrame
->rBssCoexist
.ucLength
= 1;
294 prTxFrame
->rBssCoexist
.ucData
=
295 (prBssInfo
->auc2G_20mReqChnlList
[0] > 0) ? BSS_COEXIST_20M_REQ
: 0;
297 u2PayloadLen
= 2 + 3;
299 if (prBssInfo
->auc2G_NonHtChnlList
[0] > 0) {
300 ASSERT(prBssInfo
->auc2G_NonHtChnlList
[0] <= CHNL_LIST_SZ_2G
);
302 prTxFrame
->rChnlReport
.ucId
= ELEM_ID_20_40_INTOLERANT_CHNL_REPORT
;
303 prTxFrame
->rChnlReport
.ucLength
= prBssInfo
->auc2G_NonHtChnlList
[0] + 1;
304 prTxFrame
->rChnlReport
.ucRegulatoryClass
= 81; /* 2.4GHz, ch1~13 */
305 for (i
= 0; i
< prBssInfo
->auc2G_NonHtChnlList
[0] &&
306 i
< CHNL_LIST_SZ_2G
; i
++) {
307 prTxFrame
->rChnlReport
.aucChannelList
[i
] =
308 prBssInfo
->auc2G_NonHtChnlList
[i
+ 1];
311 u2PayloadLen
+= IE_SIZE(&prTxFrame
->rChnlReport
);
313 ASSERT((WLAN_MAC_HEADER_LEN
+ u2PayloadLen
) <= PUBLIC_ACTION_MAX_LEN
);
315 /* Clear up channel lists in 2.4G band */
316 prBssInfo
->auc2G_20mReqChnlList
[0] = 0;
317 prBssInfo
->auc2G_NonHtChnlList
[0] = 0;
320 /* 4 Update information of MSDU_INFO_T */
321 prMsduInfo
->ucPacketType
= HIF_TX_PACKET_TYPE_MGMT
; /* Management frame */
322 prMsduInfo
->ucStaRecIndex
= prBssInfo
->prStaRecOfAP
->ucIndex
;
323 prMsduInfo
->ucNetworkType
= prBssInfo
->ucNetTypeIndex
;
324 prMsduInfo
->ucMacHeaderLength
= WLAN_MAC_MGMT_HEADER_LEN
;
325 prMsduInfo
->fgIs802_1x
= FALSE
;
326 prMsduInfo
->fgIs802_11
= TRUE
;
327 prMsduInfo
->u2FrameLength
= WLAN_MAC_MGMT_HEADER_LEN
+ u2PayloadLen
;
328 prMsduInfo
->ucTxSeqNum
= nicIncreaseTxSeqNum(prAdapter
);
329 prMsduInfo
->pfTxDoneHandler
= NULL
;
330 prMsduInfo
->fgIsBasicRate
= FALSE
;
332 /* 4 Enqueue the frame to send this action frame. */
333 nicTxEnqueueMsdu(prAdapter
, prMsduInfo
);
335 /* end of prMsduInfo != NULL */
336 if (prBssInfo
->u2ObssScanInterval
> 0) {
337 DBGLOG(RLM
, INFO
, ("Set OBSS timer (NetIdx=%d, %d sec)\n",
338 prBssInfo
->ucNetTypeIndex
, prBssInfo
->u2ObssScanInterval
));
340 cnmTimerStartTimer(prAdapter
, &prBssInfo
->rObssScanTimer
,
341 prBssInfo
->u2ObssScanInterval
* MSEC_PER_SEC
);
345 /*----------------------------------------------------------------------------*/
353 /*----------------------------------------------------------------------------*/
354 static VOID
rlmObssScanTimeout(P_ADAPTER_T prAdapter
, UINT_32 u4Data
)
356 P_BSS_INFO_T prBssInfo
;
358 prBssInfo
= (P_BSS_INFO_T
) u4Data
;
361 #if CFG_ENABLE_WIFI_DIRECT
363 if (prAdapter
->fgIsP2PRegistered
&&
364 (IS_NET_ACTIVE(prAdapter
, prBssInfo
->ucNetTypeIndex
)) &&
365 (prBssInfo
->eCurrentOPMode
== OP_MODE_ACCESS_POINT
)) {
367 prBssInfo
->fgObssActionForcedTo20M
= FALSE
;
369 /* Check if Beacon content need to be updated */
370 rlmUpdateParamsForAP(prAdapter
, prBssInfo
, FALSE
);
374 #endif /* end of CFG_ENABLE_WIFI_DIRECT */
378 if (prBssInfo
->eCurrentOPMode
!= OP_MODE_INFRASTRUCTURE
||
379 !RLM_NET_PARAM_VALID(prBssInfo
) || prBssInfo
->u2ObssScanInterval
== 0) {
380 DBGLOG(RLM
, WARN
, ("OBSS Scan timeout (NetIdx=%d) -- Aborted!!\n",
381 prBssInfo
->ucNetTypeIndex
));
385 rlmObssTriggerScan(prAdapter
, prBssInfo
);
388 /*----------------------------------------------------------------------------*/
396 /*----------------------------------------------------------------------------*/
397 VOID
rlmObssTriggerScan(P_ADAPTER_T prAdapter
, P_BSS_INFO_T prBssInfo
)
399 P_MSG_SCN_SCAN_REQ prScanReqMsg
;
403 prScanReqMsg
= (P_MSG_SCN_SCAN_REQ
)
404 cnmMemAlloc(prAdapter
, RAM_TYPE_MSG
, sizeof(MSG_SCN_SCAN_REQ
));
405 ASSERT(prScanReqMsg
);
408 DBGLOG(RLM
, WARN
, ("No buf for OBSS scan (NetIdx=%d)!!\n",
409 prBssInfo
->ucNetTypeIndex
));
411 cnmTimerStartTimer(prAdapter
, &prBssInfo
->rObssScanTimer
,
412 prBssInfo
->u2ObssScanInterval
* MSEC_PER_SEC
);
416 /* It is ok that ucSeqNum is set to fixed value because the same network
417 * OBSS scan interval is limited to OBSS_SCAN_MIN_INTERVAL (min 10 sec)
418 * and scan module don't care seqNum of OBSS scanning
420 prScanReqMsg
->rMsgHdr
.eMsgId
= MID_RLM_SCN_SCAN_REQ
;
421 prScanReqMsg
->ucSeqNum
= 0x33;
422 prScanReqMsg
->ucNetTypeIndex
= prBssInfo
->ucNetTypeIndex
;
423 prScanReqMsg
->eScanType
= SCAN_TYPE_ACTIVE_SCAN
;
424 prScanReqMsg
->ucSSIDType
= SCAN_REQ_SSID_WILDCARD
;
425 prScanReqMsg
->ucSSIDLength
= 0;
426 prScanReqMsg
->eScanChannel
= SCAN_CHANNEL_2G4
;
427 prScanReqMsg
->u2IELen
= 0;
429 mboxSendMsg(prAdapter
, MBOX_ID_0
, (P_MSG_HDR_T
) prScanReqMsg
, MSG_SEND_METHOD_BUF
);
431 DBGLOG(RLM
, INFO
, ("Timeout to trigger OBSS scan (NetIdx=%d)!!\n",
432 prBssInfo
->ucNetTypeIndex
));