blob: 90cc45201f2080438a443f99591e1d5791a9cc2c [file] [log] [blame]
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001/*
Himanshu Agarwalfee2e362018-01-18 20:26:35 +05302 * Copyright (c) 2012-2018 The Linux Foundation. All rights reserved.
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08003 *
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08004 * Permission to use, copy, modify, and/or distribute this software for
5 * any purpose with or without fee is hereby granted, provided that the
6 * above copyright notice and this permission notice appear in all
7 * copies.
8 *
9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
10 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
11 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
12 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
13 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
14 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
15 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
16 * PERFORMANCE OF THIS SOFTWARE.
17 */
18
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080019/*===========================================================================
20
Anurag Chouhan6d760662016-02-20 16:05:43 +053021 s a p C h S e l e c t . C
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080022 OVERVIEW:
23
24 This software unit holds the implementation of the WLAN SAP modules
25 functions for channel selection.
26
27 DEPENDENCIES:
28
29 Are listed for each API below.
30 ===========================================================================*/
31
32/*--------------------------------------------------------------------------
33 Include Files
34 ------------------------------------------------------------------------*/
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +053035#include "qdf_trace.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080036#include "csr_api.h"
37#include "sme_api.h"
38#include "sap_ch_select.h"
39#include "sap_internal.h"
40#ifdef ANI_OS_TYPE_QNX
41#include "stdio.h"
42#endif
43#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
44#include "lim_utils.h"
45#include "parser_api.h"
46#endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
Deepthi Gowri48b89332016-08-30 18:43:05 +053047#include "cds_utils.h"
Yuanyuan Liu0e0aa932016-05-12 10:17:58 -070048#include "pld_common.h"
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -070049#include "wlan_reg_services_api.h"
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080050
51/*--------------------------------------------------------------------------
52 Function definitions
53 --------------------------------------------------------------------------*/
54
55/*--------------------------------------------------------------------------
56 Defines
57 --------------------------------------------------------------------------*/
58#define SAP_DEBUG
59
60#define IS_RSSI_VALID(extRssi, rssi) \
61 ( \
62 ((extRssi < rssi) ? true : false) \
63 )
64
Jeff Johnsone13d8062017-09-28 06:54:55 -070065#define SET_ACS_BAND(acs_band, sap_ctx) \
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080066{ \
Jeff Johnsone13d8062017-09-28 06:54:55 -070067 if (sap_ctx->acs_cfg->start_ch <= 14 && \
68 sap_ctx->acs_cfg->end_ch <= 14) \
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080069 acs_band = eCSR_DOT11_MODE_11g; \
Jeff Johnsone13d8062017-09-28 06:54:55 -070070 else if (sap_ctx->acs_cfg->start_ch >= 14)\
Prakash Dhavali7090c5f2015-11-02 17:55:19 -080071 acs_band = eCSR_DOT11_MODE_11a; \
72 else \
73 acs_band = eCSR_DOT11_MODE_abg; \
74}
75
gaoleze5108942017-03-31 16:56:42 +080076#define ACS_WEIGHT_AMOUNT_LOCAL 240
77
78#define ACS_WEIGHT_AMOUNT_CONFIG(weights) \
79 (((weights) & 0xf) + \
80 (((weights) & 0xf0) >> 4) + \
81 (((weights) & 0xf00) >> 8) + \
82 (((weights) & 0xf000) >> 12) + \
83 (((weights) & 0xf0000) >> 16) + \
84 (((weights) & 0xf00000) >> 20))
85
86/*
87 * LSH/RSH 4 to enhance the accurate since
88 * need to do modulation to ACS_WEIGHT_AMOUNT_LOCAL.
89 */
90#define ACS_WEIGHT_COMPUTE(weights, weight, factor, base) \
91 (((((((((weight) << 4) * ACS_WEIGHT_AMOUNT_LOCAL * (factor)) + \
92 (ACS_WEIGHT_AMOUNT_CONFIG((weights)) >> 1)) / \
93 ACS_WEIGHT_AMOUNT_CONFIG((weights))) + \
94 ((base) >> 1)) / (base)) + 8) >> 4)
95
96#define ACS_WEIGHT_CFG_TO_LOCAL(weights, weight) \
97 (((((((weight) << 4) * ACS_WEIGHT_AMOUNT_LOCAL) + \
98 (ACS_WEIGHT_AMOUNT_CONFIG((weights)) >> 1)) / \
99 ACS_WEIGHT_AMOUNT_CONFIG((weights))) + 8) >> 4)
100
101#define ACS_WEIGHT_SOFTAP_RSSI_CFG(weights) \
102 ((weights) & 0xf)
103
104#define ACS_WEIGHT_SOFTAP_COUNT_CFG(weights) \
105 (((weights) & 0xf0) >> 4)
106
107#define ACS_WEIGHT_SOFTAP_NOISE_FLOOR_CFG(weights) \
108 (((weights) & 0xf00) >> 8)
109
110#define ACS_WEIGHT_SOFTAP_CHANNEL_FREE_CFG(weights) \
111 (((weights) & 0xf000) >> 12)
112
113#define ACS_WEIGHT_SOFTAP_TX_POWER_RANGE_CFG(weights) \
114 (((weights) & 0xf0000) >> 16)
115
116#define ACS_WEIGHT_SOFTAP_TX_POWER_THROUGHPUT_CFG(weights) \
117 (((weights) & 0xf00000) >> 20)
118
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800119#ifdef FEATURE_WLAN_CH_AVOID
Amar Singhalb8d4f152016-02-10 10:21:43 -0800120sapSafeChannelType safe_channels[NUM_CHANNELS] = {
121 {1, true},
122 {2, true},
123 {3, true},
124 {4, true},
125 {5, true},
126 {6, true},
127 {7, true},
128 {8, true},
129 {9, true},
130 {10, true},
131 {11, true},
132 {12, true},
133 {13, true},
134 {14, true},
135 {36, true},
136 {40, true},
137 {44, true},
138 {48, true},
139 {52, true},
140 {56, true},
141 {60, true},
142 {64, true},
143 {100, true},
144 {104, true},
145 {108, true},
146 {112, true},
147 {116, true},
148 {120, true},
149 {124, true},
150 {128, true},
151 {132, true},
152 {136, true},
153 {140, true},
154 {144, true},
155 {149, true},
156 {153, true},
157 {157, true},
158 {161, true},
159 {165, true},
Kiran Kumar Lokere1a43bcf2018-05-15 15:51:58 -0700160 {169, true},
161 {173, true},
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800162};
163#endif
164
165typedef struct {
166 uint16_t chStartNum;
167 uint32_t weight;
168} sapAcsChannelInfo;
169
170sapAcsChannelInfo acs_ht40_channels5_g[] = {
171 {36, SAP_ACS_WEIGHT_MAX},
172 {44, SAP_ACS_WEIGHT_MAX},
173 {52, SAP_ACS_WEIGHT_MAX},
174 {60, SAP_ACS_WEIGHT_MAX},
175 {100, SAP_ACS_WEIGHT_MAX},
176 {108, SAP_ACS_WEIGHT_MAX},
177 {116, SAP_ACS_WEIGHT_MAX},
178 {124, SAP_ACS_WEIGHT_MAX},
179 {132, SAP_ACS_WEIGHT_MAX},
180 {140, SAP_ACS_WEIGHT_MAX},
181 {149, SAP_ACS_WEIGHT_MAX},
182 {157, SAP_ACS_WEIGHT_MAX},
183};
184
185sapAcsChannelInfo acs_ht80_channels[] = {
186 {36, SAP_ACS_WEIGHT_MAX},
187 {52, SAP_ACS_WEIGHT_MAX},
188 {100, SAP_ACS_WEIGHT_MAX},
189 {116, SAP_ACS_WEIGHT_MAX},
190 {132, SAP_ACS_WEIGHT_MAX},
191 {149, SAP_ACS_WEIGHT_MAX},
192};
193
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -0700194sapAcsChannelInfo acs_vht160_channels[] = {
195 {36, SAP_ACS_WEIGHT_MAX},
196 {100, SAP_ACS_WEIGHT_MAX},
197};
198
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800199sapAcsChannelInfo acs_ht40_channels24_g[] = {
200 {1, SAP_ACS_WEIGHT_MAX},
201 {2, SAP_ACS_WEIGHT_MAX},
202 {3, SAP_ACS_WEIGHT_MAX},
203 {4, SAP_ACS_WEIGHT_MAX},
204 {9, SAP_ACS_WEIGHT_MAX},
205};
206
207#define CHANNEL_165 165
208
209/* rssi discount for channels in PCL */
210#define PCL_RSSI_DISCOUNT 10
211
212#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
213/**
214 * sap_check_n_add_channel() - checks and add given channel in sap context's
215 * avoid_channels_info struct
216 * @sap_ctx: sap context.
217 * @new_channel: channel to be added to sap_ctx's avoid ch info
218 *
219 * sap_ctx contains sap_avoid_ch_info strcut containing the list of channels on
220 * which MDM device's AP with MCC was detected. This function will add channels
221 * to that list after checking for duplicates.
222 *
223 * Return: true: if channel was added or already present
224 * else false: if channel list was already full.
225 */
Tang Yingying523322d2017-01-17 23:28:43 +0800226static bool
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700227sap_check_n_add_channel(struct sap_context *sap_ctx,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800228 uint8_t new_channel)
229{
230 uint8_t i = 0;
231 struct sap_avoid_channels_info *ie_info =
232 &sap_ctx->sap_detected_avoid_ch_ie;
233
234 for (i = 0; i < sizeof(ie_info->channels); i++) {
235 if (ie_info->channels[i] == new_channel)
236 break;
237
238 if (ie_info->channels[i] == 0) {
239 ie_info->channels[i] = new_channel;
240 break;
241 }
242 }
243 if (i == sizeof(ie_info->channels))
244 return false;
245 else
246 return true;
247}
248/**
249 * sap_check_n_add_overlapped_chnls() - checks & add overlapped channels
250 * to primary channel in 2.4Ghz band.
251 * @sap_ctx: sap context.
252 * @primary_chnl: primary channel to be avoided.
253 *
254 * sap_ctx contains sap_avoid_ch_info struct containing the list of channels on
255 * which MDM device's AP with MCC was detected. This function will add channels
256 * to that list after checking for duplicates.
257 *
258 * Return: true: if channel was added or already present
259 * else false: if channel list was already full.
260 */
261static bool
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700262sap_check_n_add_overlapped_chnls(struct sap_context *sap_ctx,
263 uint8_t primary_channel)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800264{
265 uint8_t i = 0, j = 0, upper_chnl = 0, lower_chnl = 0;
266 struct sap_avoid_channels_info *ie_info =
267 &sap_ctx->sap_detected_avoid_ch_ie;
268 /*
269 * if primary channel less than channel 1 or out of 2g band then
270 * no further process is required. return true in this case.
271 */
272 if (primary_channel < CHANNEL_1 || primary_channel > CHANNEL_14)
273 return true;
274
275 /* lower channel is one channel right before primary channel */
276 lower_chnl = primary_channel - 1;
277 /* upper channel is one channel right after primary channel */
278 upper_chnl = primary_channel + 1;
279
280 /* lower channel needs to be non-zero, zero is not valid channel */
281 if (lower_chnl > (CHANNEL_1 - 1)) {
282 for (i = 0; i < sizeof(ie_info->channels); i++) {
283 if (ie_info->channels[i] == lower_chnl)
284 break;
285 if (ie_info->channels[i] == 0) {
286 ie_info->channels[i] = lower_chnl;
287 break;
288 }
289 }
290 }
291 /* upper channel needs to be atleast last channel in 2.4Ghz band */
292 if (upper_chnl < (CHANNEL_14 + 1)) {
293 for (j = 0; j < sizeof(ie_info->channels); j++) {
294 if (ie_info->channels[j] == upper_chnl)
295 break;
296 if (ie_info->channels[j] == 0) {
297 ie_info->channels[j] = upper_chnl;
298 break;
299 }
300 }
301 }
302 if (i == sizeof(ie_info->channels) || j == sizeof(ie_info->channels))
303 return false;
304 else
305 return true;
306}
307
308/**
309 * sap_process_avoid_ie() - processes the detected Q2Q IE
310 * context's avoid_channels_info struct
311 * @hal: hal handle
312 * @sap_ctx: sap context.
313 * @scan_result: scan results for ACS scan.
314 * @spect_info: spectrum weights array to update
315 *
316 * Detection of Q2Q IE indicates presence of another MDM device with its AP
317 * operating in MCC mode. This function parses the scan results and processes
318 * the Q2Q IE if found. It then extracts the channels and populates them in
319 * sap_ctx struct. It also increases the weights of those channels so that
320 * ACS logic will avoid those channels in its selection algorithm.
321 *
322 * Return: void
323 */
Tang Yingying523322d2017-01-17 23:28:43 +0800324static void sap_process_avoid_ie(tHalHandle hal,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700325 struct sap_context *sap_ctx,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800326 tScanResultHandle scan_result,
327 tSapChSelSpectInfo *spect_info)
328{
329 uint32_t total_ie_len = 0;
330 uint8_t *temp_ptr = NULL;
331 uint8_t i = 0;
332 struct sAvoidChannelIE *avoid_ch_ie;
333 tCsrScanResultInfo *node = NULL;
334 tpAniSirGlobal mac_ctx = NULL;
335 tSapSpectChInfo *spect_ch = NULL;
336
337 mac_ctx = PMAC_STRUCT(hal);
338 spect_ch = spect_info->pSpectCh;
339 node = sme_scan_result_get_first(hal, scan_result);
340
341 while (node) {
Abhishek Singh34a4d862016-10-26 16:01:51 +0530342 total_ie_len =
Jeff Johnson38e38a82017-10-06 10:32:31 -0700343 GET_IE_LEN_IN_BSS(node->BssDescriptor.length);
Naveen Rawat08db88f2017-09-08 15:07:48 -0700344 temp_ptr = wlan_get_vendor_ie_ptr_from_oui(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800345 SIR_MAC_QCOM_VENDOR_OUI,
346 SIR_MAC_QCOM_VENDOR_SIZE,
347 ((uint8_t *)&node->BssDescriptor.ieFields),
348 total_ie_len);
349
350 if (temp_ptr) {
351 avoid_ch_ie = (struct sAvoidChannelIE *)temp_ptr;
Will Huang55ba1042017-03-22 10:43:30 +0800352 if (avoid_ch_ie->type !=
353 QCOM_VENDOR_IE_MCC_AVOID_CH) {
354 node = sme_scan_result_get_next(hal,
355 scan_result);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800356 continue;
Will Huang55ba1042017-03-22 10:43:30 +0800357 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800358
359 sap_ctx->sap_detected_avoid_ch_ie.present = 1;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530360 QDF_TRACE(QDF_MODULE_ID_SAP,
361 QDF_TRACE_LEVEL_DEBUG,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800362 "Q2Q IE - avoid ch %d",
363 avoid_ch_ie->channel);
364 /* add this channel to to_avoid channel list */
365 sap_check_n_add_channel(sap_ctx,
366 avoid_ch_ie->channel);
367 sap_check_n_add_overlapped_chnls(sap_ctx,
368 avoid_ch_ie->channel);
369 /*
370 * Mark weight of these channel present in IE to MAX
371 * so that ACS logic will to avoid thse channels
372 */
373 for (i = 0; i < spect_info->numSpectChans; i++)
374 if (spect_ch[i].chNum == avoid_ch_ie->channel) {
375 /*
376 * weight is set more than max so that,
377 * in the case of other channels being
378 * assigned max weight due to noise,
379 * they may be preferred over channels
380 * with Q2Q IE.
381 */
382 spect_ch[i].weight = SAP_ACS_WEIGHT_MAX + 1;
383 spect_ch[i].weight_copy =
384 SAP_ACS_WEIGHT_MAX + 1;
385 break;
386 }
387 } /* if (temp_ptr) */
388 node = sme_scan_result_get_next(hal, scan_result);
389 }
390}
391#endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
392
393#ifdef FEATURE_WLAN_CH_AVOID
394/*==========================================================================
395 FUNCTION sap_update_unsafe_channel_list
396
397 DESCRIPTION
398 Function Undate unsafe channel list table
399
400 DEPENDENCIES
401 NA.
402
403 IN
404 SapContext pointer
405
406 RETURN VALUE
407 NULL
408 ============================================================================*/
Jeff Johnsone13d8062017-09-28 06:54:55 -0700409void sap_update_unsafe_channel_list(tHalHandle hal, struct sap_context *sap_ctx)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800410{
411 uint16_t i, j;
Amar Singhalb8d4f152016-02-10 10:21:43 -0800412 uint16_t unsafe_channel_list[NUM_CHANNELS];
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800413 uint16_t unsafe_channel_count = 0;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700414 tpAniSirGlobal mac_ctx = NULL;
415
Yuanyuan Liu0e0aa932016-05-12 10:17:58 -0700416 qdf_device_t qdf_ctx = cds_get_context(QDF_MODULE_ID_QDF_DEVICE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800417
Yuanyuan Liu97361182016-06-06 09:38:04 -0700418 if (!qdf_ctx) {
419 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_FATAL,
420 "qdf_ctx is NULL");
421 return;
422 }
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700423 mac_ctx = PMAC_STRUCT(hal);
Yuanyuan Liu97361182016-06-06 09:38:04 -0700424
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800425 /* Flush, default set all channel safe */
Amar Singhalb8d4f152016-02-10 10:21:43 -0800426 for (i = 0; i < NUM_CHANNELS; i++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800427 safe_channels[i].isSafe = true;
428 }
429
430 /* Try to find unsafe channel */
Ryan Hsu4252a2f2016-01-05 11:18:24 -0800431#if defined(FEATURE_WLAN_STA_AP_MODE_DFS_DISABLE)
Amar Singhalb8d4f152016-02-10 10:21:43 -0800432 for (i = 0; i < NUM_CHANNELS; i++) {
Jeff Johnsone13d8062017-09-28 06:54:55 -0700433 if (sap_ctx->dfs_ch_disable == true) {
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700434 if (wlan_reg_is_dfs_ch(mac_ctx->pdev,
435 safe_channels[i].channelNumber)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800436 safe_channels[i].isSafe = false;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530437 QDF_TRACE(QDF_MODULE_ID_SAP,
438 QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800439 "%s: DFS Ch %d is not safe in"
440 " Concurrent mode",
441 __func__,
442 safe_channels[i].channelNumber);
443 }
444 }
445 }
446#endif
Yuanyuan Liu0e0aa932016-05-12 10:17:58 -0700447 pld_get_wlan_unsafe_channel(qdf_ctx->dev,
448 unsafe_channel_list,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800449 &unsafe_channel_count,
450 sizeof(unsafe_channel_list));
451
452 for (i = 0; i < unsafe_channel_count; i++) {
Amar Singhalb8d4f152016-02-10 10:21:43 -0800453 for (j = 0; j < NUM_CHANNELS; j++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800454 if (safe_channels[j].channelNumber ==
455 unsafe_channel_list[i]) {
456 /* Found unsafe channel, update it */
457 safe_channels[j].isSafe = false;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530458 QDF_TRACE(QDF_MODULE_ID_SAP,
459 QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800460 FL("CH %d is not safe"),
461 unsafe_channel_list[i]);
462 break;
463 }
464 }
465 }
466
467 return;
468}
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800469
470#endif /* FEATURE_WLAN_CH_AVOID */
471
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800472/**
gaoleze5108942017-03-31 16:56:42 +0800473 * sap_channel_in_acs_channel_list() - check if channel in acs channel list
474 * @channel_num: channel to check
475 * @sap_ctx: struct ptSapContext
476 * @spect_info_params: strcut tSapChSelSpectInfo
477 *
478 * This function checks if specified channel is in the configured ACS channel
479 * list.
480 *
481 * Return: channel number if in acs channel list or SAP_CHANNEL_NOT_SELECTED
482 */
gaoleze5108942017-03-31 16:56:42 +0800483uint8_t sap_channel_in_acs_channel_list(uint8_t channel_num,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700484 struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800485 tSapChSelSpectInfo *spect_info_params)
486{
487 uint8_t i = 0;
488
489 if ((NULL == sap_ctx->acs_cfg->ch_list) ||
490 (NULL == spect_info_params))
491 return channel_num;
492
493 if (channel_num > 0 && channel_num <= 252) {
494 for (i = 0; i < sap_ctx->acs_cfg->ch_list_count; i++) {
495 if ((sap_ctx->acs_cfg->ch_list[i]) == channel_num)
496 return channel_num;
497 }
498 return SAP_CHANNEL_NOT_SELECTED;
499 } else {
500 return SAP_CHANNEL_NOT_SELECTED;
501 }
502}
503
504/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800505 * sap_select_preferred_channel_from_channel_list() - to calc best cahnnel
506 * @best_chnl: best channel already calculated among all the chanels
507 * @sap_ctx: sap context
508 * @spectinfo_param: Pointer to tSapChSelSpectInfo structure
509 *
510 * This function calculates the best channel among the configured channel list.
511 * If channel list not configured then returns the best channel calculated
512 * among all the channel list.
513 *
514 * Return: uint8_t best channel
515 */
Jeff Johnson464f7ea2016-10-07 10:21:26 -0700516static
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800517uint8_t sap_select_preferred_channel_from_channel_list(uint8_t best_chnl,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700518 struct sap_context *sap_ctx,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800519 tSapChSelSpectInfo *spectinfo_param)
520{
521 uint8_t i = 0;
Tushnim Bhattacharyya518e80f2017-08-30 17:35:33 -0700522 tpAniSirGlobal mac_ctx = sme_get_mac_context();
523
524 if (NULL == mac_ctx) {
525 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
526 "pmac Global Context is NULL");
527 return SAP_CHANNEL_NOT_SELECTED;
528 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800529
530 /*
531 * If Channel List is not Configured don't do anything
532 * Else return the Best Channel from the Channel List
533 */
534 if ((NULL == sap_ctx->acs_cfg->ch_list) ||
535 (NULL == spectinfo_param) ||
536 (0 == sap_ctx->acs_cfg->ch_list_count))
537 return best_chnl;
538
539 if (best_chnl <= 0 || best_chnl > 252)
540 return SAP_CHANNEL_NOT_SELECTED;
541
542 /* Select the best channel from allowed list */
543 for (i = 0; i < sap_ctx->acs_cfg->ch_list_count; i++) {
Tushnim Bhattacharyya518e80f2017-08-30 17:35:33 -0700544 if ((sap_ctx->acs_cfg->ch_list[i] == best_chnl) &&
545 !(wlan_reg_is_dfs_ch(mac_ctx->pdev, best_chnl) &&
546 policy_mgr_disallow_mcc(mac_ctx->psoc, best_chnl))) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530547 QDF_TRACE(QDF_MODULE_ID_SAP,
Ravi Joshi9788fcd2018-02-13 15:12:22 -0800548 QDF_TRACE_LEVEL_INFO,
Naveen Rawatbec64d92017-09-13 14:35:21 -0700549 "Best channel so far is: %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800550 best_chnl);
551 return best_chnl;
552 }
553 }
554
555 return SAP_CHANNEL_NOT_SELECTED;
556}
557
558/*==========================================================================
559 FUNCTION sap_chan_sel_init
560
561 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -0700562 Function sap_chan_sel_init allocates the memory, initializes the
Anurag Chouhan6d760662016-02-20 16:05:43 +0530563 structures used by the channel selection algorithm
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800564
565 DEPENDENCIES
566 NA.
567
568 PARAMETERS
569
570 IN
571 halHandle : Pointer to tHalHandle
572 *pSpectInfoParams : Pointer to tSapChSelSpectInfo structure
Jeff Johnsone13d8062017-09-28 06:54:55 -0700573 sap_ctx : Pointer to SAP Context
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800574
575 RETURN VALUE
576 bool: Success or FAIL
577
578 SIDE EFFECTS
579 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -0700580static bool sap_chan_sel_init(tHalHandle halHandle,
581 tSapChSelSpectInfo *pSpectInfoParams,
Jeff Johnsone13d8062017-09-28 06:54:55 -0700582 struct sap_context *sap_ctx)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800583{
584 tSapSpectChInfo *pSpectCh = NULL;
585 uint8_t *pChans = NULL;
586 uint16_t channelnum = 0;
587 tpAniSirGlobal pMac = PMAC_STRUCT(halHandle);
588 bool chSafe = true;
589#ifdef FEATURE_WLAN_CH_AVOID
590 uint16_t i;
591#endif
592 uint32_t dfs_master_cap_enabled;
593 bool include_dfs_ch = true;
Himanshu Agarwalfee2e362018-01-18 20:26:35 +0530594 uint8_t chan_num;
Bala Venkatesh2f25c812017-12-15 17:42:12 +0530595 bool sta_sap_scc_on_dfs_chan =
596 policy_mgr_is_sta_sap_scc_allowed_on_dfs_chan(pMac->psoc);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800597
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530598 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH, "In %s",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800599 __func__);
600
601 pSpectInfoParams->numSpectChans =
602 pMac->scan.base_channels.numChannels;
603
604 /* Allocate memory for weight computation of 2.4GHz */
605 pSpectCh =
Himanshu Agarwal052ce252018-06-18 17:18:59 +0530606 (tSapSpectChInfo *)qdf_mem_malloc(
607 (pSpectInfoParams->numSpectChans) *
608 sizeof(*pSpectCh));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800609
610 if (pSpectCh == NULL) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530611 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Anurag Chouhanf04e84f2016-03-03 10:12:12 +0530612 "In %s, QDF_MALLOC_ERR", __func__);
Srinivas Girigowda74a66d62017-06-21 23:28:25 -0700613 return false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800614 }
615
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800616 /* Initialize the pointers in the DfsParams to the allocated memory */
617 pSpectInfoParams->pSpectCh = pSpectCh;
618
619 pChans = pMac->scan.base_channels.channelList;
620
Ryan Hsu4252a2f2016-01-05 11:18:24 -0800621#if defined(FEATURE_WLAN_STA_AP_MODE_DFS_DISABLE)
Jeff Johnsone13d8062017-09-28 06:54:55 -0700622 if (sap_ctx->dfs_ch_disable == true)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800623 include_dfs_ch = false;
624#endif
625 sme_cfg_get_int(halHandle, WNI_CFG_DFS_MASTER_ENABLED,
626 &dfs_master_cap_enabled);
Agrawal Ashish65634612016-08-18 13:24:32 +0530627 if (dfs_master_cap_enabled == 0 ||
Jeff Johnsone13d8062017-09-28 06:54:55 -0700628 ACS_DFS_MODE_DISABLE == sap_ctx->dfs_mode)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800629 include_dfs_ch = false;
630
631 /* Fill the channel number in the spectrum in the operating freq band */
632 for (channelnum = 0;
633 channelnum < pSpectInfoParams->numSpectChans;
Edhar, Mahesh Kumar4f660672015-10-30 11:53:26 +0530634 channelnum++, pChans++, pSpectCh++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800635 chSafe = true;
636
Himanshu Agarwal052ce252018-06-18 17:18:59 +0530637 pSpectCh->chNum = *pChans;
638 /* Initialise for all channels */
639 pSpectCh->rssiAgr = SOFTAP_MIN_RSSI;
640 /* Initialise 20MHz for all the Channels */
641 pSpectCh->channelWidth = SOFTAP_HT20_CHANNELWIDTH;
642 /* Initialise max ACS weight for all channels */
643 pSpectCh->weight = SAP_ACS_WEIGHT_MAX;
644
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800645 /* check if the channel is in NOL blacklist */
Himanshu Agarwal052ce252018-06-18 17:18:59 +0530646 if (sap_dfs_is_channel_in_nol_list(
647 sap_ctx, *pChans,
648 PHY_SINGLE_CHANNEL_CENTERED)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530649 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800650 "In %s, Ch %d is in NOL list", __func__,
651 *pChans);
652 chSafe = false;
653 continue;
654 }
655
Bala Venkatesh2f25c812017-12-15 17:42:12 +0530656 if (!include_dfs_ch || sta_sap_scc_on_dfs_chan) {
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700657 if (wlan_reg_is_dfs_ch(pMac->pdev, *pChans)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800658 chSafe = false;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530659 QDF_TRACE(QDF_MODULE_ID_SAP,
660 QDF_TRACE_LEVEL_INFO_HIGH,
Bala Venkatesh2f25c812017-12-15 17:42:12 +0530661 "In %s, DFS Ch %d not considered for ACS. include_dfs_ch %u, sta_sap_scc_on_dfs_chan %d",
662 __func__, *pChans, include_dfs_ch,
663 sta_sap_scc_on_dfs_chan);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800664 continue;
665 }
666 }
667
668#ifdef FEATURE_WLAN_CH_AVOID
Amar Singhalb8d4f152016-02-10 10:21:43 -0800669 for (i = 0; i < NUM_CHANNELS; i++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800670 if ((safe_channels[i].channelNumber == *pChans) &&
671 (false == safe_channels[i].isSafe)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530672 QDF_TRACE(QDF_MODULE_ID_SAP,
673 QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800674 "In %s, Ch %d is not safe", __func__,
675 *pChans);
676 chSafe = false;
677 break;
678 }
679 }
680#endif /* FEATURE_WLAN_CH_AVOID */
681
682 /* OFDM rates are not supported on channel 14 */
683 if (*pChans == 14 &&
Jeff Johnsone13d8062017-09-28 06:54:55 -0700684 eCSR_DOT11_MODE_11b != sap_ctx->csr_roamProfile.phyMode) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800685 continue;
686 }
687
Deepthi Gowri48b89332016-08-30 18:43:05 +0530688 /* Skip DSRC channels */
Kiran Kumar Lokere1a43bcf2018-05-15 15:51:58 -0700689 if (wlan_reg_is_dsrc_chan(pMac->pdev, *pChans))
690 continue;
691
692 if (!pMac->sap.enable_etsi13_srd_chan_support &&
693 wlan_reg_is_etsi13_srd_chan(pMac->pdev, *pChans))
Deepthi Gowri48b89332016-08-30 18:43:05 +0530694 continue;
695
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800696 if (true == chSafe) {
Srinivas Girigowda74a66d62017-06-21 23:28:25 -0700697 pSpectCh->valid = true;
Himanshu Agarwalfee2e362018-01-18 20:26:35 +0530698 for (chan_num = 0; chan_num < sap_ctx->num_of_channel;
699 chan_num++) {
700 if (pSpectCh->chNum !=
701 sap_ctx->channelList[chan_num])
702 continue;
703
704 /*
705 * Initialize ACS weight to 0 for channels
706 * present in sap context scan channel list
707 */
708 pSpectCh->weight = 0;
709 break;
710 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800711 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800712 }
Srinivas Girigowda74a66d62017-06-21 23:28:25 -0700713 return true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800714}
715
gaoleze5108942017-03-31 16:56:42 +0800716/**
717 * sapweight_rssi_count() - calculates the channel weight due to rssi
Anurag Chouhan6d760662016-02-20 16:05:43 +0530718 and data count(here number of BSS observed)
gaoleze5108942017-03-31 16:56:42 +0800719 * @sap_ctx : Softap context
720 * @rssi : Max signal strength receieved from a BSS for the channel
721 * @count : Number of BSS observed in the channel
722 *
723 * Return: uint32_t Calculated channel weight based on above two
724 */
725static
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700726uint32_t sapweight_rssi_count(struct sap_context *sap_ctx, int8_t rssi,
gaoleze5108942017-03-31 16:56:42 +0800727 uint16_t count)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800728{
729 int32_t rssiWeight = 0;
730 int32_t countWeight = 0;
731 uint32_t rssicountWeight = 0;
gaoleze5108942017-03-31 16:56:42 +0800732 uint8_t softap_rssi_weight_cfg, softap_count_weight_cfg;
733 uint8_t softap_rssi_weight_local, softap_count_weight_local;
734
735 softap_rssi_weight_cfg =
736 ACS_WEIGHT_SOFTAP_RSSI_CFG(sap_ctx->auto_channel_select_weight);
737
738 softap_count_weight_cfg =
739 ACS_WEIGHT_SOFTAP_COUNT_CFG(sap_ctx->auto_channel_select_weight);
740
741 softap_rssi_weight_local =
742 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
743 softap_rssi_weight_cfg);
744
745 softap_count_weight_local =
746 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
747 softap_count_weight_cfg);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800748
749 /* Weight from RSSI */
gaoleze5108942017-03-31 16:56:42 +0800750 rssiWeight = ACS_WEIGHT_COMPUTE(sap_ctx->auto_channel_select_weight,
751 softap_rssi_weight_cfg,
752 rssi - SOFTAP_MIN_RSSI,
753 SOFTAP_MAX_RSSI - SOFTAP_MIN_RSSI);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800754
gaoleze5108942017-03-31 16:56:42 +0800755 if (rssiWeight > softap_rssi_weight_local)
756 rssiWeight = softap_rssi_weight_local;
757
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800758 else if (rssiWeight < 0)
759 rssiWeight = 0;
760
761 /* Weight from data count */
gaoleze5108942017-03-31 16:56:42 +0800762 countWeight = ACS_WEIGHT_COMPUTE(sap_ctx->auto_channel_select_weight,
763 softap_count_weight_cfg,
764 count - SOFTAP_MIN_COUNT,
765 SOFTAP_MAX_COUNT - SOFTAP_MIN_COUNT);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800766
gaoleze5108942017-03-31 16:56:42 +0800767 if (countWeight > softap_count_weight_local)
768 countWeight = softap_count_weight_local;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800769
770 rssicountWeight = rssiWeight + countWeight;
771
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530772 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800773 "In %s, rssiWeight=%d, countWeight=%d, rssicountWeight=%d",
774 __func__, rssiWeight, countWeight, rssicountWeight);
775
776 return rssicountWeight;
777}
778
779/**
gaoleze5108942017-03-31 16:56:42 +0800780 * sap_get_channel_status() - get channel info via channel number
781 * @p_mac: Pointer to Global MAC structure
782 * @channel_id: channel id
783 *
784 * Return: chan status info
785 */
786static struct lim_channel_status *sap_get_channel_status
787 (tpAniSirGlobal p_mac, uint32_t channel_id)
788{
789 return csr_get_channel_status(p_mac, channel_id);
790}
791
792/**
793 * sap_clear_channel_status() - clear chan info
794 * @p_mac: Pointer to Global MAC structure
795 *
796 * Return: none
797 */
798static void sap_clear_channel_status(tpAniSirGlobal p_mac)
799{
800 csr_clear_channel_status(p_mac);
801}
802
803/**
804 * sap_weight_channel_noise_floor() - compute noise floor weight
805 * @sap_ctx: sap context
806 * @chn_stat: Pointer to chan status info
807 *
808 * Return: channel noise floor weight
809 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700810static uint32_t sap_weight_channel_noise_floor(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800811 struct lim_channel_status
812 *channel_stat)
813{
814 uint32_t noise_floor_weight;
815 uint8_t softap_nf_weight_cfg;
816 uint8_t softap_nf_weight_local;
817
818 softap_nf_weight_cfg =
819 ACS_WEIGHT_SOFTAP_NOISE_FLOOR_CFG
820 (sap_ctx->auto_channel_select_weight);
821
822 softap_nf_weight_local =
823 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
824 softap_nf_weight_cfg);
825
826 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800827 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800828 "In %s, sanity check failed return max weight",
829 __func__);
830 return softap_nf_weight_local;
831 }
832
833 noise_floor_weight = (channel_stat->noise_floor == 0) ? 0 :
834 (ACS_WEIGHT_COMPUTE(
835 sap_ctx->auto_channel_select_weight,
836 softap_nf_weight_cfg,
837 channel_stat->noise_floor -
838 SOFTAP_MIN_NF,
839 SOFTAP_MAX_NF - SOFTAP_MIN_NF));
840
841 if (noise_floor_weight > softap_nf_weight_local)
842 noise_floor_weight = softap_nf_weight_local;
843 else if (noise_floor_weight < 0)
844 noise_floor_weight = 0;
845
846 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
847 "In %s, nf=%d, nfwc=%d, nfwl=%d, nfw=%d",
848 __func__, channel_stat->noise_floor,
849 softap_nf_weight_cfg, softap_nf_weight_local,
850 noise_floor_weight);
851
852 return noise_floor_weight;
853}
854
855/**
856 * sap_weight_channel_free() - compute channel free weight
857 * @sap_ctx: sap context
858 * @chn_stat: Pointer to chan status info
859 *
860 * Return: channel free weight
861 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700862static uint32_t sap_weight_channel_free(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800863 struct lim_channel_status
864 *channel_stat)
865{
866 uint32_t channel_free_weight;
867 uint8_t softap_channel_free_weight_cfg;
868 uint8_t softap_channel_free_weight_local;
869 uint32_t rx_clear_count = 0;
870 uint32_t cycle_count = 0;
871
872 softap_channel_free_weight_cfg =
873 ACS_WEIGHT_SOFTAP_CHANNEL_FREE_CFG
874 (sap_ctx->auto_channel_select_weight);
875
876 softap_channel_free_weight_local =
877 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
878 softap_channel_free_weight_cfg);
879
880 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800881 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800882 "In %s, sanity check failed return max weight",
883 __func__);
884 return softap_channel_free_weight_local;
885 }
886
887 rx_clear_count = channel_stat->rx_clear_count -
888 channel_stat->tx_frame_count -
889 channel_stat->rx_frame_count;
890 cycle_count = channel_stat->cycle_count;
891
892 /* LSH 4, otherwise it is always 0. */
893 channel_free_weight = (cycle_count == 0) ? 0 :
894 (ACS_WEIGHT_COMPUTE(
895 sap_ctx->auto_channel_select_weight,
896 softap_channel_free_weight_cfg,
897 ((rx_clear_count << 8) +
898 (cycle_count >> 1))/cycle_count -
899 (SOFTAP_MIN_CHNFREE << 8),
900 (SOFTAP_MAX_CHNFREE -
901 SOFTAP_MIN_CHNFREE) << 8));
902
903 if (channel_free_weight > softap_channel_free_weight_local)
904 channel_free_weight = softap_channel_free_weight_local;
905
906 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
907 "In %s, rcc=%d, cc=%d, tc=%d, rc=%d, cfwc=%d, cfwl=%d, cfw=%d",
908 __func__, rx_clear_count, cycle_count,
909 channel_stat->tx_frame_count,
910 channel_stat->rx_frame_count,
911 softap_channel_free_weight_cfg,
912 softap_channel_free_weight_local,
913 channel_free_weight);
914
915 return channel_free_weight;
916}
917
918/**
919 * sap_weight_channel_txpwr_range() - compute channel tx power range weight
920 * @sap_ctx: sap context
921 * @chn_stat: Pointer to chan status info
922 *
923 * Return: tx power range weight
924 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700925static uint32_t sap_weight_channel_txpwr_range(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800926 struct lim_channel_status
927 *channel_stat)
928{
929 uint32_t txpwr_weight_low_speed;
930 uint8_t softap_txpwr_range_weight_cfg;
931 uint8_t softap_txpwr_range_weight_local;
932
933 softap_txpwr_range_weight_cfg =
934 ACS_WEIGHT_SOFTAP_TX_POWER_RANGE_CFG
935 (sap_ctx->auto_channel_select_weight);
936
937 softap_txpwr_range_weight_local =
938 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
939 softap_txpwr_range_weight_cfg);
940
941 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800942 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800943 "In %s, sanity check failed return max weight",
944 __func__);
945 return softap_txpwr_range_weight_local;
946 }
947
948 txpwr_weight_low_speed = (channel_stat->chan_tx_pwr_range == 0) ? 0 :
949 (ACS_WEIGHT_COMPUTE(
950 sap_ctx->auto_channel_select_weight,
951 softap_txpwr_range_weight_cfg,
952 SOFTAP_MAX_TXPWR -
953 channel_stat->chan_tx_pwr_range,
954 SOFTAP_MAX_TXPWR - SOFTAP_MIN_TXPWR));
955
956 if (txpwr_weight_low_speed > softap_txpwr_range_weight_local)
957 txpwr_weight_low_speed = softap_txpwr_range_weight_local;
958
959 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
960 "In %s, tpr=%d, tprwc=%d, tprwl=%d, tprw=%d",
961 __func__, channel_stat->chan_tx_pwr_range,
962 softap_txpwr_range_weight_cfg,
963 softap_txpwr_range_weight_local,
964 txpwr_weight_low_speed);
965
966 return txpwr_weight_low_speed;
967}
968
969/**
970 * sap_weight_channel_txpwr_tput() - compute channel tx power
971 * throughput weight
972 * @sap_ctx: sap context
973 * @chn_stat: Pointer to chan status info
974 *
975 * Return: tx power throughput weight
976 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700977static uint32_t sap_weight_channel_txpwr_tput(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800978 struct lim_channel_status
979 *channel_stat)
980{
981 uint32_t txpwr_weight_high_speed;
982 uint8_t softap_txpwr_tput_weight_cfg;
983 uint8_t softap_txpwr_tput_weight_local;
984
985 softap_txpwr_tput_weight_cfg =
986 ACS_WEIGHT_SOFTAP_TX_POWER_THROUGHPUT_CFG
987 (sap_ctx->auto_channel_select_weight);
988
989 softap_txpwr_tput_weight_local =
990 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
991 softap_txpwr_tput_weight_cfg);
992
993 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800994 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800995 "In %s, sanity check failed return max weight",
996 __func__);
997 return softap_txpwr_tput_weight_local;
998 }
999
1000 txpwr_weight_high_speed = (channel_stat->chan_tx_pwr_throughput == 0)
1001 ? 0 : (ACS_WEIGHT_COMPUTE(
1002 sap_ctx->auto_channel_select_weight,
1003 softap_txpwr_tput_weight_cfg,
1004 SOFTAP_MAX_TXPWR -
1005 channel_stat->chan_tx_pwr_throughput,
1006 SOFTAP_MAX_TXPWR - SOFTAP_MIN_TXPWR));
1007
1008 if (txpwr_weight_high_speed > softap_txpwr_tput_weight_local)
1009 txpwr_weight_high_speed = softap_txpwr_tput_weight_local;
1010
1011 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
1012 "In %s, tpt=%d, tptwc=%d, tptwl=%d, tptw=%d",
1013 __func__, channel_stat->chan_tx_pwr_throughput,
1014 softap_txpwr_tput_weight_cfg,
1015 softap_txpwr_tput_weight_local,
1016 txpwr_weight_high_speed);
1017
1018 return txpwr_weight_high_speed;
1019}
1020
1021/**
1022 * sap_weight_channel_status() - compute chan status weight
1023 * @sap_ctx: sap context
1024 * @chn_stat: Pointer to chan status info
1025 *
1026 * Return: chan status weight
1027 */
1028static
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07001029uint32_t sap_weight_channel_status(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +08001030 struct lim_channel_status *channel_stat)
1031{
1032 return sap_weight_channel_noise_floor(sap_ctx, channel_stat) +
1033 sap_weight_channel_free(sap_ctx, channel_stat) +
1034 sap_weight_channel_txpwr_range(sap_ctx, channel_stat) +
1035 sap_weight_channel_txpwr_tput(sap_ctx, channel_stat);
1036}
1037
1038/**
Yeshwanth Sriram Guntuka273889e2018-02-16 17:11:46 +05301039 * sap_check_channels_same_band() - Check if two channels belong to same band
1040 * @ch_num1: channel number
1041 * @ch_num2: channel number
1042 *
1043 * Return: true if both channels belong to same band else false
1044 */
1045static bool sap_check_channels_same_band(uint16_t ch_num1, uint16_t ch_num2)
1046{
1047 if ((ch_num1 <= SIR_11B_CHANNEL_END &&
1048 ch_num2 <= SIR_11B_CHANNEL_END) ||
1049 (ch_num1 >= SIR_11A_CHANNEL_BEGIN &&
1050 ch_num2 >= SIR_11A_CHANNEL_BEGIN))
1051 return true;
1052
1053 return false;
1054}
1055
1056/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001057 * sap_update_rssi_bsscount() - updates bss count and rssi effect.
1058 *
1059 * @pSpectCh: Channel Information
1060 * @offset: Channel Offset
1061 * @sap_24g: Channel is in 2.4G or 5G
Liangwei Dong71ed6502016-10-20 03:40:45 -04001062 * @spectch_start: the start of spect ch array
1063 * @spectch_end: the end of spect ch array
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001064 *
1065 * sap_update_rssi_bsscount updates bss count and rssi effect based
1066 * on the channel offset.
1067 *
1068 * Return: None.
1069 */
1070
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001071static void sap_update_rssi_bsscount(tSapSpectChInfo *pSpectCh, int32_t offset,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001072 bool sap_24g, tSapSpectChInfo *spectch_start,
1073 tSapSpectChInfo *spectch_end)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001074{
1075 tSapSpectChInfo *pExtSpectCh = NULL;
1076 int32_t rssi, rsssi_effect;
1077
1078 pExtSpectCh = (pSpectCh + offset);
Liangwei Dong71ed6502016-10-20 03:40:45 -04001079 if (pExtSpectCh != NULL &&
1080 pExtSpectCh >= spectch_start &&
1081 pExtSpectCh < spectch_end) {
Yeshwanth Sriram Guntuka273889e2018-02-16 17:11:46 +05301082 if (!sap_check_channels_same_band(pSpectCh->chNum,
1083 pExtSpectCh->chNum))
1084 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001085 ++pExtSpectCh->bssCount;
1086 switch (offset) {
1087 case -1:
1088 case 1:
1089 rsssi_effect = sap_24g ?
1090 SAP_24GHZ_FIRST_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1091 SAP_SUBBAND1_RSSI_EFFECT_PRIMARY;
1092 break;
1093 case -2:
1094 case 2:
1095 rsssi_effect = sap_24g ?
1096 SAP_24GHZ_SEC_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1097 SAP_SUBBAND2_RSSI_EFFECT_PRIMARY;
1098 break;
1099 case -3:
1100 case 3:
1101 rsssi_effect = sap_24g ?
1102 SAP_24GHZ_THIRD_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1103 SAP_SUBBAND3_RSSI_EFFECT_PRIMARY;
1104 break;
1105 case -4:
1106 case 4:
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001107 rsssi_effect = sap_24g ?
1108 SAP_24GHZ_FOURTH_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1109 SAP_SUBBAND4_RSSI_EFFECT_PRIMARY;
1110 break;
1111 case -5:
1112 case 5:
1113 rsssi_effect = SAP_SUBBAND5_RSSI_EFFECT_PRIMARY;
1114 break;
1115 case -6:
1116 case 6:
1117 rsssi_effect = SAP_SUBBAND6_RSSI_EFFECT_PRIMARY;
1118 break;
1119 case -7:
1120 case 7:
1121 rsssi_effect = SAP_SUBBAND7_RSSI_EFFECT_PRIMARY;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001122 break;
1123 default:
1124 rsssi_effect = 0;
1125 break;
1126 }
1127
1128 rssi = pSpectCh->rssiAgr + rsssi_effect;
1129 if (IS_RSSI_VALID(pExtSpectCh->rssiAgr, rssi))
1130 pExtSpectCh->rssiAgr = rssi;
1131 if (pExtSpectCh->rssiAgr < SOFTAP_MIN_RSSI)
1132 pExtSpectCh->rssiAgr = SOFTAP_MIN_RSSI;
1133 }
1134}
1135
1136/**
1137 * sap_upd_chan_spec_params() - sap_upd_chan_spec_params
1138 * updates channel parameters obtained from Beacon
1139 * @pBeaconStruct Beacon strucutre populated by parse_beacon function
1140 * @channelWidth Channel width
1141 * @secondaryChannelOffset Secondary Channel Offset
1142 * @vhtSupport If channel supports VHT
1143 * @centerFreq Central frequency for the given channel.
1144 *
1145 * sap_upd_chan_spec_params updates the spectrum channels based on the
1146 * pBeaconStruct obtained from Beacon IE
1147 *
1148 * Return: NA.
1149 */
1150
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001151static void sap_upd_chan_spec_params(tSirProbeRespBeacon *pBeaconStruct,
1152 uint16_t *channelWidth,
1153 uint16_t *secondaryChannelOffset,
1154 uint16_t *vhtSupport,
1155 uint16_t *centerFreq,
1156 uint16_t *centerFreq_2)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001157{
1158 if (NULL == pBeaconStruct) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301159 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001160 FL("pBeaconStruct is NULL"));
1161 return;
1162 }
1163
1164 if (pBeaconStruct->HTCaps.present && pBeaconStruct->HTInfo.present) {
1165 *channelWidth = pBeaconStruct->HTCaps.supportedChannelWidthSet;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001166 *secondaryChannelOffset =
1167 pBeaconStruct->HTInfo.secondaryChannelOffset;
1168 if (!pBeaconStruct->VHTOperation.present)
1169 return;
1170 *vhtSupport = pBeaconStruct->VHTOperation.present;
1171 if (pBeaconStruct->VHTOperation.chanWidth) {
1172 *centerFreq =
1173 pBeaconStruct->VHTOperation.chanCenterFreqSeg1;
1174 *centerFreq_2 =
1175 pBeaconStruct->VHTOperation.chanCenterFreqSeg2;
1176 /*
1177 * LHS follows tSirMacHTChannelWidth, while RHS follows
1178 * WNI_CFG_VHT_CHANNEL_WIDTH_X format hence following
1179 * adjustment
1180 */
1181 *channelWidth =
1182 pBeaconStruct->VHTOperation.chanWidth + 1;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001183
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001184 }
1185 }
1186}
1187
1188/**
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001189 * sap_update_rssi_bsscount_vht_5G() - updates bss count and rssi effect.
1190 *
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001191 * @spect_ch: Channel Information
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001192 * @offset: Channel Offset
1193 * @num_ch: no.of channels
Liangwei Dong71ed6502016-10-20 03:40:45 -04001194 * @spectch_start: the start of spect ch array
1195 * @spectch_end: the end of spect ch array
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001196 *
1197 * sap_update_rssi_bsscount_vht_5G updates bss count and rssi effect based
1198 * on the channel offset.
1199 *
1200 * Return: None.
1201 */
1202
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001203static void sap_update_rssi_bsscount_vht_5G(tSapSpectChInfo *spect_ch,
1204 int32_t offset,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001205 uint16_t num_ch,
1206 tSapSpectChInfo *spectch_start,
1207 tSapSpectChInfo *spectch_end)
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001208{
1209 int32_t ch_offset;
1210 uint16_t i, cnt;
1211
1212 if (!offset)
1213 return;
1214 if (offset > 0)
1215 cnt = num_ch;
1216 else
1217 cnt = num_ch + 1;
1218 for (i = 0; i < cnt; i++) {
1219 ch_offset = offset + i;
1220 if (ch_offset == 0)
1221 continue;
Liangwei Dong71ed6502016-10-20 03:40:45 -04001222 sap_update_rssi_bsscount(spect_ch, ch_offset, false,
1223 spectch_start, spectch_end);
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001224 }
1225}
1226/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001227 * sap_interference_rssi_count_5G() - sap_interference_rssi_count
1228 * considers the Adjacent channel rssi and
1229 * data count(here number of BSS observed)
1230 * @spect_ch: Channel Information
1231 * @chan_width: Channel width parsed from beacon IE
1232 * @sec_chan_offset: Secondary Channel Offset
1233 * @center_freq: Central frequency for the given channel.
1234 * @channel_id: channel_id
Liangwei Dong71ed6502016-10-20 03:40:45 -04001235 * @spectch_start: the start of spect ch array
1236 * @spectch_end: the end of spect ch array
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001237 *
1238 * sap_interference_rssi_count_5G considers the Adjacent channel rssi
1239 * and data count(here number of BSS observed)
1240 *
1241 * Return: NA.
1242 */
1243
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001244static void sap_interference_rssi_count_5G(tSapSpectChInfo *spect_ch,
1245 uint16_t chan_width,
1246 uint16_t sec_chan_offset,
1247 uint16_t center_freq,
1248 uint16_t center_freq_2,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001249 uint8_t channel_id,
1250 tSapSpectChInfo *spectch_start,
1251 tSapSpectChInfo *spectch_end)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001252{
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001253 uint16_t num_ch;
1254 int32_t offset = 0;
Srinivas Girigowda4d65ebe2017-10-13 21:41:42 -07001255
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001256 if (NULL == spect_ch) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301257 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001258 FL("spect_ch is NULL"));
1259 return;
1260 }
1261
1262 /* Updating the received ChannelWidth */
1263 if (spect_ch->channelWidth != chan_width)
1264 spect_ch->channelWidth = chan_width;
1265 /* If received ChannelWidth is other than HT20,
1266 * we need to update the extension channel Params as well
1267 * chan_width == 0, HT20
1268 * chan_width == 1, HT40
1269 * chan_width == 2, VHT80
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001270 * chan_width == 3, VHT160
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001271 */
1272
1273 switch (spect_ch->channelWidth) {
1274 case eHT_CHANNEL_WIDTH_40MHZ: /* HT40 */
1275 switch (sec_chan_offset) {
1276 /* Above the Primary Channel */
1277 case PHY_DOUBLE_CHANNEL_LOW_PRIMARY:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001278 sap_update_rssi_bsscount(spect_ch, 1, false,
1279 spectch_start, spectch_end);
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001280 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001281
1282 /* Below the Primary channel */
1283 case PHY_DOUBLE_CHANNEL_HIGH_PRIMARY:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001284 sap_update_rssi_bsscount(spect_ch, -1, false,
1285 spectch_start, spectch_end);
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001286 return;
1287 }
1288 return;
1289 case eHT_CHANNEL_WIDTH_80MHZ: /* VHT80 */
1290 num_ch = 3;
1291 if ((center_freq - channel_id) == 6) {
1292 offset = 1;
1293 } else if ((center_freq - channel_id) == 2) {
1294 offset = -1;
1295 } else if ((center_freq - channel_id) == -2) {
1296 offset = -2;
1297 } else if ((center_freq - channel_id) == -6) {
1298 offset = -3;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001299 }
1300 break;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001301 case eHT_CHANNEL_WIDTH_160MHZ: /* VHT160 */
1302 num_ch = 7;
1303 if ((center_freq - channel_id) == 14)
1304 offset = 1;
1305 else if ((center_freq - channel_id) == 10)
1306 offset = -1;
1307 else if ((center_freq - channel_id) == 6)
1308 offset = -2;
1309 else if ((center_freq - channel_id) == 2)
1310 offset = -3;
1311 else if ((center_freq - channel_id) == -2)
1312 offset = -4;
1313 else if ((center_freq - channel_id) == -6)
1314 offset = -5;
1315 else if ((center_freq - channel_id) == -10)
1316 offset = -6;
1317 else if ((center_freq - channel_id) == -14)
1318 offset = -7;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001319 break;
1320 default:
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001321 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001322 }
Liangwei Dong71ed6502016-10-20 03:40:45 -04001323 sap_update_rssi_bsscount_vht_5G(spect_ch, offset, num_ch,
1324 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001325}
1326
1327/**
1328 * sap_interference_rssi_count() - sap_interference_rssi_count
1329 * considers the Adjacent channel rssi
1330 * and data count(here number of BSS observed)
1331 * @spect_ch Channel Information
Liangwei Dong71ed6502016-10-20 03:40:45 -04001332 * @spectch_start: the start of spect ch array
1333 * @spectch_end: the end of spect ch array
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001334 *
1335 * sap_interference_rssi_count considers the Adjacent channel rssi
1336 * and data count(here number of BSS observed)
1337 *
1338 * Return: None.
1339 */
1340
Liangwei Dong71ed6502016-10-20 03:40:45 -04001341static void sap_interference_rssi_count(tSapSpectChInfo *spect_ch,
1342 tSapSpectChInfo *spectch_start,
1343 tSapSpectChInfo *spectch_end)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001344{
1345 if (NULL == spect_ch) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301346 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001347 "%s: spect_ch is NULL", __func__);
1348 return;
1349 }
1350
1351 switch (spect_ch->chNum) {
1352 case CHANNEL_1:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001353 sap_update_rssi_bsscount(spect_ch, 1, true,
1354 spectch_start, spectch_end);
1355 sap_update_rssi_bsscount(spect_ch, 2, true,
1356 spectch_start, spectch_end);
1357 sap_update_rssi_bsscount(spect_ch, 3, true,
1358 spectch_start, spectch_end);
1359 sap_update_rssi_bsscount(spect_ch, 4, true,
1360 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001361 break;
1362
1363 case CHANNEL_2:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001364 sap_update_rssi_bsscount(spect_ch, -1, true,
1365 spectch_start, spectch_end);
1366 sap_update_rssi_bsscount(spect_ch, 1, true,
1367 spectch_start, spectch_end);
1368 sap_update_rssi_bsscount(spect_ch, 2, true,
1369 spectch_start, spectch_end);
1370 sap_update_rssi_bsscount(spect_ch, 3, true,
1371 spectch_start, spectch_end);
1372 sap_update_rssi_bsscount(spect_ch, 4, true,
1373 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001374 break;
1375 case CHANNEL_3:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001376 sap_update_rssi_bsscount(spect_ch, -2, true,
1377 spectch_start, spectch_end);
1378 sap_update_rssi_bsscount(spect_ch, -1, true,
1379 spectch_start, spectch_end);
1380 sap_update_rssi_bsscount(spect_ch, 1, true,
1381 spectch_start, spectch_end);
1382 sap_update_rssi_bsscount(spect_ch, 2, true,
1383 spectch_start, spectch_end);
1384 sap_update_rssi_bsscount(spect_ch, 3, true,
1385 spectch_start, spectch_end);
1386 sap_update_rssi_bsscount(spect_ch, 4, true,
1387 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001388 break;
1389 case CHANNEL_4:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001390 sap_update_rssi_bsscount(spect_ch, -3, true,
1391 spectch_start, spectch_end);
1392 sap_update_rssi_bsscount(spect_ch, -2, true,
1393 spectch_start, spectch_end);
1394 sap_update_rssi_bsscount(spect_ch, -1, true,
1395 spectch_start, spectch_end);
1396 sap_update_rssi_bsscount(spect_ch, 1, true,
1397 spectch_start, spectch_end);
1398 sap_update_rssi_bsscount(spect_ch, 2, true,
1399 spectch_start, spectch_end);
1400 sap_update_rssi_bsscount(spect_ch, 3, true,
1401 spectch_start, spectch_end);
1402 sap_update_rssi_bsscount(spect_ch, 4, true,
1403 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001404 break;
1405
1406 case CHANNEL_5:
1407 case CHANNEL_6:
1408 case CHANNEL_7:
1409 case CHANNEL_8:
1410 case CHANNEL_9:
1411 case CHANNEL_10:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001412 sap_update_rssi_bsscount(spect_ch, -4, true,
1413 spectch_start, spectch_end);
1414 sap_update_rssi_bsscount(spect_ch, -3, true,
1415 spectch_start, spectch_end);
1416 sap_update_rssi_bsscount(spect_ch, -2, true,
1417 spectch_start, spectch_end);
1418 sap_update_rssi_bsscount(spect_ch, -1, true,
1419 spectch_start, spectch_end);
1420 sap_update_rssi_bsscount(spect_ch, 1, true,
1421 spectch_start, spectch_end);
1422 sap_update_rssi_bsscount(spect_ch, 2, true,
1423 spectch_start, spectch_end);
1424 sap_update_rssi_bsscount(spect_ch, 3, true,
1425 spectch_start, spectch_end);
1426 sap_update_rssi_bsscount(spect_ch, 4, true,
1427 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001428 break;
1429
1430 case CHANNEL_11:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001431 sap_update_rssi_bsscount(spect_ch, -4, true,
1432 spectch_start, spectch_end);
1433 sap_update_rssi_bsscount(spect_ch, -3, true,
1434 spectch_start, spectch_end);
1435 sap_update_rssi_bsscount(spect_ch, -2, true,
1436 spectch_start, spectch_end);
1437 sap_update_rssi_bsscount(spect_ch, -1, true,
1438 spectch_start, spectch_end);
1439 sap_update_rssi_bsscount(spect_ch, 1, true,
1440 spectch_start, spectch_end);
1441 sap_update_rssi_bsscount(spect_ch, 2, true,
1442 spectch_start, spectch_end);
1443 sap_update_rssi_bsscount(spect_ch, 3, true,
1444 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001445 break;
1446
1447 case CHANNEL_12:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001448 sap_update_rssi_bsscount(spect_ch, -4, true,
1449 spectch_start, spectch_end);
1450 sap_update_rssi_bsscount(spect_ch, -3, true,
1451 spectch_start, spectch_end);
1452 sap_update_rssi_bsscount(spect_ch, -2, true,
1453 spectch_start, spectch_end);
1454 sap_update_rssi_bsscount(spect_ch, -1, true,
1455 spectch_start, spectch_end);
1456 sap_update_rssi_bsscount(spect_ch, 1, true,
1457 spectch_start, spectch_end);
1458 sap_update_rssi_bsscount(spect_ch, 2, true,
1459 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001460 break;
1461
1462 case CHANNEL_13:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001463 sap_update_rssi_bsscount(spect_ch, -4, true,
1464 spectch_start, spectch_end);
1465 sap_update_rssi_bsscount(spect_ch, -3, true,
1466 spectch_start, spectch_end);
1467 sap_update_rssi_bsscount(spect_ch, -2, true,
1468 spectch_start, spectch_end);
1469 sap_update_rssi_bsscount(spect_ch, -1, true,
1470 spectch_start, spectch_end);
1471 sap_update_rssi_bsscount(spect_ch, 1, true,
1472 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001473 break;
1474
1475 case CHANNEL_14:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001476 sap_update_rssi_bsscount(spect_ch, -4, true,
1477 spectch_start, spectch_end);
1478 sap_update_rssi_bsscount(spect_ch, -3, true,
1479 spectch_start, spectch_end);
1480 sap_update_rssi_bsscount(spect_ch, -2, true,
1481 spectch_start, spectch_end);
1482 sap_update_rssi_bsscount(spect_ch, -1, true,
1483 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001484 break;
1485
1486 default:
1487 break;
1488 }
1489}
1490
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001491/**
1492 * ch_in_pcl() - Is channel in the Preferred Channel List (PCL)
1493 * @sap_ctx: SAP context which contains the current PCL
1494 * @channel: Input channel number to be checked
1495 *
1496 * Check if a channel is in the preferred channel list
1497 *
1498 * Return:
1499 * true: channel is in PCL,
1500 * false: channel is not in PCL
1501 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07001502static bool ch_in_pcl(struct sap_context *sap_ctx, uint8_t channel)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001503{
1504 uint32_t i;
1505
1506 for (i = 0; i < sap_ctx->acs_cfg->pcl_ch_count; i++) {
1507 if (channel == sap_ctx->acs_cfg->pcl_channels[i])
1508 return true;
1509 }
1510
1511 return false;
1512}
1513
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001514/**
1515 * sap_compute_spect_weight() - Compute spectrum weight
1516 * @pSpectInfoParams: Pointer to the tSpectInfoParams structure
1517 * @halHandle: Pointer to HAL handle
1518 * @pResult: Pointer to tScanResultHandle
1519 * @sap_ctx: Context of the SAP
1520 *
1521 * Main function for computing the weight of each channel in the
1522 * spectrum based on the RSSI value of the BSSes on the channel
1523 * and number of BSS
1524 */
1525static void sap_compute_spect_weight(tSapChSelSpectInfo *pSpectInfoParams,
1526 tHalHandle halHandle,
1527 tScanResultHandle pResult,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07001528 struct sap_context *sap_ctx)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001529{
1530 int8_t rssi = 0;
1531 uint8_t chn_num = 0;
1532 uint8_t channel_id = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001533 tCsrScanResultInfo *pScanResult;
1534 tSapSpectChInfo *pSpectCh = pSpectInfoParams->pSpectCh;
1535 uint32_t operatingBand;
1536 uint16_t channelWidth;
1537 uint16_t secondaryChannelOffset;
1538 uint16_t centerFreq;
gaurank kathpalia859c9362018-08-02 23:07:21 +05301539 uint8_t i;
1540 bool found;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001541 uint16_t centerFreq_2 = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001542 uint16_t vhtSupport;
1543 uint32_t ieLen = 0;
1544 tSirProbeRespBeacon *pBeaconStruct;
1545 tpAniSirGlobal pMac = (tpAniSirGlobal) halHandle;
Liangwei Dong71ed6502016-10-20 03:40:45 -04001546 tSapSpectChInfo *spectch_start = pSpectInfoParams->pSpectCh;
1547 tSapSpectChInfo *spectch_end = pSpectInfoParams->pSpectCh +
1548 pSpectInfoParams->numSpectChans;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001549
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301550 pBeaconStruct = qdf_mem_malloc(sizeof(tSirProbeRespBeacon));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001551 if (NULL == pBeaconStruct) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301552 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Kaushik, Sushantee3ed032016-08-04 16:40:46 +05301553 "Unable to allocate memory in sap_compute_spect_weight");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001554 return;
1555 }
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301556 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001557 "In %s, Computing spectral weight", __func__);
1558
1559 /**
1560 * Soft AP specific channel weight calculation using DFS formula
1561 */
1562 SET_ACS_BAND(operatingBand, sap_ctx);
1563
1564 pScanResult = sme_scan_result_get_first(halHandle, pResult);
1565
1566 while (pScanResult) {
1567 pSpectCh = pSpectInfoParams->pSpectCh;
1568 /* Defining the default values, so that any value will hold the default values */
1569 channelWidth = eHT_CHANNEL_WIDTH_20MHZ;
1570 secondaryChannelOffset = PHY_SINGLE_CHANNEL_CENTERED;
1571 vhtSupport = 0;
1572 centerFreq = 0;
1573
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001574
Yingying Tang22facc12016-10-20 17:43:59 +08001575 ieLen = GET_IE_LEN_IN_BSS(
1576 pScanResult->BssDescriptor.length);
1577 qdf_mem_set((uint8_t *) pBeaconStruct,
1578 sizeof(tSirProbeRespBeacon), 0);
1579
1580
1581 if ((sir_parse_beacon_ie
1582 (pMac, pBeaconStruct, (uint8_t *)
1583 (pScanResult->BssDescriptor.ieFields),
Jeff Johnson83e30fa2018-06-07 23:01:11 -07001584 ieLen)) == QDF_STATUS_SUCCESS)
Yingying Tang22facc12016-10-20 17:43:59 +08001585 sap_upd_chan_spec_params(
1586 pBeaconStruct,
1587 &channelWidth,
1588 &secondaryChannelOffset,
1589 &vhtSupport, &centerFreq,
1590 &centerFreq_2);
1591
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001592 /* Processing for each tCsrScanResultInfo in the tCsrScanResult DLink list */
1593 for (chn_num = 0; chn_num < pSpectInfoParams->numSpectChans;
1594 chn_num++) {
1595
1596 /*
Himanshu Agarwalcf5b8932018-07-02 18:06:49 +05301597 * If the Beacon has channel ID, use it other wise we
1598 * will rely on the channelIdSelf
1599 */
1600 if (pScanResult->BssDescriptor.channelId == 0)
1601 channel_id =
1602 pScanResult->BssDescriptor.channelIdSelf;
1603 else
1604 channel_id =
1605 pScanResult->BssDescriptor.channelId;
1606
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001607 if (pSpectCh && (channel_id == pSpectCh->chNum)) {
1608 if (pSpectCh->rssiAgr <
1609 pScanResult->BssDescriptor.rssi)
1610 pSpectCh->rssiAgr =
1611 pScanResult->BssDescriptor.rssi;
1612
1613 ++pSpectCh->bssCount; /* Increment the count of BSS */
1614
1615 /*
1616 * Connsidering the Extension Channel
1617 * only in a channels
1618 */
1619 switch (operatingBand) {
1620 case eCSR_DOT11_MODE_11a:
1621 sap_interference_rssi_count_5G(
1622 pSpectCh, channelWidth,
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001623 secondaryChannelOffset,
1624 centerFreq,
1625 centerFreq_2,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001626 channel_id,
1627 spectch_start,
1628 spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001629 break;
1630
1631 case eCSR_DOT11_MODE_11g:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001632 sap_interference_rssi_count(pSpectCh,
1633 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001634 break;
1635
1636 case eCSR_DOT11_MODE_abg:
Himanshu Agarwal4f503b82018-03-19 12:10:45 +05301637 if (pSpectCh->chNum >=
1638 SIR_11A_CHANNEL_BEGIN)
1639 sap_interference_rssi_count_5G(
1640 pSpectCh, channelWidth,
1641 secondaryChannelOffset,
1642 centerFreq,
1643 centerFreq_2,
1644 channel_id,
1645 spectch_start,
1646 spectch_end);
1647 else
1648 sap_interference_rssi_count(
1649 pSpectCh,
1650 spectch_start,
1651 spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001652 break;
1653 }
1654
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301655 QDF_TRACE(QDF_MODULE_ID_SAP,
1656 QDF_TRACE_LEVEL_INFO_HIGH,
Jeff Johnsona7c0ddb2017-09-18 08:14:12 -07001657 "In %s, bssdes.ch_self=%d, bssdes.ch_ID=%d, bssdes.rssi=%d, SpectCh.bssCount=%d, pScanResult=%pK, ChannelWidth %d, secondaryChanOffset %d, center frequency %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001658 __func__,
1659 pScanResult->BssDescriptor.
1660 channelIdSelf,
1661 pScanResult->BssDescriptor.channelId,
1662 pScanResult->BssDescriptor.rssi,
1663 pSpectCh->bssCount, pScanResult,
1664 pSpectCh->channelWidth,
1665 secondaryChannelOffset, centerFreq);
1666 pSpectCh++;
1667 break;
1668 } else {
1669 pSpectCh++;
1670 }
1671 }
1672
1673 pScanResult = sme_scan_result_get_next(halHandle, pResult);
1674 }
1675
1676 /* Calculate the weights for all channels in the spectrum pSpectCh */
1677 pSpectCh = pSpectInfoParams->pSpectCh;
1678
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301679 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001680 "In %s, Spectrum Channels Weight", __func__);
1681
1682 for (chn_num = 0; chn_num < (pSpectInfoParams->numSpectChans);
1683 chn_num++) {
1684
1685 /*
1686 rssi : Maximum received signal strength among all BSS on that channel
1687 bssCount : Number of BSS on that channel
1688 */
1689
1690 rssi = (int8_t) pSpectCh->rssiAgr;
Himanshu Agarwal3697f942018-06-13 14:04:26 +05301691 if (ch_in_pcl(sap_ctx, pSpectCh->chNum))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001692 rssi -= PCL_RSSI_DISCOUNT;
1693
Himanshu Agarwal3697f942018-06-13 14:04:26 +05301694 if (rssi < SOFTAP_MIN_RSSI)
1695 rssi = SOFTAP_MIN_RSSI;
1696
hqub6441f22018-08-09 16:15:31 +08001697 if (pSpectCh->weight == SAP_ACS_WEIGHT_MAX) {
1698 pSpectCh->weight_copy = pSpectCh->weight;
Himanshu Agarwalfee2e362018-01-18 20:26:35 +05301699 goto debug_info;
hqub6441f22018-08-09 16:15:31 +08001700 }
Himanshu Agarwalfee2e362018-01-18 20:26:35 +05301701
gaurank kathpalia859c9362018-08-02 23:07:21 +05301702 /* There may be channels in scanlist, which were not sent to
1703 * FW for scanning as part of ACS scan list, but they do have an
1704 * effect on the neighbouring channels, so they help to find a
1705 * suitable channel, but there weight should be max as they were
1706 * and not meant to be included in the ACS scan results.
1707 * So just assign RSSI as -100, bsscount as 0, and weight as max
1708 * to them, so that they always stay low in sorting of best
1709 * channles which were included in ACS scan list
1710 */
1711 found = false;
1712 for (i = 0; i < sap_ctx->num_of_channel; i++) {
1713 if (pSpectCh->chNum == sap_ctx->channelList[i]) {
1714 /* Scan channel was included in ACS scan list */
1715 found = true;
1716 break;
1717 }
1718 }
1719
1720 if (found)
1721 pSpectCh->weight =
1722 SAPDFS_NORMALISE_1000 *
1723 (sapweight_rssi_count(sap_ctx, rssi,
1724 pSpectCh->bssCount) + sap_weight_channel_status(
1725 sap_ctx, sap_get_channel_status(pMac,
gaoleze5108942017-03-31 16:56:42 +08001726 pSpectCh->chNum)));
gaurank kathpalia859c9362018-08-02 23:07:21 +05301727 else {
1728 pSpectCh->weight = SAP_ACS_WEIGHT_MAX;
1729 pSpectCh->rssiAgr = SOFTAP_MIN_RSSI;
1730 rssi = SOFTAP_MIN_RSSI;
1731 pSpectCh->bssCount = SOFTAP_MIN_COUNT;
1732 }
1733
gaoleze5108942017-03-31 16:56:42 +08001734 if (pSpectCh->weight > SAP_ACS_WEIGHT_MAX)
1735 pSpectCh->weight = SAP_ACS_WEIGHT_MAX;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001736 pSpectCh->weight_copy = pSpectCh->weight;
1737
Himanshu Agarwalfee2e362018-01-18 20:26:35 +05301738debug_info:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001739 /* ------ Debug Info ------ */
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301740 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Himanshu Agarwal3697f942018-06-13 14:04:26 +05301741 "In %s, Chan=%d Weight= %d rssiAgr=%d rssi_pcl_discount: %d bssCount=%d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001742 __func__, pSpectCh->chNum, pSpectCh->weight,
Himanshu Agarwal3697f942018-06-13 14:04:26 +05301743 pSpectCh->rssiAgr, rssi, pSpectCh->bssCount);
wadesongcb0ded22018-02-02 17:57:20 +08001744 host_log_acs_chan_spect_weight(pSpectCh->chNum,
1745 (uint16_t)pSpectCh->weight,
1746 pSpectCh->rssiAgr,
1747 pSpectCh->bssCount);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001748 /* ------ Debug Info ------ */
1749 pSpectCh++;
1750 }
gaoleze5108942017-03-31 16:56:42 +08001751 sap_clear_channel_status(pMac);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301752 qdf_mem_free(pBeaconStruct);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001753}
1754
1755/*==========================================================================
1756 FUNCTION sap_chan_sel_exit
1757
1758 DESCRIPTION
1759 Exit function for free out the allocated memory, to be called
1760 at the end of the dfsSelectChannel function
1761
1762 DEPENDENCIES
1763 NA.
1764
1765 PARAMETERS
1766
1767 IN
1768 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
1769
1770 RETURN VALUE
1771 void : NULL
1772
1773 SIDE EFFECTS
1774 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001775static void sap_chan_sel_exit(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001776{
1777 /* Free all the allocated memory */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301778 qdf_mem_free(pSpectInfoParams->pSpectCh);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001779}
1780
1781/*==========================================================================
1782 FUNCTION sap_sort_chl_weight
1783
1784 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07001785 Function to sort the channels with the least weight first for 20MHz channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001786
1787 DEPENDENCIES
1788 NA.
1789
1790 PARAMETERS
1791
1792 IN
1793 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
1794
1795 RETURN VALUE
1796 void : NULL
1797
1798 SIDE EFFECTS
1799 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001800static void sap_sort_chl_weight(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001801{
1802 tSapSpectChInfo temp;
1803
1804 tSapSpectChInfo *pSpectCh = NULL;
1805 uint32_t i = 0, j = 0, minWeightIndex = 0;
1806
1807 pSpectCh = pSpectInfoParams->pSpectCh;
1808 for (i = 0; i < pSpectInfoParams->numSpectChans; i++) {
1809 minWeightIndex = i;
1810 for (j = i + 1; j < pSpectInfoParams->numSpectChans; j++) {
1811 if (pSpectCh[j].weight <
1812 pSpectCh[minWeightIndex].weight) {
1813 minWeightIndex = j;
Yeshwanth Sriram Guntuka273889e2018-02-16 17:11:46 +05301814 } else if (pSpectCh[j].weight ==
1815 pSpectCh[minWeightIndex].weight) {
1816 if (pSpectCh[j].bssCount <
1817 pSpectCh[minWeightIndex].bssCount)
1818 minWeightIndex = j;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001819 }
1820 }
1821 if (minWeightIndex != i) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301822 qdf_mem_copy(&temp, &pSpectCh[minWeightIndex],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001823 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301824 qdf_mem_copy(&pSpectCh[minWeightIndex], &pSpectCh[i],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001825 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301826 qdf_mem_copy(&pSpectCh[i], &temp, sizeof(*pSpectCh));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001827 }
1828 }
1829}
1830
1831/**
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07001832 * set_ht80_chl_bit() - to set available channel to ht80 channel bitmap
bingse2782382017-03-23 10:34:52 +08001833 * @channel_bitmap: Pointer to the chan_bonding_bitmap structure
1834 * @spect_info_params: Pointer to the tSapChSelSpectInfo structure
1835 *
1836 * Return: none
1837 */
1838static void set_ht80_chl_bit(chan_bonding_bitmap *channel_bitmap,
1839 tSapChSelSpectInfo *spec_info_params)
1840{
1841 uint8_t i, j;
1842 tSapSpectChInfo *spec_info;
1843 int start_channel = 0;
1844
1845 channel_bitmap->chanBondingSet[0].startChannel =
1846 acs_ht80_channels[0].chStartNum;
1847 channel_bitmap->chanBondingSet[1].startChannel =
1848 acs_ht80_channels[1].chStartNum;
1849 channel_bitmap->chanBondingSet[2].startChannel =
1850 acs_ht80_channels[2].chStartNum;
1851 channel_bitmap->chanBondingSet[3].startChannel =
1852 acs_ht80_channels[3].chStartNum;
1853 channel_bitmap->chanBondingSet[4].startChannel =
1854 acs_ht80_channels[4].chStartNum;
1855 channel_bitmap->chanBondingSet[5].startChannel =
1856 acs_ht80_channels[5].chStartNum;
1857
1858 spec_info = spec_info_params->pSpectCh;
1859 for (j = 0; j < spec_info_params->numSpectChans; j++) {
1860 for (i = 0; i < MAX_80MHZ_BANDS; i++) {
1861 start_channel =
1862 channel_bitmap->chanBondingSet[i].startChannel;
1863 if (spec_info[j].chNum >= start_channel &&
1864 (spec_info[j].chNum <= start_channel + 12)) {
1865 channel_bitmap->chanBondingSet[i].channelMap |=
1866 1 << ((spec_info[j].chNum -
1867 start_channel)/4);
1868 break;
1869 }
1870 }
1871 }
1872}
1873
1874/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001875 * sap_sort_chl_weight_ht80() - to sort the channels with the least weight
1876 * @pSpectInfoParams: Pointer to the tSapChSelSpectInfo structure
1877 *
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07001878 * Function to sort the channels with the least weight first for HT80 channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001879 *
1880 * Return: none
1881 */
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001882static void sap_sort_chl_weight_ht80(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001883{
1884 uint8_t i, j, n;
1885 tSapSpectChInfo *pSpectInfo;
1886 uint8_t minIdx;
bingse2782382017-03-23 10:34:52 +08001887 int start_channel = 0;
1888 chan_bonding_bitmap *channel_bitmap;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001889
bingse2782382017-03-23 10:34:52 +08001890 channel_bitmap = qdf_mem_malloc(sizeof(chan_bonding_bitmap));
1891 if (NULL == channel_bitmap) {
1892 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
1893 "%s: Failed to allocate memory", __func__);
1894 return;
1895 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001896 pSpectInfo = pSpectInfoParams->pSpectCh;
1897 /* for each HT80 channel, calculate the combined weight of the
1898 four 20MHz weight */
1899 for (i = 0; i < ARRAY_SIZE(acs_ht80_channels); i++) {
1900 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
1901 if (pSpectInfo[j].chNum ==
1902 acs_ht80_channels[i].chStartNum)
1903 break;
1904 }
1905 if (j == pSpectInfoParams->numSpectChans)
1906 continue;
1907
1908 if (!(((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 1].chNum) &&
1909 ((pSpectInfo[j].chNum + 8) ==
1910 pSpectInfo[j + 2].chNum) &&
1911 ((pSpectInfo[j].chNum + 12) ==
1912 pSpectInfo[j + 3].chNum))) {
1913 /*
1914 * some channels does not exist in pSectInfo array,
1915 * skip this channel and those in the same HT80 width
1916 */
1917 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 4;
1918 if ((pSpectInfo[j].chNum + 4) ==
1919 pSpectInfo[j + 1].chNum)
1920 pSpectInfo[j + 1].weight =
1921 SAP_ACS_WEIGHT_MAX * 4;
1922 if ((pSpectInfo[j].chNum + 8) ==
1923 pSpectInfo[j + 2].chNum)
1924 pSpectInfo[j + 2].weight =
1925 SAP_ACS_WEIGHT_MAX * 4;
1926 if ((pSpectInfo[j].chNum + 12) ==
1927 pSpectInfo[j + 3].chNum)
1928 pSpectInfo[j + 3].weight =
1929 SAP_ACS_WEIGHT_MAX * 4;
1930 continue;
1931 }
1932 /*found the channel, add the 4 adjacent channels' weight */
1933 acs_ht80_channels[i].weight = pSpectInfo[j].weight +
1934 pSpectInfo[j + 1].weight + pSpectInfo[j + 2].weight +
1935 pSpectInfo[j + 3].weight;
1936 /* find best channel among 4 channels as the primary channel */
1937 if ((pSpectInfo[j].weight + pSpectInfo[j + 1].weight) <
1938 (pSpectInfo[j + 2].weight + pSpectInfo[j + 3].weight)) {
1939 /* lower 2 channels are better choice */
1940 if (pSpectInfo[j].weight < pSpectInfo[j + 1].weight)
1941 minIdx = 0;
1942 else
1943 minIdx = 1;
1944 } else if (pSpectInfo[j + 2].weight <=
1945 pSpectInfo[j + 3].weight) {
1946 /* upper 2 channels are better choice */
1947 minIdx = 2;
1948 } else {
1949 minIdx = 3;
1950 }
1951
1952 /*
1953 * set all 4 channels to max value first, then reset the
1954 * best channel as the selected primary channel, update its
1955 * weightage with the combined weight value
1956 */
1957 for (n = 0; n < 4; n++)
1958 pSpectInfo[j + n].weight = SAP_ACS_WEIGHT_MAX * 4;
1959
1960 pSpectInfo[j + minIdx].weight = acs_ht80_channels[i].weight;
1961 }
1962
bingse2782382017-03-23 10:34:52 +08001963 /*
1964 * mark the weight of the channel that can't satisfy 80MHZ
1965 * as max value, so that it will be sorted to the bottom
1966 */
1967 set_ht80_chl_bit(channel_bitmap, pSpectInfoParams);
1968 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
1969 for (i = 0; i < MAX_80MHZ_BANDS; i++) {
1970 start_channel =
1971 channel_bitmap->chanBondingSet[i].startChannel;
1972 if (pSpectInfo[j].chNum >= start_channel &&
1973 (pSpectInfo[j].chNum <=
1974 start_channel + 12) &&
1975 channel_bitmap->chanBondingSet[i].channelMap !=
1976 SAP_80MHZ_MASK)
1977 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 4;
1978 }
1979 }
1980
Himanshu Agarwal75e74412018-02-01 20:51:47 +05301981 /*
1982 * Assign max weight(SAP_ACS_WEIGHT_MAX * 4) to 2.4 Ghz channels
1983 * and channel 165 as they cannot be part of a 80Mhz channel bonding.
1984 */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001985 pSpectInfo = pSpectInfoParams->pSpectCh;
1986 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
Himanshu Agarwal75e74412018-02-01 20:51:47 +05301987 if ((pSpectInfo[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_1) &&
1988 pSpectInfo[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_14)) ||
1989 (CHANNEL_165 == pSpectInfo[j].chNum))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001990 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 4;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001991 }
1992
Manishekar Chandrasekaran44e334f2016-05-30 16:42:50 +05301993 sap_sort_chl_weight(pSpectInfoParams);
1994
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001995 pSpectInfo = pSpectInfoParams->pSpectCh;
1996 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301997 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001998 FL("Channel=%d Weight= %d rssi=%d bssCount=%d"),
1999 pSpectInfo->chNum, pSpectInfo->weight,
2000 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
2001 pSpectInfo++;
2002 }
bingse2782382017-03-23 10:34:52 +08002003 qdf_mem_free(channel_bitmap);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002004}
2005
2006/**
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002007 * sap_sort_chl_weight_vht160() - to sort the channels with the least weight
2008 * @pSpectInfoParams: Pointer to the tSapChSelSpectInfo structure
2009 *
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07002010 * Function to sort the channels with the least weight first for VHT160 channels
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002011 *
2012 * Return: none
2013 */
Jeff Johnson464f7ea2016-10-07 10:21:26 -07002014static void sap_sort_chl_weight_vht160(tSapChSelSpectInfo *pSpectInfoParams)
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002015{
2016 uint8_t i, j, n, idx;
2017 tSapSpectChInfo *pSpectInfo;
2018 uint8_t minIdx;
2019
2020 pSpectInfo = pSpectInfoParams->pSpectCh;
2021 /* for each VHT160 channel, calculate the combined weight of the
2022 8 20MHz weight */
2023 for (i = 0; i < ARRAY_SIZE(acs_vht160_channels); i++) {
2024 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2025 if (pSpectInfo[j].chNum ==
2026 acs_vht160_channels[i].chStartNum)
2027 break;
2028 }
2029 if (j == pSpectInfoParams->numSpectChans)
2030 continue;
2031
2032 if (!(((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 1].chNum) &&
2033 ((pSpectInfo[j].chNum + 8) ==
2034 pSpectInfo[j + 2].chNum) &&
2035 ((pSpectInfo[j].chNum + 12) ==
2036 pSpectInfo[j + 3].chNum) &&
2037 ((pSpectInfo[j].chNum + 16) ==
2038 pSpectInfo[j + 4].chNum) &&
2039 ((pSpectInfo[j].chNum + 20) ==
2040 pSpectInfo[j + 5].chNum) &&
2041 ((pSpectInfo[j].chNum + 24) ==
2042 pSpectInfo[j + 6].chNum) &&
2043 ((pSpectInfo[j].chNum + 28) ==
2044 pSpectInfo[j + 7].chNum))) {
2045 /*
2046 * some channels does not exist in pSectInfo array,
2047 * skip this channel and those in the same VHT160 width
2048 */
2049 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 8;
2050 if ((pSpectInfo[j].chNum + 4) ==
2051 pSpectInfo[j + 1].chNum)
2052 pSpectInfo[j + 1].weight =
2053 SAP_ACS_WEIGHT_MAX * 8;
2054 if ((pSpectInfo[j].chNum + 8) ==
2055 pSpectInfo[j + 2].chNum)
2056 pSpectInfo[j + 2].weight =
2057 SAP_ACS_WEIGHT_MAX * 8;
2058 if ((pSpectInfo[j].chNum + 12) ==
2059 pSpectInfo[j + 3].chNum)
2060 pSpectInfo[j + 3].weight =
2061 SAP_ACS_WEIGHT_MAX * 8;
2062 if ((pSpectInfo[j].chNum + 16) ==
2063 pSpectInfo[j + 4].chNum)
2064 pSpectInfo[j + 4].weight =
2065 SAP_ACS_WEIGHT_MAX * 8;
2066 if ((pSpectInfo[j].chNum + 20) ==
2067 pSpectInfo[j + 5].chNum)
2068 pSpectInfo[j + 5].weight =
2069 SAP_ACS_WEIGHT_MAX * 8;
2070 if ((pSpectInfo[j].chNum + 24) ==
2071 pSpectInfo[j + 6].chNum)
2072 pSpectInfo[j + 6].weight =
2073 SAP_ACS_WEIGHT_MAX * 8;
2074 if ((pSpectInfo[j].chNum + 28) ==
2075 pSpectInfo[j + 7].chNum)
2076 pSpectInfo[j + 7].weight =
2077 SAP_ACS_WEIGHT_MAX * 8;
2078 continue;
2079 }
2080 /*found the channel, add the 7 adjacent channels' weight */
2081 acs_vht160_channels[i].weight = pSpectInfo[j].weight +
2082 pSpectInfo[j + 1].weight + pSpectInfo[j + 2].weight +
2083 pSpectInfo[j + 3].weight + pSpectInfo[j + 4].weight +
2084 pSpectInfo[j + 5].weight + pSpectInfo[j + 6].weight +
2085 pSpectInfo[j + 7].weight;
2086
2087 /* find best channel among 8 channels as the primary channel */
2088 if ((pSpectInfo[j].weight + pSpectInfo[j + 1].weight +
2089 pSpectInfo[j + 2].weight + pSpectInfo[j + 3].weight) >
2090 (pSpectInfo[j + 4].weight + pSpectInfo[j + 5].weight +
2091 pSpectInfo[j + 6].weight + pSpectInfo[j + 7].weight))
2092 idx = 4;
2093 else
2094 idx = 0;
2095 /* find best channel among 4 channels as the primary channel */
2096 if ((pSpectInfo[j + idx].weight +
2097 pSpectInfo[j + idx + 1].weight) <
2098 (pSpectInfo[j + idx + 2].weight +
2099 pSpectInfo[j + idx + 3].weight)) {
2100 /* lower 2 channels are better choice */
2101 if (pSpectInfo[j + idx].weight <
2102 pSpectInfo[j + idx + 1].weight)
2103 minIdx = 0 + idx;
2104 else
2105 minIdx = 1 + idx;
2106 } else if (pSpectInfo[j + idx + 2].weight <=
2107 pSpectInfo[j + idx + 3].weight) {
2108 /* upper 2 channels are better choice */
2109 minIdx = 2 + idx;
2110 } else {
2111 minIdx = 3 + idx;
2112 }
2113
2114 /*
2115 * set all 8 channels to max value first, then reset the
2116 * best channel as the selected primary channel, update its
2117 * weightage with the combined weight value
2118 */
2119 for (n = 0; n < 8; n++)
2120 pSpectInfo[j + n].weight = SAP_ACS_WEIGHT_MAX * 8;
2121
2122 pSpectInfo[j + minIdx].weight = acs_vht160_channels[i].weight;
2123 }
2124
Himanshu Agarwal75e74412018-02-01 20:51:47 +05302125 /*
2126 * Assign max weight(SAP_ACS_WEIGHT_MAX * 8) to 2.4 Ghz channels
Kiran Kumar Lokere1a43bcf2018-05-15 15:51:58 -07002127 * and channel 132-173 as they cannot be part of a 160Mhz channel
Himanshu Agarwal75e74412018-02-01 20:51:47 +05302128 * bonding.
2129 */
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002130 pSpectInfo = pSpectInfoParams->pSpectCh;
2131 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
Himanshu Agarwal75e74412018-02-01 20:51:47 +05302132 if ((pSpectInfo[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_1) &&
2133 pSpectInfo[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_14)) ||
2134 (pSpectInfo[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_132) &&
Kiran Kumar Lokere1a43bcf2018-05-15 15:51:58 -07002135 pSpectInfo[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_173)))
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002136 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 8;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002137 }
2138
Manishekar Chandrasekaran44e334f2016-05-30 16:42:50 +05302139 sap_sort_chl_weight(pSpectInfoParams);
2140
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002141 pSpectInfo = pSpectInfoParams->pSpectCh;
2142 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302143 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002144 FL("Channel=%d Weight= %d rssi=%d bssCount=%d"),
2145 pSpectInfo->chNum, pSpectInfo->weight,
2146 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
2147 pSpectInfo++;
2148 }
2149}
2150
2151/**
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302152 * sap_allocate_max_weight_ht40_24_g() - allocate max weight for 40Mhz
2153 * to all 2.4Ghz channels
2154 * @spect_info_params: Pointer to the tSapChSelSpectInfo structure
2155 *
2156 * Return: none
2157 */
2158static void sap_allocate_max_weight_ht40_24_g(
2159 tSapChSelSpectInfo *spect_info_params)
2160{
2161 tSapSpectChInfo *spect_info;
2162 uint8_t j;
2163
2164 /*
2165 * Assign max weight for 40Mhz (SAP_ACS_WEIGHT_MAX * 2) to all
2166 * 2.4 Ghz channels
2167 */
2168 spect_info = spect_info_params->pSpectCh;
2169 for (j = 0; j < spect_info_params->numSpectChans; j++) {
2170 if ((spect_info[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_1) &&
2171 spect_info[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_14)))
2172 spect_info[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2173 }
2174}
2175
2176/**
2177 * sap_allocate_max_weight_ht40_5_g() - allocate max weight for 40Mhz
2178 * to all 5Ghz channels
2179 * @spect_info_params: Pointer to the tSapChSelSpectInfo structure
2180 *
2181 * Return: none
2182 */
2183static void sap_allocate_max_weight_ht40_5_g(
2184 tSapChSelSpectInfo *spect_info_params)
2185{
2186 tSapSpectChInfo *spect_info;
2187 uint8_t j;
2188
2189 /*
2190 * Assign max weight for 40Mhz (SAP_ACS_WEIGHT_MAX * 2) to all
2191 * 5 Ghz channels
2192 */
2193 spect_info = spect_info_params->pSpectCh;
2194 for (j = 0; j < spect_info_params->numSpectChans; j++) {
2195 if ((spect_info[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_36) &&
Kiran Kumar Lokere1a43bcf2018-05-15 15:51:58 -07002196 spect_info[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_173)))
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302197 spect_info[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2198 }
2199}
2200
2201/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002202 * sap_sort_chl_weight_ht40_24_g() - to sort channel with the least weight
2203 * @pSpectInfoParams: Pointer to the tSapChSelSpectInfo structure
2204 *
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07002205 * Function to sort the channels with the least weight first for HT40 channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002206 *
2207 * Return: none
2208 */
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002209static void sap_sort_chl_weight_ht40_24_g(tSapChSelSpectInfo *pSpectInfoParams,
2210 v_REGDOMAIN_t domain)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002211{
2212 uint8_t i, j;
2213 tSapSpectChInfo *pSpectInfo;
2214 uint32_t tmpWeight1, tmpWeight2;
bingse2782382017-03-23 10:34:52 +08002215 uint32_t ht40plus2gendch = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002216
2217 pSpectInfo = pSpectInfoParams->pSpectCh;
2218 /*
2219 * for each HT40 channel, calculate the combined weight of the
2220 * two 20MHz weight
2221 */
2222 for (i = 0; i < ARRAY_SIZE(acs_ht40_channels24_g); i++) {
2223 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2224 if (pSpectInfo[j].chNum ==
2225 acs_ht40_channels24_g[i].chStartNum)
2226 break;
2227 }
2228 if (j == pSpectInfoParams->numSpectChans)
2229 continue;
2230
2231 if (!((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 4].chNum)) {
2232 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2233 continue;
2234 }
2235 /*
2236 * check if there is another channel combination possiblity
2237 * e.g., {1, 5} & {5, 9}
2238 */
2239 if ((pSpectInfo[j + 4].chNum + 4) == pSpectInfo[j + 8].chNum) {
2240 /* need to compare two channel pairs */
2241 tmpWeight1 = pSpectInfo[j].weight +
2242 pSpectInfo[j + 4].weight;
2243 tmpWeight2 = pSpectInfo[j + 4].weight +
2244 pSpectInfo[j + 8].weight;
2245 if (tmpWeight1 <= tmpWeight2) {
2246 if (pSpectInfo[j].weight <=
2247 pSpectInfo[j + 4].weight) {
2248 pSpectInfo[j].weight =
2249 tmpWeight1;
2250 pSpectInfo[j + 4].weight =
2251 SAP_ACS_WEIGHT_MAX * 2;
2252 pSpectInfo[j + 8].weight =
2253 SAP_ACS_WEIGHT_MAX * 2;
2254 } else {
2255 pSpectInfo[j + 4].weight =
2256 tmpWeight1;
2257 /* for secondary channel selection */
2258 pSpectInfo[j].weight =
2259 SAP_ACS_WEIGHT_MAX * 2
2260 - 1;
2261 pSpectInfo[j + 8].weight =
2262 SAP_ACS_WEIGHT_MAX * 2;
2263 }
2264 } else {
2265 if (pSpectInfo[j + 4].weight <=
2266 pSpectInfo[j + 8].weight) {
2267 pSpectInfo[j + 4].weight =
2268 tmpWeight2;
2269 pSpectInfo[j].weight =
2270 SAP_ACS_WEIGHT_MAX * 2;
2271 /* for secondary channel selection */
2272 pSpectInfo[j + 8].weight =
2273 SAP_ACS_WEIGHT_MAX * 2
2274 - 1;
2275 } else {
2276 pSpectInfo[j + 8].weight =
2277 tmpWeight2;
2278 pSpectInfo[j].weight =
2279 SAP_ACS_WEIGHT_MAX * 2;
2280 pSpectInfo[j + 4].weight =
2281 SAP_ACS_WEIGHT_MAX * 2;
2282 }
2283 }
2284 } else {
bingsaa6f96a2017-09-11 09:49:43 +08002285 tmpWeight1 = pSpectInfo[j].weight_copy +
2286 pSpectInfo[j + 4].weight_copy;
2287 if (pSpectInfo[j].weight_copy <=
2288 pSpectInfo[j + 4].weight_copy) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002289 pSpectInfo[j].weight = tmpWeight1;
2290 pSpectInfo[j + 4].weight =
2291 SAP_ACS_WEIGHT_MAX * 2;
2292 } else {
2293 pSpectInfo[j + 4].weight = tmpWeight1;
2294 pSpectInfo[j].weight =
2295 SAP_ACS_WEIGHT_MAX * 2;
2296 }
2297 }
2298 }
bingse2782382017-03-23 10:34:52 +08002299 /*
2300 * Every channel should be checked. Add the check for the omissive
2301 * channel. Mark the channel whose combination can't satisfy 40MHZ
2302 * as max value, so that it will be sorted to the bottom.
2303 */
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002304 if (REGDOMAIN_FCC == domain)
bingse2782382017-03-23 10:34:52 +08002305 ht40plus2gendch = HT40PLUS_2G_FCC_CH_END;
2306 else
2307 ht40plus2gendch = HT40PLUS_2G_EURJAP_CH_END;
2308 for (i = HT40MINUS_2G_CH_START; i <= ht40plus2gendch; i++) {
2309 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2310 if (pSpectInfo[j].chNum == i &&
2311 ((pSpectInfo[j].chNum + 4) !=
2312 pSpectInfo[j+4].chNum) &&
2313 ((pSpectInfo[j].chNum - 4) !=
2314 pSpectInfo[j-4].chNum))
2315 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2316 }
2317 }
2318 for (i = ht40plus2gendch + 1; i <= HT40MINUS_2G_CH_END; i++) {
2319 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2320 if (pSpectInfo[j].chNum == i &&
2321 (pSpectInfo[j].chNum - 4) !=
2322 pSpectInfo[j-4].chNum)
2323 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2324 }
2325 }
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302326
2327 pSpectInfo = pSpectInfoParams->pSpectCh;
2328 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
2329 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2330 "In %s, Channel=%d Weight= %d rssi=%d bssCount=%d",
2331 __func__, pSpectInfo->chNum, pSpectInfo->weight,
2332 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
2333 pSpectInfo++;
2334 }
2335
Manishekar Chandrasekaran44e334f2016-05-30 16:42:50 +05302336 sap_sort_chl_weight(pSpectInfoParams);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002337}
2338
2339/*==========================================================================
2340 FUNCTION sap_sort_chl_weight_ht40_5_g
2341
2342 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07002343 Function to sort the channels with the least weight first for HT40 channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002344
2345 DEPENDENCIES
2346 NA.
2347
2348 PARAMETERS
2349
2350 IN
2351 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
2352
2353 RETURN VALUE
2354 void : NULL
2355
2356 SIDE EFFECTS
2357 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -07002358static void sap_sort_chl_weight_ht40_5_g(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002359{
2360 uint8_t i, j;
2361 tSapSpectChInfo *pSpectInfo;
2362
2363 pSpectInfo = pSpectInfoParams->pSpectCh;
2364 /*for each HT40 channel, calculate the combined weight of the
2365 two 20MHz weight */
2366 for (i = 0; i < ARRAY_SIZE(acs_ht40_channels5_g); i++) {
2367 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2368 if (pSpectInfo[j].chNum ==
2369 acs_ht40_channels5_g[i].chStartNum)
2370 break;
2371 }
2372 if (j == pSpectInfoParams->numSpectChans)
2373 continue;
2374
2375 /* found the channel, add the two adjacent channels' weight */
2376 if ((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 1].chNum) {
2377 acs_ht40_channels5_g[i].weight = pSpectInfo[j].weight +
2378 pSpectInfo[j + 1].weight;
2379 /* select better of the adjact channel as the primary channel */
2380 if (pSpectInfo[j].weight <= pSpectInfo[j + 1].weight) {
2381 pSpectInfo[j].weight =
2382 acs_ht40_channels5_g[i].weight;
2383 /* mark the adjacent channel's weight as max value so
2384 that it will be sorted to the bottom */
2385 pSpectInfo[j + 1].weight =
2386 SAP_ACS_WEIGHT_MAX * 2;
2387 } else {
2388 pSpectInfo[j + 1].weight =
2389 acs_ht40_channels5_g[i].weight;
2390 /* mark the adjacent channel's weight as max value so
2391 that it will be sorted to the bottom */
2392 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2393 }
2394
2395 } else
2396 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2397 }
2398
bingse2782382017-03-23 10:34:52 +08002399 /*
2400 *Every channel should be checked. Add the check for the omissive
2401 * channel. Mark the channel whose combination can't satisfy 40MHZ
2402 * as max value, so that it will be sorted to the bottom
2403 */
2404 for (j = 1; j < pSpectInfoParams->numSpectChans; j++) {
2405 for (i = 0; i < ARRAY_SIZE(acs_ht40_channels5_g); i++) {
2406 if (pSpectInfo[j].chNum ==
2407 (acs_ht40_channels5_g[i].chStartNum +
2408 4) &&
2409 pSpectInfo[j - 1].chNum !=
2410 acs_ht40_channels5_g[i].chStartNum) {
2411 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2412 break;
2413 }
2414 }
2415 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002416 /* avoid channel 165 by setting its weight to max */
2417 pSpectInfo = pSpectInfoParams->pSpectCh;
2418 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2419 if (CHANNEL_165 == pSpectInfo[j].chNum) {
2420 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2421 break;
2422 }
2423 }
2424
2425 pSpectInfo = pSpectInfoParams->pSpectCh;
2426 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302427 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002428 "In %s, Channel=%d Weight= %d rssi=%d bssCount=%d",
2429 __func__, pSpectInfo->chNum, pSpectInfo->weight,
2430 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
2431 pSpectInfo++;
2432 }
2433
2434 sap_sort_chl_weight(pSpectInfoParams);
2435}
2436
2437/*==========================================================================
2438 FUNCTION sap_sort_chl_weight_all
2439
2440 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07002441 Function to sort the channels with the least weight first
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002442
2443 DEPENDENCIES
2444 NA.
2445
2446 PARAMETERS
2447
2448 IN
Jeff Johnsone13d8062017-09-28 06:54:55 -07002449 sap_ctx : Pointer to the struct sap_context *structure
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002450 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
2451
2452 RETURN VALUE
2453 void : NULL
2454
2455 SIDE EFFECTS
2456 ============================================================================*/
Jeff Johnsone13d8062017-09-28 06:54:55 -07002457static void sap_sort_chl_weight_all(struct sap_context *sap_ctx,
Jeff Johnson464f7ea2016-10-07 10:21:26 -07002458 tSapChSelSpectInfo *pSpectInfoParams,
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002459 uint32_t operatingBand,
2460 v_REGDOMAIN_t domain)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002461{
2462 tSapSpectChInfo *pSpectCh = NULL;
2463 uint32_t j = 0;
2464#ifndef SOFTAP_CHANNEL_RANGE
2465 uint32_t i = 0;
2466#endif
2467
2468 pSpectCh = pSpectInfoParams->pSpectCh;
2469#ifdef SOFTAP_CHANNEL_RANGE
2470
Jeff Johnsone13d8062017-09-28 06:54:55 -07002471 switch (sap_ctx->acs_cfg->ch_width) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002472 case CH_WIDTH_40MHZ:
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302473 /*
2474 * Assign max weight to all 5Ghz channels when operating band
2475 * is 11g and to all 2.4Ghz channels when operating band is 11a
2476 * or 11abg to avoid selection in ACS algorithm for starting SAP
2477 */
2478 if (eCSR_DOT11_MODE_11g == operatingBand) {
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002479 sap_sort_chl_weight_ht40_24_g(pSpectInfoParams, domain);
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302480 sap_allocate_max_weight_ht40_5_g(pSpectInfoParams);
2481 } else {
2482 sap_allocate_max_weight_ht40_24_g(pSpectInfoParams);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002483 sap_sort_chl_weight_ht40_5_g(pSpectInfoParams);
2484 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002485 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002486 case CH_WIDTH_80MHZ:
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002487 case CH_WIDTH_80P80MHZ:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002488 sap_sort_chl_weight_ht80(pSpectInfoParams);
2489 break;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002490 case CH_WIDTH_160MHZ:
2491 sap_sort_chl_weight_vht160(pSpectInfoParams);
2492 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002493 case CH_WIDTH_20MHZ:
2494 default:
2495 /* Sorting the channels as per weights as 20MHz channels */
2496 sap_sort_chl_weight(pSpectInfoParams);
2497 }
2498
2499#else
2500 /* Sorting the channels as per weights */
2501 for (i = 0; i < SPECT_24GHZ_CH_COUNT; i++) {
2502 minWeightIndex = i;
2503 for (j = i + 1; j < SPECT_24GHZ_CH_COUNT; j++) {
2504 if (pSpectCh[j].weight <
2505 pSpectCh[minWeightIndex].weight) {
2506 minWeightIndex = j;
2507 }
2508 }
2509 if (minWeightIndex != i) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302510 qdf_mem_copy(&temp, &pSpectCh[minWeightIndex],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002511 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302512 qdf_mem_copy(&pSpectCh[minWeightIndex], &pSpectCh[i],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002513 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302514 qdf_mem_copy(&pSpectCh[i], &temp, sizeof(*pSpectCh));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002515 }
2516 }
2517#endif
2518
2519 /* For testing */
Ravi Joshi9788fcd2018-02-13 15:12:22 -08002520 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002521 "In %s, Sorted Spectrum Channels Weight", __func__);
2522 pSpectCh = pSpectInfoParams->pSpectCh;
2523 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Ravi Joshi9788fcd2018-02-13 15:12:22 -08002524 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002525 "In %s, Channel=%d Weight= %d rssi=%d bssCount=%d",
2526 __func__, pSpectCh->chNum, pSpectCh->weight,
2527 pSpectCh->rssiAgr, pSpectCh->bssCount);
2528 pSpectCh++;
2529 }
2530
2531}
2532
Naveen Rawatbec64d92017-09-13 14:35:21 -07002533/**
2534 * sap_is_ch_non_overlap() - returns true if non-overlapping channel
2535 * @sap_ctx: Sap context
2536 * @ch: channel number
2537 *
2538 * Returns: true if non-overlapping (1, 6, 11) channel, false otherwise
2539 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002540static bool sap_is_ch_non_overlap(struct sap_context *sap_ctx, uint16_t ch)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002541{
Naveen Rawatbec64d92017-09-13 14:35:21 -07002542 if (sap_ctx->enableOverLapCh)
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002543 return true;
Naveen Rawatbec64d92017-09-13 14:35:21 -07002544
2545 if ((ch == CHANNEL_1) || (ch == CHANNEL_6) || (ch == CHANNEL_11))
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002546 return true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002547
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002548 return false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002549}
2550
Dustin Brown0ce56d32016-10-17 16:18:03 -07002551#ifdef FEATURE_WLAN_CH_AVOID
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002552/**
2553 * sap_select_channel_no_scan_result() - select SAP channel when no scan results
2554 * are available.
2555 * @sap_ctx: Sap context
2556 *
2557 * Returns: channel number if success, 0 otherwise
2558 */
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302559static uint8_t sap_select_channel_no_scan_result(tHalHandle hal,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002560 struct sap_context *sap_ctx)
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002561{
Mohit Khanna841044f2016-03-25 16:16:24 -07002562 enum channel_state ch_type;
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002563 uint8_t i, first_safe_ch_in_range = SAP_CHANNEL_NOT_SELECTED;
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302564 uint32_t dfs_master_cap_enabled;
Dustin Brown0ce56d32016-10-17 16:18:03 -07002565 uint32_t start_ch_num = sap_ctx->acs_cfg->start_ch;
2566 uint32_t end_ch_num = sap_ctx->acs_cfg->end_ch;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002567 tpAniSirGlobal mac_ctx = NULL;
2568
2569 mac_ctx = PMAC_STRUCT(hal);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002570
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002571 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2572 FL("start - end: %d - %d"), start_ch_num, end_ch_num);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002573
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302574 sme_cfg_get_int(hal, WNI_CFG_DFS_MASTER_ENABLED,
2575 &dfs_master_cap_enabled);
2576
2577 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2578 "%s: dfs_master %x", __func__, dfs_master_cap_enabled);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002579
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002580 /* get a channel in PCL and within the range */
2581 for (i = 0; i < sap_ctx->acs_cfg->pcl_ch_count; i++) {
2582 if ((sap_ctx->acs_cfg->pcl_channels[i] < start_ch_num) ||
2583 (sap_ctx->acs_cfg->pcl_channels[i] > end_ch_num))
2584 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002585
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002586 first_safe_ch_in_range = sap_ctx->acs_cfg->pcl_channels[i];
2587 break;
2588 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002589
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002590 if (SAP_CHANNEL_NOT_SELECTED != first_safe_ch_in_range)
2591 return first_safe_ch_in_range;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002592
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002593 for (i = 0; i < NUM_CHANNELS; i++) {
2594 if ((safe_channels[i].channelNumber < start_ch_num) ||
2595 (safe_channels[i].channelNumber > end_ch_num))
2596 continue;
2597
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002598 ch_type = wlan_reg_get_channel_state(mac_ctx->pdev,
2599 safe_channels[i].channelNumber);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002600
2601 if ((ch_type == CHANNEL_STATE_DISABLE) ||
2602 (ch_type == CHANNEL_STATE_INVALID))
2603 continue;
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302604 if ((!dfs_master_cap_enabled) &&
2605 (CHANNEL_STATE_DFS == ch_type)) {
2606 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2607 "%s: DFS master mode disabled. Skip DFS channel %d",
2608 __func__, safe_channels[i].channelNumber);
2609 continue;
2610 }
Agrawal Ashish65634612016-08-18 13:24:32 +05302611 if ((sap_ctx->dfs_mode == ACS_DFS_MODE_DISABLE) &&
2612 (CHANNEL_STATE_DFS == ch_type))
2613 continue;
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302614
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002615 if (safe_channels[i].isSafe == true) {
2616 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2617 FL("channel %d in the configuration is safe"),
2618 safe_channels[i].channelNumber);
2619 first_safe_ch_in_range = safe_channels[i].channelNumber;
2620 break;
2621 }
2622
2623 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2624 FL("channel %d in the configuration is unsafe"),
2625 safe_channels[i].channelNumber);
2626 }
2627
2628 /* if no channel selected return SAP_CHANNEL_NOT_SELECTED */
2629 return first_safe_ch_in_range;
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002630}
Dustin Brown0ce56d32016-10-17 16:18:03 -07002631#else
2632static uint8_t sap_select_channel_no_scan_result(tHalHandle hal,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002633 struct sap_context *sap_ctx)
Dustin Brown0ce56d32016-10-17 16:18:03 -07002634{
2635 uint32_t start_ch_num = sap_ctx->acs_cfg->start_ch;
2636
2637 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2638 FL("start - end: %d - %d"),
2639 start_ch_num,
2640 sap_ctx->acs_cfg->end_ch);
2641
2642 sap_ctx->acs_cfg->pri_ch = start_ch_num;
2643 sap_ctx->acs_cfg->ht_sec_ch = 0;
2644
2645 /* pick the first channel in configured range */
2646 return start_ch_num;
2647}
2648#endif /* FEATURE_WLAN_CH_AVOID */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002649
2650/**
2651 * sap_select_channel() - select SAP channel
2652 * @hal: Pointer to HAL handle
2653 * @sap_ctx: Sap context
2654 * @scan_result: Pointer to tScanResultHandle
2655 *
2656 * Runs a algorithm to select the best channel to operate in based on BSS
2657 * rssi and bss count on each channel
2658 *
2659 * Returns: channel number if success, 0 otherwise
2660 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002661uint8_t sap_select_channel(tHalHandle hal, struct sap_context *sap_ctx,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002662 tScanResultHandle scan_result)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002663{
2664 /* DFS param object holding all the data req by the algo */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002665 tSapChSelSpectInfo spect_info_obj = { NULL, 0 };
2666 tSapChSelSpectInfo *spect_info = &spect_info_obj;
2667 uint8_t best_ch_num = SAP_CHANNEL_NOT_SELECTED;
bingse2782382017-03-23 10:34:52 +08002668 uint32_t ht40plus2gendch = 0;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002669 v_REGDOMAIN_t domain;
Arif Hussain21ad4342017-12-21 12:00:54 -08002670 uint8_t country[CDS_COUNTRY_CODE_LEN + 1];
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002671#ifdef SOFTAP_CHANNEL_RANGE
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002672 uint8_t count;
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002673 uint32_t start_ch_num, end_ch_num, tmp_ch_num, operating_band = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002674#endif
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002675 tpAniSirGlobal mac_ctx;
2676
2677 mac_ctx = PMAC_STRUCT(hal);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302678 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002679 "In %s, Running SAP Ch Select", __func__);
2680
2681#ifdef FEATURE_WLAN_CH_AVOID
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002682 sap_update_unsafe_channel_list(hal, sap_ctx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002683#endif
2684
gaoleze5108942017-03-31 16:56:42 +08002685 /*
2686 * If ACS weight is not enabled on noise_floor/channel_free/tx_power,
2687 * then skip acs process if no bss found.
2688 */
2689 if (NULL == scan_result &&
2690 !(sap_ctx->auto_channel_select_weight & 0xffff00)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302691 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002692 FL("No external AP present"));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002693
2694#ifndef SOFTAP_CHANNEL_RANGE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002695 return SAP_CHANNEL_NOT_SELECTED;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002696#else
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302697 return sap_select_channel_no_scan_result(hal, sap_ctx);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002698#endif
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002699 }
2700
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002701 /* Initialize the structure pointed by spect_info */
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002702 if (sap_chan_sel_init(hal, spect_info, sap_ctx) != true) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302703 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002704 FL("Ch Select initialization failed"));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002705 return SAP_CHANNEL_NOT_SELECTED;
2706 }
2707 /* Compute the weight of the entire spectrum in the operating band */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002708 sap_compute_spect_weight(spect_info, hal, scan_result, sap_ctx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002709
2710#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
2711 /* process avoid channel IE to collect all channels to avoid */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002712 sap_process_avoid_ie(hal, sap_ctx, scan_result, spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002713#endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
2714
Paul Zhang0f85b412018-01-18 19:14:51 +08002715 wlan_reg_read_current_country(mac_ctx->psoc, country);
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002716 wlan_reg_get_domain_from_country_code(&domain, country, SOURCE_DRIVER);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002717#ifdef SOFTAP_CHANNEL_RANGE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002718 start_ch_num = sap_ctx->acs_cfg->start_ch;
2719 end_ch_num = sap_ctx->acs_cfg->end_ch;
2720 SET_ACS_BAND(operating_band, sap_ctx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002721
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002722 sap_ctx->acsBestChannelInfo.channelNum = 0;
2723 sap_ctx->acsBestChannelInfo.weight = SAP_ACS_WEIGHT_MAX;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002724
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002725 /* Sort the ch lst as per the computed weights, lesser weight first. */
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002726 sap_sort_chl_weight_all(sap_ctx, spect_info, operating_band, domain);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002727
2728 /*Loop till get the best channel in the given range */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002729 for (count = 0; count < spect_info->numSpectChans; count++) {
2730 if ((start_ch_num > spect_info->pSpectCh[count].chNum) ||
2731 (end_ch_num < spect_info->pSpectCh[count].chNum))
2732 continue;
2733
2734 if (best_ch_num == SAP_CHANNEL_NOT_SELECTED) {
2735 best_ch_num = spect_info->pSpectCh[count].chNum;
2736 /* check if best_ch_num is in preferred channel list */
2737 best_ch_num =
2738 sap_select_preferred_channel_from_channel_list(
2739 best_ch_num, sap_ctx, spect_info);
2740 /* if not in preferred ch lst, go to nxt best ch */
2741 if (best_ch_num == SAP_CHANNEL_NOT_SELECTED)
2742 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002743
2744#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002745 /*
2746 * Weight of the channels(device's AP is operating)
Jeff Johnson2cc31fd2018-05-05 23:54:23 -07002747 * increased to MAX+1 so that they will be chosen only
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002748 * when there is no other best channel to choose
2749 */
2750 if (sap_check_in_avoid_ch_list(sap_ctx, best_ch_num)) {
2751 best_ch_num = SAP_CHANNEL_NOT_SELECTED;
2752 continue;
2753 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002754#endif
2755
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002756 sap_ctx->acsBestChannelInfo.channelNum = best_ch_num;
2757 sap_ctx->acsBestChannelInfo.weight =
2758 spect_info->pSpectCh[count].weight_copy;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002759 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002760
2761 if (best_ch_num == SAP_CHANNEL_NOT_SELECTED)
2762 continue;
2763
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002764 if (operating_band != eCSR_DOT11_MODE_11g) {
2765 QDF_TRACE(QDF_MODULE_ID_SAP,
2766 QDF_TRACE_LEVEL_INFO_HIGH,
2767 "operating_band %d", operating_band);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002768 continue;
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002769 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002770
2771 /* Give preference to Non-overlap channels */
Naveen Rawatbec64d92017-09-13 14:35:21 -07002772 if (false == sap_is_ch_non_overlap(sap_ctx,
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002773 spect_info->pSpectCh[count].chNum)) {
2774 QDF_TRACE(QDF_MODULE_ID_SAP,
2775 QDF_TRACE_LEVEL_INFO_HIGH,
Naveen Rawatbec64d92017-09-13 14:35:21 -07002776 FL("ch: %d skipped as its overlapping ch"),
2777 spect_info->pSpectCh[count].chNum);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002778 continue;
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002779 }
2780
2781 if (wlan_reg_is_dfs_ch(mac_ctx->pdev,
2782 spect_info->pSpectCh[count].chNum) &&
2783 policy_mgr_disallow_mcc(mac_ctx->psoc,
2784 spect_info->pSpectCh[count].chNum)) {
2785 QDF_TRACE(QDF_MODULE_ID_SAP,
2786 QDF_TRACE_LEVEL_INFO_HIGH,
2787 "No DFS MCC");
2788 continue;
2789 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002790
bings14d1d3b2017-08-03 11:14:29 +08002791 if (spect_info->pSpectCh[count].weight_copy >
2792 sap_ctx->acsBestChannelInfo.weight)
2793 continue;
2794
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002795 tmp_ch_num = spect_info->pSpectCh[count].chNum;
gaoleze5108942017-03-31 16:56:42 +08002796 tmp_ch_num = sap_channel_in_acs_channel_list(
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002797 tmp_ch_num, sap_ctx, spect_info);
2798 if (tmp_ch_num == SAP_CHANNEL_NOT_SELECTED)
2799 continue;
2800
2801 best_ch_num = tmp_ch_num;
2802 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002803 }
2804#else
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002805 /* Sort the ch lst as per the computed weights, lesser weight first. */
2806 sap_sort_chl_weight_all(sap_ctx, hal, spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002807 /* Get the first channel in sorted array as best 20M Channel */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002808 best_ch_num = (uint8_t) spect_info->pSpectCh[0].chNum;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002809 /* Select Best Channel from Channel List if Configured */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002810 best_ch_num = sap_select_preferred_channel_from_channel_list(
2811 best_ch_num, sap_ctx, spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002812#endif
2813
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002814 /*
2815 * in case the best channel seleted is not in PCL and there is another
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002816 * channel which has same weightage and is in PCL, choose the one in
2817 * PCL
2818 */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002819 for (count = 0; count < spect_info->numSpectChans; count++) {
2820 if (!ch_in_pcl(sap_ctx, spect_info->pSpectCh[count].chNum) ||
2821 (spect_info->pSpectCh[count].weight !=
2822 sap_ctx->acsBestChannelInfo.weight))
2823 continue;
2824
2825 if (sap_select_preferred_channel_from_channel_list(
2826 spect_info->pSpectCh[count].chNum, sap_ctx, spect_info)
2827 == SAP_CHANNEL_NOT_SELECTED)
2828 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002829
2830#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002831 if (sap_check_in_avoid_ch_list(sap_ctx, best_ch_num))
2832 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002833#endif
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002834 best_ch_num = spect_info->pSpectCh[count].chNum;
2835 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2836 FL("change best channel to %d in PCL"), best_ch_num);
2837 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002838 }
2839
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002840 sap_ctx->acs_cfg->pri_ch = best_ch_num;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002841 /* determine secondary channel for 2.4G channel 5, 6, 7 in HT40 */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002842 if ((operating_band != eCSR_DOT11_MODE_11g) ||
2843 (sap_ctx->acs_cfg->ch_width != CH_WIDTH_40MHZ))
2844 goto sap_ch_sel_end;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002845 if (REGDOMAIN_FCC == domain)
bingse2782382017-03-23 10:34:52 +08002846 ht40plus2gendch = HT40PLUS_2G_FCC_CH_END;
2847 else
2848 ht40plus2gendch = HT40PLUS_2G_EURJAP_CH_END;
2849 if ((best_ch_num >= HT40MINUS_2G_CH_START) &&
2850 (best_ch_num <= ht40plus2gendch)) {
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002851 int weight_below, weight_above, i;
2852 tSapSpectChInfo *pspect_info;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002853
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002854 weight_below = weight_above = SAP_ACS_WEIGHT_MAX;
2855 pspect_info = spect_info->pSpectCh;
2856 for (i = 0; i < spect_info->numSpectChans; i++) {
2857 if (pspect_info[i].chNum == (best_ch_num - 4))
2858 weight_below = pspect_info[i].weight;
2859 if (pspect_info[i].chNum == (best_ch_num + 4))
2860 weight_above = pspect_info[i].weight;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002861 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002862
2863 if (weight_below < weight_above)
2864 sap_ctx->acs_cfg->ht_sec_ch =
2865 sap_ctx->acs_cfg->pri_ch - 4;
2866 else
2867 sap_ctx->acs_cfg->ht_sec_ch =
2868 sap_ctx->acs_cfg->pri_ch + 4;
2869 } else if (best_ch_num >= 1 && best_ch_num <= 4) {
2870 sap_ctx->acs_cfg->ht_sec_ch = sap_ctx->acs_cfg->pri_ch + 4;
bingse2782382017-03-23 10:34:52 +08002871 } else if (best_ch_num >= ht40plus2gendch && best_ch_num <=
2872 HT40MINUS_2G_CH_END) {
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002873 sap_ctx->acs_cfg->ht_sec_ch = sap_ctx->acs_cfg->pri_ch - 4;
2874 } else if (best_ch_num == 14) {
2875 sap_ctx->acs_cfg->ht_sec_ch = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002876 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002877 sap_ctx->secondary_ch = sap_ctx->acs_cfg->ht_sec_ch;
2878
2879sap_ch_sel_end:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002880 /* Free all the allocated memory */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002881 sap_chan_sel_exit(spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002882
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302883 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002884 FL("Running SAP Ch select Completed, Ch=%d"), best_ch_num);
wadesongcb0ded22018-02-02 17:57:20 +08002885 host_log_acs_best_chan(best_ch_num, sap_ctx->acsBestChannelInfo.weight);
2886
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002887 if (best_ch_num > 0 && best_ch_num <= 252)
2888 return best_ch_num;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002889 else
2890 return SAP_CHANNEL_NOT_SELECTED;
2891}