blob: d29aa9f11f2c76425c737da9b6a5779c809345be [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},
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800160};
161#endif
162
163typedef struct {
164 uint16_t chStartNum;
165 uint32_t weight;
166} sapAcsChannelInfo;
167
168sapAcsChannelInfo acs_ht40_channels5_g[] = {
169 {36, SAP_ACS_WEIGHT_MAX},
170 {44, SAP_ACS_WEIGHT_MAX},
171 {52, SAP_ACS_WEIGHT_MAX},
172 {60, SAP_ACS_WEIGHT_MAX},
173 {100, SAP_ACS_WEIGHT_MAX},
174 {108, SAP_ACS_WEIGHT_MAX},
175 {116, SAP_ACS_WEIGHT_MAX},
176 {124, SAP_ACS_WEIGHT_MAX},
177 {132, SAP_ACS_WEIGHT_MAX},
178 {140, SAP_ACS_WEIGHT_MAX},
179 {149, SAP_ACS_WEIGHT_MAX},
180 {157, SAP_ACS_WEIGHT_MAX},
181};
182
183sapAcsChannelInfo acs_ht80_channels[] = {
184 {36, SAP_ACS_WEIGHT_MAX},
185 {52, SAP_ACS_WEIGHT_MAX},
186 {100, SAP_ACS_WEIGHT_MAX},
187 {116, SAP_ACS_WEIGHT_MAX},
188 {132, SAP_ACS_WEIGHT_MAX},
189 {149, SAP_ACS_WEIGHT_MAX},
190};
191
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -0700192sapAcsChannelInfo acs_vht160_channels[] = {
193 {36, SAP_ACS_WEIGHT_MAX},
194 {100, SAP_ACS_WEIGHT_MAX},
195};
196
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800197sapAcsChannelInfo acs_ht40_channels24_g[] = {
198 {1, SAP_ACS_WEIGHT_MAX},
199 {2, SAP_ACS_WEIGHT_MAX},
200 {3, SAP_ACS_WEIGHT_MAX},
201 {4, SAP_ACS_WEIGHT_MAX},
202 {9, SAP_ACS_WEIGHT_MAX},
203};
204
205#define CHANNEL_165 165
206
207/* rssi discount for channels in PCL */
208#define PCL_RSSI_DISCOUNT 10
209
210#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
211/**
212 * sap_check_n_add_channel() - checks and add given channel in sap context's
213 * avoid_channels_info struct
214 * @sap_ctx: sap context.
215 * @new_channel: channel to be added to sap_ctx's avoid ch info
216 *
217 * sap_ctx contains sap_avoid_ch_info strcut containing the list of channels on
218 * which MDM device's AP with MCC was detected. This function will add channels
219 * to that list after checking for duplicates.
220 *
221 * Return: true: if channel was added or already present
222 * else false: if channel list was already full.
223 */
Tang Yingying523322d2017-01-17 23:28:43 +0800224static bool
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700225sap_check_n_add_channel(struct sap_context *sap_ctx,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800226 uint8_t new_channel)
227{
228 uint8_t i = 0;
229 struct sap_avoid_channels_info *ie_info =
230 &sap_ctx->sap_detected_avoid_ch_ie;
231
232 for (i = 0; i < sizeof(ie_info->channels); i++) {
233 if (ie_info->channels[i] == new_channel)
234 break;
235
236 if (ie_info->channels[i] == 0) {
237 ie_info->channels[i] = new_channel;
238 break;
239 }
240 }
241 if (i == sizeof(ie_info->channels))
242 return false;
243 else
244 return true;
245}
246/**
247 * sap_check_n_add_overlapped_chnls() - checks & add overlapped channels
248 * to primary channel in 2.4Ghz band.
249 * @sap_ctx: sap context.
250 * @primary_chnl: primary channel to be avoided.
251 *
252 * sap_ctx contains sap_avoid_ch_info struct containing the list of channels on
253 * which MDM device's AP with MCC was detected. This function will add channels
254 * to that list after checking for duplicates.
255 *
256 * Return: true: if channel was added or already present
257 * else false: if channel list was already full.
258 */
259static bool
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700260sap_check_n_add_overlapped_chnls(struct sap_context *sap_ctx,
261 uint8_t primary_channel)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800262{
263 uint8_t i = 0, j = 0, upper_chnl = 0, lower_chnl = 0;
264 struct sap_avoid_channels_info *ie_info =
265 &sap_ctx->sap_detected_avoid_ch_ie;
266 /*
267 * if primary channel less than channel 1 or out of 2g band then
268 * no further process is required. return true in this case.
269 */
270 if (primary_channel < CHANNEL_1 || primary_channel > CHANNEL_14)
271 return true;
272
273 /* lower channel is one channel right before primary channel */
274 lower_chnl = primary_channel - 1;
275 /* upper channel is one channel right after primary channel */
276 upper_chnl = primary_channel + 1;
277
278 /* lower channel needs to be non-zero, zero is not valid channel */
279 if (lower_chnl > (CHANNEL_1 - 1)) {
280 for (i = 0; i < sizeof(ie_info->channels); i++) {
281 if (ie_info->channels[i] == lower_chnl)
282 break;
283 if (ie_info->channels[i] == 0) {
284 ie_info->channels[i] = lower_chnl;
285 break;
286 }
287 }
288 }
289 /* upper channel needs to be atleast last channel in 2.4Ghz band */
290 if (upper_chnl < (CHANNEL_14 + 1)) {
291 for (j = 0; j < sizeof(ie_info->channels); j++) {
292 if (ie_info->channels[j] == upper_chnl)
293 break;
294 if (ie_info->channels[j] == 0) {
295 ie_info->channels[j] = upper_chnl;
296 break;
297 }
298 }
299 }
300 if (i == sizeof(ie_info->channels) || j == sizeof(ie_info->channels))
301 return false;
302 else
303 return true;
304}
305
306/**
307 * sap_process_avoid_ie() - processes the detected Q2Q IE
308 * context's avoid_channels_info struct
309 * @hal: hal handle
310 * @sap_ctx: sap context.
311 * @scan_result: scan results for ACS scan.
312 * @spect_info: spectrum weights array to update
313 *
314 * Detection of Q2Q IE indicates presence of another MDM device with its AP
315 * operating in MCC mode. This function parses the scan results and processes
316 * the Q2Q IE if found. It then extracts the channels and populates them in
317 * sap_ctx struct. It also increases the weights of those channels so that
318 * ACS logic will avoid those channels in its selection algorithm.
319 *
320 * Return: void
321 */
Tang Yingying523322d2017-01-17 23:28:43 +0800322static void sap_process_avoid_ie(tHalHandle hal,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700323 struct sap_context *sap_ctx,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800324 tScanResultHandle scan_result,
325 tSapChSelSpectInfo *spect_info)
326{
327 uint32_t total_ie_len = 0;
328 uint8_t *temp_ptr = NULL;
329 uint8_t i = 0;
330 struct sAvoidChannelIE *avoid_ch_ie;
331 tCsrScanResultInfo *node = NULL;
332 tpAniSirGlobal mac_ctx = NULL;
333 tSapSpectChInfo *spect_ch = NULL;
334
335 mac_ctx = PMAC_STRUCT(hal);
336 spect_ch = spect_info->pSpectCh;
337 node = sme_scan_result_get_first(hal, scan_result);
338
339 while (node) {
Abhishek Singh34a4d862016-10-26 16:01:51 +0530340 total_ie_len =
Jeff Johnson38e38a82017-10-06 10:32:31 -0700341 GET_IE_LEN_IN_BSS(node->BssDescriptor.length);
Naveen Rawat08db88f2017-09-08 15:07:48 -0700342 temp_ptr = wlan_get_vendor_ie_ptr_from_oui(
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800343 SIR_MAC_QCOM_VENDOR_OUI,
344 SIR_MAC_QCOM_VENDOR_SIZE,
345 ((uint8_t *)&node->BssDescriptor.ieFields),
346 total_ie_len);
347
348 if (temp_ptr) {
349 avoid_ch_ie = (struct sAvoidChannelIE *)temp_ptr;
Will Huang55ba1042017-03-22 10:43:30 +0800350 if (avoid_ch_ie->type !=
351 QCOM_VENDOR_IE_MCC_AVOID_CH) {
352 node = sme_scan_result_get_next(hal,
353 scan_result);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800354 continue;
Will Huang55ba1042017-03-22 10:43:30 +0800355 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800356
357 sap_ctx->sap_detected_avoid_ch_ie.present = 1;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530358 QDF_TRACE(QDF_MODULE_ID_SAP,
359 QDF_TRACE_LEVEL_DEBUG,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800360 "Q2Q IE - avoid ch %d",
361 avoid_ch_ie->channel);
362 /* add this channel to to_avoid channel list */
363 sap_check_n_add_channel(sap_ctx,
364 avoid_ch_ie->channel);
365 sap_check_n_add_overlapped_chnls(sap_ctx,
366 avoid_ch_ie->channel);
367 /*
368 * Mark weight of these channel present in IE to MAX
369 * so that ACS logic will to avoid thse channels
370 */
371 for (i = 0; i < spect_info->numSpectChans; i++)
372 if (spect_ch[i].chNum == avoid_ch_ie->channel) {
373 /*
374 * weight is set more than max so that,
375 * in the case of other channels being
376 * assigned max weight due to noise,
377 * they may be preferred over channels
378 * with Q2Q IE.
379 */
380 spect_ch[i].weight = SAP_ACS_WEIGHT_MAX + 1;
381 spect_ch[i].weight_copy =
382 SAP_ACS_WEIGHT_MAX + 1;
383 break;
384 }
385 } /* if (temp_ptr) */
386 node = sme_scan_result_get_next(hal, scan_result);
387 }
388}
389#endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
390
391#ifdef FEATURE_WLAN_CH_AVOID
392/*==========================================================================
393 FUNCTION sap_update_unsafe_channel_list
394
395 DESCRIPTION
396 Function Undate unsafe channel list table
397
398 DEPENDENCIES
399 NA.
400
401 IN
402 SapContext pointer
403
404 RETURN VALUE
405 NULL
406 ============================================================================*/
Jeff Johnsone13d8062017-09-28 06:54:55 -0700407void sap_update_unsafe_channel_list(tHalHandle hal, struct sap_context *sap_ctx)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800408{
409 uint16_t i, j;
Amar Singhalb8d4f152016-02-10 10:21:43 -0800410 uint16_t unsafe_channel_list[NUM_CHANNELS];
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800411 uint16_t unsafe_channel_count = 0;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700412 tpAniSirGlobal mac_ctx = NULL;
413
Yuanyuan Liu0e0aa932016-05-12 10:17:58 -0700414 qdf_device_t qdf_ctx = cds_get_context(QDF_MODULE_ID_QDF_DEVICE);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800415
Yuanyuan Liu97361182016-06-06 09:38:04 -0700416 if (!qdf_ctx) {
417 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_FATAL,
418 "qdf_ctx is NULL");
419 return;
420 }
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700421 mac_ctx = PMAC_STRUCT(hal);
422 if (!mac_ctx) {
423 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_FATAL,
424 "mac_ctx is NULL");
425 return;
426 }
Yuanyuan Liu97361182016-06-06 09:38:04 -0700427
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800428 /* Flush, default set all channel safe */
Amar Singhalb8d4f152016-02-10 10:21:43 -0800429 for (i = 0; i < NUM_CHANNELS; i++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800430 safe_channels[i].isSafe = true;
431 }
432
433 /* Try to find unsafe channel */
Ryan Hsu4252a2f2016-01-05 11:18:24 -0800434#if defined(FEATURE_WLAN_STA_AP_MODE_DFS_DISABLE)
Amar Singhalb8d4f152016-02-10 10:21:43 -0800435 for (i = 0; i < NUM_CHANNELS; i++) {
Jeff Johnsone13d8062017-09-28 06:54:55 -0700436 if (sap_ctx->dfs_ch_disable == true) {
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700437 if (wlan_reg_is_dfs_ch(mac_ctx->pdev,
438 safe_channels[i].channelNumber)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800439 safe_channels[i].isSafe = false;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530440 QDF_TRACE(QDF_MODULE_ID_SAP,
441 QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800442 "%s: DFS Ch %d is not safe in"
443 " Concurrent mode",
444 __func__,
445 safe_channels[i].channelNumber);
446 }
447 }
448 }
449#endif
Yuanyuan Liu0e0aa932016-05-12 10:17:58 -0700450 pld_get_wlan_unsafe_channel(qdf_ctx->dev,
451 unsafe_channel_list,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800452 &unsafe_channel_count,
453 sizeof(unsafe_channel_list));
454
455 for (i = 0; i < unsafe_channel_count; i++) {
Amar Singhalb8d4f152016-02-10 10:21:43 -0800456 for (j = 0; j < NUM_CHANNELS; j++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800457 if (safe_channels[j].channelNumber ==
458 unsafe_channel_list[i]) {
459 /* Found unsafe channel, update it */
460 safe_channels[j].isSafe = false;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530461 QDF_TRACE(QDF_MODULE_ID_SAP,
462 QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800463 FL("CH %d is not safe"),
464 unsafe_channel_list[i]);
465 break;
466 }
467 }
468 }
469
470 return;
471}
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800472
473#endif /* FEATURE_WLAN_CH_AVOID */
474
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800475/**
gaoleze5108942017-03-31 16:56:42 +0800476 * sap_channel_in_acs_channel_list() - check if channel in acs channel list
477 * @channel_num: channel to check
478 * @sap_ctx: struct ptSapContext
479 * @spect_info_params: strcut tSapChSelSpectInfo
480 *
481 * This function checks if specified channel is in the configured ACS channel
482 * list.
483 *
484 * Return: channel number if in acs channel list or SAP_CHANNEL_NOT_SELECTED
485 */
gaoleze5108942017-03-31 16:56:42 +0800486uint8_t sap_channel_in_acs_channel_list(uint8_t channel_num,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700487 struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800488 tSapChSelSpectInfo *spect_info_params)
489{
490 uint8_t i = 0;
491
492 if ((NULL == sap_ctx->acs_cfg->ch_list) ||
493 (NULL == spect_info_params))
494 return channel_num;
495
496 if (channel_num > 0 && channel_num <= 252) {
497 for (i = 0; i < sap_ctx->acs_cfg->ch_list_count; i++) {
498 if ((sap_ctx->acs_cfg->ch_list[i]) == channel_num)
499 return channel_num;
500 }
501 return SAP_CHANNEL_NOT_SELECTED;
502 } else {
503 return SAP_CHANNEL_NOT_SELECTED;
504 }
505}
506
507/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800508 * sap_select_preferred_channel_from_channel_list() - to calc best cahnnel
509 * @best_chnl: best channel already calculated among all the chanels
510 * @sap_ctx: sap context
511 * @spectinfo_param: Pointer to tSapChSelSpectInfo structure
512 *
513 * This function calculates the best channel among the configured channel list.
514 * If channel list not configured then returns the best channel calculated
515 * among all the channel list.
516 *
517 * Return: uint8_t best channel
518 */
Jeff Johnson464f7ea2016-10-07 10:21:26 -0700519static
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800520uint8_t sap_select_preferred_channel_from_channel_list(uint8_t best_chnl,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700521 struct sap_context *sap_ctx,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800522 tSapChSelSpectInfo *spectinfo_param)
523{
524 uint8_t i = 0;
Tushnim Bhattacharyya518e80f2017-08-30 17:35:33 -0700525 tpAniSirGlobal mac_ctx = sme_get_mac_context();
526
527 if (NULL == mac_ctx) {
528 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
529 "pmac Global Context is NULL");
530 return SAP_CHANNEL_NOT_SELECTED;
531 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800532
533 /*
534 * If Channel List is not Configured don't do anything
535 * Else return the Best Channel from the Channel List
536 */
537 if ((NULL == sap_ctx->acs_cfg->ch_list) ||
538 (NULL == spectinfo_param) ||
539 (0 == sap_ctx->acs_cfg->ch_list_count))
540 return best_chnl;
541
542 if (best_chnl <= 0 || best_chnl > 252)
543 return SAP_CHANNEL_NOT_SELECTED;
544
545 /* Select the best channel from allowed list */
546 for (i = 0; i < sap_ctx->acs_cfg->ch_list_count; i++) {
Tushnim Bhattacharyya518e80f2017-08-30 17:35:33 -0700547 if ((sap_ctx->acs_cfg->ch_list[i] == best_chnl) &&
548 !(wlan_reg_is_dfs_ch(mac_ctx->pdev, best_chnl) &&
549 policy_mgr_disallow_mcc(mac_ctx->psoc, best_chnl))) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530550 QDF_TRACE(QDF_MODULE_ID_SAP,
Ravi Joshi9788fcd2018-02-13 15:12:22 -0800551 QDF_TRACE_LEVEL_INFO,
Naveen Rawatbec64d92017-09-13 14:35:21 -0700552 "Best channel so far is: %d",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800553 best_chnl);
554 return best_chnl;
555 }
556 }
557
558 return SAP_CHANNEL_NOT_SELECTED;
559}
560
561/*==========================================================================
562 FUNCTION sap_chan_sel_init
563
564 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -0700565 Function sap_chan_sel_init allocates the memory, initializes the
Anurag Chouhan6d760662016-02-20 16:05:43 +0530566 structures used by the channel selection algorithm
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800567
568 DEPENDENCIES
569 NA.
570
571 PARAMETERS
572
573 IN
574 halHandle : Pointer to tHalHandle
575 *pSpectInfoParams : Pointer to tSapChSelSpectInfo structure
Jeff Johnsone13d8062017-09-28 06:54:55 -0700576 sap_ctx : Pointer to SAP Context
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800577
578 RETURN VALUE
579 bool: Success or FAIL
580
581 SIDE EFFECTS
582 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -0700583static bool sap_chan_sel_init(tHalHandle halHandle,
584 tSapChSelSpectInfo *pSpectInfoParams,
Jeff Johnsone13d8062017-09-28 06:54:55 -0700585 struct sap_context *sap_ctx)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800586{
587 tSapSpectChInfo *pSpectCh = NULL;
588 uint8_t *pChans = NULL;
589 uint16_t channelnum = 0;
590 tpAniSirGlobal pMac = PMAC_STRUCT(halHandle);
591 bool chSafe = true;
592#ifdef FEATURE_WLAN_CH_AVOID
593 uint16_t i;
594#endif
595 uint32_t dfs_master_cap_enabled;
596 bool include_dfs_ch = true;
Himanshu Agarwalfee2e362018-01-18 20:26:35 +0530597 uint8_t chan_num;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800598
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530599 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH, "In %s",
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800600 __func__);
601
602 pSpectInfoParams->numSpectChans =
603 pMac->scan.base_channels.numChannels;
604
605 /* Allocate memory for weight computation of 2.4GHz */
606 pSpectCh =
Anurag Chouhan600c3a02016-03-01 10:33:54 +0530607 (tSapSpectChInfo *) qdf_mem_malloc((pSpectInfoParams->numSpectChans)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800608 * sizeof(*pSpectCh));
609
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
637 /* check if the channel is in NOL blacklist */
Jeff Johnsone13d8062017-09-28 06:54:55 -0700638 if (sap_dfs_is_channel_in_nol_list(sap_ctx, *pChans,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800639 PHY_SINGLE_CHANNEL_CENTERED)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530640 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800641 "In %s, Ch %d is in NOL list", __func__,
642 *pChans);
643 chSafe = false;
644 continue;
645 }
646
647 if (include_dfs_ch == false) {
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700648 if (wlan_reg_is_dfs_ch(pMac->pdev, *pChans)) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800649 chSafe = false;
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530650 QDF_TRACE(QDF_MODULE_ID_SAP,
651 QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800652 "In %s, DFS Ch %d not considered for ACS",
653 __func__, *pChans);
654 continue;
655 }
656 }
657
658#ifdef FEATURE_WLAN_CH_AVOID
Amar Singhalb8d4f152016-02-10 10:21:43 -0800659 for (i = 0; i < NUM_CHANNELS; i++) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800660 if ((safe_channels[i].channelNumber == *pChans) &&
661 (false == safe_channels[i].isSafe)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530662 QDF_TRACE(QDF_MODULE_ID_SAP,
663 QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800664 "In %s, Ch %d is not safe", __func__,
665 *pChans);
666 chSafe = false;
667 break;
668 }
669 }
670#endif /* FEATURE_WLAN_CH_AVOID */
671
672 /* OFDM rates are not supported on channel 14 */
673 if (*pChans == 14 &&
Jeff Johnsone13d8062017-09-28 06:54:55 -0700674 eCSR_DOT11_MODE_11b != sap_ctx->csr_roamProfile.phyMode) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800675 continue;
676 }
677
Deepthi Gowri48b89332016-08-30 18:43:05 +0530678 /* Skip DSRC channels */
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -0700679 if (WLAN_REG_IS_11P_CH(*pChans))
Deepthi Gowri48b89332016-08-30 18:43:05 +0530680 continue;
681
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800682 if (true == chSafe) {
683 pSpectCh->chNum = *pChans;
Srinivas Girigowda74a66d62017-06-21 23:28:25 -0700684 pSpectCh->valid = true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800685 pSpectCh->rssiAgr = SOFTAP_MIN_RSSI; /* Initialise for all channels */
686 pSpectCh->channelWidth = SOFTAP_HT20_CHANNELWIDTH; /* Initialise 20MHz for all the Channels */
Himanshu Agarwalfee2e362018-01-18 20:26:35 +0530687 /* Initialise max ACS weight for all channels */
688 pSpectCh->weight = SAP_ACS_WEIGHT_MAX;
689 for (chan_num = 0; chan_num < sap_ctx->num_of_channel;
690 chan_num++) {
691 if (pSpectCh->chNum !=
692 sap_ctx->channelList[chan_num])
693 continue;
694
695 /*
696 * Initialize ACS weight to 0 for channels
697 * present in sap context scan channel list
698 */
699 pSpectCh->weight = 0;
700 break;
701 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800702 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800703 }
Srinivas Girigowda74a66d62017-06-21 23:28:25 -0700704 return true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800705}
706
gaoleze5108942017-03-31 16:56:42 +0800707/**
708 * sapweight_rssi_count() - calculates the channel weight due to rssi
Anurag Chouhan6d760662016-02-20 16:05:43 +0530709 and data count(here number of BSS observed)
gaoleze5108942017-03-31 16:56:42 +0800710 * @sap_ctx : Softap context
711 * @rssi : Max signal strength receieved from a BSS for the channel
712 * @count : Number of BSS observed in the channel
713 *
714 * Return: uint32_t Calculated channel weight based on above two
715 */
716static
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700717uint32_t sapweight_rssi_count(struct sap_context *sap_ctx, int8_t rssi,
gaoleze5108942017-03-31 16:56:42 +0800718 uint16_t count)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800719{
720 int32_t rssiWeight = 0;
721 int32_t countWeight = 0;
722 uint32_t rssicountWeight = 0;
gaoleze5108942017-03-31 16:56:42 +0800723 uint8_t softap_rssi_weight_cfg, softap_count_weight_cfg;
724 uint8_t softap_rssi_weight_local, softap_count_weight_local;
725
726 softap_rssi_weight_cfg =
727 ACS_WEIGHT_SOFTAP_RSSI_CFG(sap_ctx->auto_channel_select_weight);
728
729 softap_count_weight_cfg =
730 ACS_WEIGHT_SOFTAP_COUNT_CFG(sap_ctx->auto_channel_select_weight);
731
732 softap_rssi_weight_local =
733 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
734 softap_rssi_weight_cfg);
735
736 softap_count_weight_local =
737 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
738 softap_count_weight_cfg);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800739
740 /* Weight from RSSI */
gaoleze5108942017-03-31 16:56:42 +0800741 rssiWeight = ACS_WEIGHT_COMPUTE(sap_ctx->auto_channel_select_weight,
742 softap_rssi_weight_cfg,
743 rssi - SOFTAP_MIN_RSSI,
744 SOFTAP_MAX_RSSI - SOFTAP_MIN_RSSI);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800745
gaoleze5108942017-03-31 16:56:42 +0800746 if (rssiWeight > softap_rssi_weight_local)
747 rssiWeight = softap_rssi_weight_local;
748
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800749 else if (rssiWeight < 0)
750 rssiWeight = 0;
751
752 /* Weight from data count */
gaoleze5108942017-03-31 16:56:42 +0800753 countWeight = ACS_WEIGHT_COMPUTE(sap_ctx->auto_channel_select_weight,
754 softap_count_weight_cfg,
755 count - SOFTAP_MIN_COUNT,
756 SOFTAP_MAX_COUNT - SOFTAP_MIN_COUNT);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800757
gaoleze5108942017-03-31 16:56:42 +0800758 if (countWeight > softap_count_weight_local)
759 countWeight = softap_count_weight_local;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800760
761 rssicountWeight = rssiWeight + countWeight;
762
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +0530763 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -0800764 "In %s, rssiWeight=%d, countWeight=%d, rssicountWeight=%d",
765 __func__, rssiWeight, countWeight, rssicountWeight);
766
767 return rssicountWeight;
768}
769
770/**
gaoleze5108942017-03-31 16:56:42 +0800771 * sap_get_channel_status() - get channel info via channel number
772 * @p_mac: Pointer to Global MAC structure
773 * @channel_id: channel id
774 *
775 * Return: chan status info
776 */
777static struct lim_channel_status *sap_get_channel_status
778 (tpAniSirGlobal p_mac, uint32_t channel_id)
779{
780 return csr_get_channel_status(p_mac, channel_id);
781}
782
783/**
784 * sap_clear_channel_status() - clear chan info
785 * @p_mac: Pointer to Global MAC structure
786 *
787 * Return: none
788 */
789static void sap_clear_channel_status(tpAniSirGlobal p_mac)
790{
791 csr_clear_channel_status(p_mac);
792}
793
794/**
795 * sap_weight_channel_noise_floor() - compute noise floor weight
796 * @sap_ctx: sap context
797 * @chn_stat: Pointer to chan status info
798 *
799 * Return: channel noise floor weight
800 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700801static uint32_t sap_weight_channel_noise_floor(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800802 struct lim_channel_status
803 *channel_stat)
804{
805 uint32_t noise_floor_weight;
806 uint8_t softap_nf_weight_cfg;
807 uint8_t softap_nf_weight_local;
808
809 softap_nf_weight_cfg =
810 ACS_WEIGHT_SOFTAP_NOISE_FLOOR_CFG
811 (sap_ctx->auto_channel_select_weight);
812
813 softap_nf_weight_local =
814 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
815 softap_nf_weight_cfg);
816
817 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800818 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800819 "In %s, sanity check failed return max weight",
820 __func__);
821 return softap_nf_weight_local;
822 }
823
824 noise_floor_weight = (channel_stat->noise_floor == 0) ? 0 :
825 (ACS_WEIGHT_COMPUTE(
826 sap_ctx->auto_channel_select_weight,
827 softap_nf_weight_cfg,
828 channel_stat->noise_floor -
829 SOFTAP_MIN_NF,
830 SOFTAP_MAX_NF - SOFTAP_MIN_NF));
831
832 if (noise_floor_weight > softap_nf_weight_local)
833 noise_floor_weight = softap_nf_weight_local;
834 else if (noise_floor_weight < 0)
835 noise_floor_weight = 0;
836
837 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
838 "In %s, nf=%d, nfwc=%d, nfwl=%d, nfw=%d",
839 __func__, channel_stat->noise_floor,
840 softap_nf_weight_cfg, softap_nf_weight_local,
841 noise_floor_weight);
842
843 return noise_floor_weight;
844}
845
846/**
847 * sap_weight_channel_free() - compute channel free weight
848 * @sap_ctx: sap context
849 * @chn_stat: Pointer to chan status info
850 *
851 * Return: channel free weight
852 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700853static uint32_t sap_weight_channel_free(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800854 struct lim_channel_status
855 *channel_stat)
856{
857 uint32_t channel_free_weight;
858 uint8_t softap_channel_free_weight_cfg;
859 uint8_t softap_channel_free_weight_local;
860 uint32_t rx_clear_count = 0;
861 uint32_t cycle_count = 0;
862
863 softap_channel_free_weight_cfg =
864 ACS_WEIGHT_SOFTAP_CHANNEL_FREE_CFG
865 (sap_ctx->auto_channel_select_weight);
866
867 softap_channel_free_weight_local =
868 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
869 softap_channel_free_weight_cfg);
870
871 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800872 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800873 "In %s, sanity check failed return max weight",
874 __func__);
875 return softap_channel_free_weight_local;
876 }
877
878 rx_clear_count = channel_stat->rx_clear_count -
879 channel_stat->tx_frame_count -
880 channel_stat->rx_frame_count;
881 cycle_count = channel_stat->cycle_count;
882
883 /* LSH 4, otherwise it is always 0. */
884 channel_free_weight = (cycle_count == 0) ? 0 :
885 (ACS_WEIGHT_COMPUTE(
886 sap_ctx->auto_channel_select_weight,
887 softap_channel_free_weight_cfg,
888 ((rx_clear_count << 8) +
889 (cycle_count >> 1))/cycle_count -
890 (SOFTAP_MIN_CHNFREE << 8),
891 (SOFTAP_MAX_CHNFREE -
892 SOFTAP_MIN_CHNFREE) << 8));
893
894 if (channel_free_weight > softap_channel_free_weight_local)
895 channel_free_weight = softap_channel_free_weight_local;
896
897 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
898 "In %s, rcc=%d, cc=%d, tc=%d, rc=%d, cfwc=%d, cfwl=%d, cfw=%d",
899 __func__, rx_clear_count, cycle_count,
900 channel_stat->tx_frame_count,
901 channel_stat->rx_frame_count,
902 softap_channel_free_weight_cfg,
903 softap_channel_free_weight_local,
904 channel_free_weight);
905
906 return channel_free_weight;
907}
908
909/**
910 * sap_weight_channel_txpwr_range() - compute channel tx power range weight
911 * @sap_ctx: sap context
912 * @chn_stat: Pointer to chan status info
913 *
914 * Return: tx power range weight
915 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700916static uint32_t sap_weight_channel_txpwr_range(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800917 struct lim_channel_status
918 *channel_stat)
919{
920 uint32_t txpwr_weight_low_speed;
921 uint8_t softap_txpwr_range_weight_cfg;
922 uint8_t softap_txpwr_range_weight_local;
923
924 softap_txpwr_range_weight_cfg =
925 ACS_WEIGHT_SOFTAP_TX_POWER_RANGE_CFG
926 (sap_ctx->auto_channel_select_weight);
927
928 softap_txpwr_range_weight_local =
929 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
930 softap_txpwr_range_weight_cfg);
931
932 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800933 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800934 "In %s, sanity check failed return max weight",
935 __func__);
936 return softap_txpwr_range_weight_local;
937 }
938
939 txpwr_weight_low_speed = (channel_stat->chan_tx_pwr_range == 0) ? 0 :
940 (ACS_WEIGHT_COMPUTE(
941 sap_ctx->auto_channel_select_weight,
942 softap_txpwr_range_weight_cfg,
943 SOFTAP_MAX_TXPWR -
944 channel_stat->chan_tx_pwr_range,
945 SOFTAP_MAX_TXPWR - SOFTAP_MIN_TXPWR));
946
947 if (txpwr_weight_low_speed > softap_txpwr_range_weight_local)
948 txpwr_weight_low_speed = softap_txpwr_range_weight_local;
949
950 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
951 "In %s, tpr=%d, tprwc=%d, tprwl=%d, tprw=%d",
952 __func__, channel_stat->chan_tx_pwr_range,
953 softap_txpwr_range_weight_cfg,
954 softap_txpwr_range_weight_local,
955 txpwr_weight_low_speed);
956
957 return txpwr_weight_low_speed;
958}
959
960/**
961 * sap_weight_channel_txpwr_tput() - compute channel tx power
962 * throughput weight
963 * @sap_ctx: sap context
964 * @chn_stat: Pointer to chan status info
965 *
966 * Return: tx power throughput weight
967 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -0700968static uint32_t sap_weight_channel_txpwr_tput(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +0800969 struct lim_channel_status
970 *channel_stat)
971{
972 uint32_t txpwr_weight_high_speed;
973 uint8_t softap_txpwr_tput_weight_cfg;
974 uint8_t softap_txpwr_tput_weight_local;
975
976 softap_txpwr_tput_weight_cfg =
977 ACS_WEIGHT_SOFTAP_TX_POWER_THROUGHPUT_CFG
978 (sap_ctx->auto_channel_select_weight);
979
980 softap_txpwr_tput_weight_local =
981 ACS_WEIGHT_CFG_TO_LOCAL(sap_ctx->auto_channel_select_weight,
982 softap_txpwr_tput_weight_cfg);
983
984 if (channel_stat == NULL || channel_stat->channelfreq == 0) {
Srinivas Girigowda80213e52018-01-23 14:51:33 -0800985 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
gaoleze5108942017-03-31 16:56:42 +0800986 "In %s, sanity check failed return max weight",
987 __func__);
988 return softap_txpwr_tput_weight_local;
989 }
990
991 txpwr_weight_high_speed = (channel_stat->chan_tx_pwr_throughput == 0)
992 ? 0 : (ACS_WEIGHT_COMPUTE(
993 sap_ctx->auto_channel_select_weight,
994 softap_txpwr_tput_weight_cfg,
995 SOFTAP_MAX_TXPWR -
996 channel_stat->chan_tx_pwr_throughput,
997 SOFTAP_MAX_TXPWR - SOFTAP_MIN_TXPWR));
998
999 if (txpwr_weight_high_speed > softap_txpwr_tput_weight_local)
1000 txpwr_weight_high_speed = softap_txpwr_tput_weight_local;
1001
1002 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
1003 "In %s, tpt=%d, tptwc=%d, tptwl=%d, tptw=%d",
1004 __func__, channel_stat->chan_tx_pwr_throughput,
1005 softap_txpwr_tput_weight_cfg,
1006 softap_txpwr_tput_weight_local,
1007 txpwr_weight_high_speed);
1008
1009 return txpwr_weight_high_speed;
1010}
1011
1012/**
1013 * sap_weight_channel_status() - compute chan status weight
1014 * @sap_ctx: sap context
1015 * @chn_stat: Pointer to chan status info
1016 *
1017 * Return: chan status weight
1018 */
1019static
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07001020uint32_t sap_weight_channel_status(struct sap_context *sap_ctx,
gaoleze5108942017-03-31 16:56:42 +08001021 struct lim_channel_status *channel_stat)
1022{
1023 return sap_weight_channel_noise_floor(sap_ctx, channel_stat) +
1024 sap_weight_channel_free(sap_ctx, channel_stat) +
1025 sap_weight_channel_txpwr_range(sap_ctx, channel_stat) +
1026 sap_weight_channel_txpwr_tput(sap_ctx, channel_stat);
1027}
1028
1029/**
Yeshwanth Sriram Guntuka273889e2018-02-16 17:11:46 +05301030 * sap_check_channels_same_band() - Check if two channels belong to same band
1031 * @ch_num1: channel number
1032 * @ch_num2: channel number
1033 *
1034 * Return: true if both channels belong to same band else false
1035 */
1036static bool sap_check_channels_same_band(uint16_t ch_num1, uint16_t ch_num2)
1037{
1038 if ((ch_num1 <= SIR_11B_CHANNEL_END &&
1039 ch_num2 <= SIR_11B_CHANNEL_END) ||
1040 (ch_num1 >= SIR_11A_CHANNEL_BEGIN &&
1041 ch_num2 >= SIR_11A_CHANNEL_BEGIN))
1042 return true;
1043
1044 return false;
1045}
1046
1047/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001048 * sap_update_rssi_bsscount() - updates bss count and rssi effect.
1049 *
1050 * @pSpectCh: Channel Information
1051 * @offset: Channel Offset
1052 * @sap_24g: Channel is in 2.4G or 5G
Liangwei Dong71ed6502016-10-20 03:40:45 -04001053 * @spectch_start: the start of spect ch array
1054 * @spectch_end: the end of spect ch array
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001055 *
1056 * sap_update_rssi_bsscount updates bss count and rssi effect based
1057 * on the channel offset.
1058 *
1059 * Return: None.
1060 */
1061
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001062static void sap_update_rssi_bsscount(tSapSpectChInfo *pSpectCh, int32_t offset,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001063 bool sap_24g, tSapSpectChInfo *spectch_start,
1064 tSapSpectChInfo *spectch_end)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001065{
1066 tSapSpectChInfo *pExtSpectCh = NULL;
1067 int32_t rssi, rsssi_effect;
1068
1069 pExtSpectCh = (pSpectCh + offset);
Liangwei Dong71ed6502016-10-20 03:40:45 -04001070 if (pExtSpectCh != NULL &&
1071 pExtSpectCh >= spectch_start &&
1072 pExtSpectCh < spectch_end) {
Yeshwanth Sriram Guntuka273889e2018-02-16 17:11:46 +05301073 if (!sap_check_channels_same_band(pSpectCh->chNum,
1074 pExtSpectCh->chNum))
1075 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001076 ++pExtSpectCh->bssCount;
1077 switch (offset) {
1078 case -1:
1079 case 1:
1080 rsssi_effect = sap_24g ?
1081 SAP_24GHZ_FIRST_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1082 SAP_SUBBAND1_RSSI_EFFECT_PRIMARY;
1083 break;
1084 case -2:
1085 case 2:
1086 rsssi_effect = sap_24g ?
1087 SAP_24GHZ_SEC_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1088 SAP_SUBBAND2_RSSI_EFFECT_PRIMARY;
1089 break;
1090 case -3:
1091 case 3:
1092 rsssi_effect = sap_24g ?
1093 SAP_24GHZ_THIRD_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1094 SAP_SUBBAND3_RSSI_EFFECT_PRIMARY;
1095 break;
1096 case -4:
1097 case 4:
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001098 rsssi_effect = sap_24g ?
1099 SAP_24GHZ_FOURTH_OVERLAP_CHAN_RSSI_EFFECT_PRIMARY :
1100 SAP_SUBBAND4_RSSI_EFFECT_PRIMARY;
1101 break;
1102 case -5:
1103 case 5:
1104 rsssi_effect = SAP_SUBBAND5_RSSI_EFFECT_PRIMARY;
1105 break;
1106 case -6:
1107 case 6:
1108 rsssi_effect = SAP_SUBBAND6_RSSI_EFFECT_PRIMARY;
1109 break;
1110 case -7:
1111 case 7:
1112 rsssi_effect = SAP_SUBBAND7_RSSI_EFFECT_PRIMARY;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001113 break;
1114 default:
1115 rsssi_effect = 0;
1116 break;
1117 }
1118
1119 rssi = pSpectCh->rssiAgr + rsssi_effect;
1120 if (IS_RSSI_VALID(pExtSpectCh->rssiAgr, rssi))
1121 pExtSpectCh->rssiAgr = rssi;
1122 if (pExtSpectCh->rssiAgr < SOFTAP_MIN_RSSI)
1123 pExtSpectCh->rssiAgr = SOFTAP_MIN_RSSI;
1124 }
1125}
1126
1127/**
1128 * sap_upd_chan_spec_params() - sap_upd_chan_spec_params
1129 * updates channel parameters obtained from Beacon
1130 * @pBeaconStruct Beacon strucutre populated by parse_beacon function
1131 * @channelWidth Channel width
1132 * @secondaryChannelOffset Secondary Channel Offset
1133 * @vhtSupport If channel supports VHT
1134 * @centerFreq Central frequency for the given channel.
1135 *
1136 * sap_upd_chan_spec_params updates the spectrum channels based on the
1137 * pBeaconStruct obtained from Beacon IE
1138 *
1139 * Return: NA.
1140 */
1141
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001142static void sap_upd_chan_spec_params(tSirProbeRespBeacon *pBeaconStruct,
1143 uint16_t *channelWidth,
1144 uint16_t *secondaryChannelOffset,
1145 uint16_t *vhtSupport,
1146 uint16_t *centerFreq,
1147 uint16_t *centerFreq_2)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001148{
1149 if (NULL == pBeaconStruct) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301150 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001151 FL("pBeaconStruct is NULL"));
1152 return;
1153 }
1154
1155 if (pBeaconStruct->HTCaps.present && pBeaconStruct->HTInfo.present) {
1156 *channelWidth = pBeaconStruct->HTCaps.supportedChannelWidthSet;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001157 *secondaryChannelOffset =
1158 pBeaconStruct->HTInfo.secondaryChannelOffset;
1159 if (!pBeaconStruct->VHTOperation.present)
1160 return;
1161 *vhtSupport = pBeaconStruct->VHTOperation.present;
1162 if (pBeaconStruct->VHTOperation.chanWidth) {
1163 *centerFreq =
1164 pBeaconStruct->VHTOperation.chanCenterFreqSeg1;
1165 *centerFreq_2 =
1166 pBeaconStruct->VHTOperation.chanCenterFreqSeg2;
1167 /*
1168 * LHS follows tSirMacHTChannelWidth, while RHS follows
1169 * WNI_CFG_VHT_CHANNEL_WIDTH_X format hence following
1170 * adjustment
1171 */
1172 *channelWidth =
1173 pBeaconStruct->VHTOperation.chanWidth + 1;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001174
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001175 }
1176 }
1177}
1178
1179/**
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001180 * sap_update_rssi_bsscount_vht_5G() - updates bss count and rssi effect.
1181 *
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001182 * @spect_ch: Channel Information
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001183 * @offset: Channel Offset
1184 * @num_ch: no.of channels
Liangwei Dong71ed6502016-10-20 03:40:45 -04001185 * @spectch_start: the start of spect ch array
1186 * @spectch_end: the end of spect ch array
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001187 *
1188 * sap_update_rssi_bsscount_vht_5G updates bss count and rssi effect based
1189 * on the channel offset.
1190 *
1191 * Return: None.
1192 */
1193
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001194static void sap_update_rssi_bsscount_vht_5G(tSapSpectChInfo *spect_ch,
1195 int32_t offset,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001196 uint16_t num_ch,
1197 tSapSpectChInfo *spectch_start,
1198 tSapSpectChInfo *spectch_end)
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001199{
1200 int32_t ch_offset;
1201 uint16_t i, cnt;
1202
1203 if (!offset)
1204 return;
1205 if (offset > 0)
1206 cnt = num_ch;
1207 else
1208 cnt = num_ch + 1;
1209 for (i = 0; i < cnt; i++) {
1210 ch_offset = offset + i;
1211 if (ch_offset == 0)
1212 continue;
Liangwei Dong71ed6502016-10-20 03:40:45 -04001213 sap_update_rssi_bsscount(spect_ch, ch_offset, false,
1214 spectch_start, spectch_end);
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001215 }
1216}
1217/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001218 * sap_interference_rssi_count_5G() - sap_interference_rssi_count
1219 * considers the Adjacent channel rssi and
1220 * data count(here number of BSS observed)
1221 * @spect_ch: Channel Information
1222 * @chan_width: Channel width parsed from beacon IE
1223 * @sec_chan_offset: Secondary Channel Offset
1224 * @center_freq: Central frequency for the given channel.
1225 * @channel_id: channel_id
Liangwei Dong71ed6502016-10-20 03:40:45 -04001226 * @spectch_start: the start of spect ch array
1227 * @spectch_end: the end of spect ch array
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001228 *
1229 * sap_interference_rssi_count_5G considers the Adjacent channel rssi
1230 * and data count(here number of BSS observed)
1231 *
1232 * Return: NA.
1233 */
1234
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001235static void sap_interference_rssi_count_5G(tSapSpectChInfo *spect_ch,
1236 uint16_t chan_width,
1237 uint16_t sec_chan_offset,
1238 uint16_t center_freq,
1239 uint16_t center_freq_2,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001240 uint8_t channel_id,
1241 tSapSpectChInfo *spectch_start,
1242 tSapSpectChInfo *spectch_end)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001243{
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001244 uint16_t num_ch;
1245 int32_t offset = 0;
Srinivas Girigowda4d65ebe2017-10-13 21:41:42 -07001246
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001247 if (NULL == spect_ch) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301248 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001249 FL("spect_ch is NULL"));
1250 return;
1251 }
1252
1253 /* Updating the received ChannelWidth */
1254 if (spect_ch->channelWidth != chan_width)
1255 spect_ch->channelWidth = chan_width;
1256 /* If received ChannelWidth is other than HT20,
1257 * we need to update the extension channel Params as well
1258 * chan_width == 0, HT20
1259 * chan_width == 1, HT40
1260 * chan_width == 2, VHT80
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001261 * chan_width == 3, VHT160
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001262 */
1263
1264 switch (spect_ch->channelWidth) {
1265 case eHT_CHANNEL_WIDTH_40MHZ: /* HT40 */
1266 switch (sec_chan_offset) {
1267 /* Above the Primary Channel */
1268 case PHY_DOUBLE_CHANNEL_LOW_PRIMARY:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001269 sap_update_rssi_bsscount(spect_ch, 1, false,
1270 spectch_start, spectch_end);
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001271 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001272
1273 /* Below the Primary channel */
1274 case PHY_DOUBLE_CHANNEL_HIGH_PRIMARY:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001275 sap_update_rssi_bsscount(spect_ch, -1, false,
1276 spectch_start, spectch_end);
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001277 return;
1278 }
1279 return;
1280 case eHT_CHANNEL_WIDTH_80MHZ: /* VHT80 */
1281 num_ch = 3;
1282 if ((center_freq - channel_id) == 6) {
1283 offset = 1;
1284 } else if ((center_freq - channel_id) == 2) {
1285 offset = -1;
1286 } else if ((center_freq - channel_id) == -2) {
1287 offset = -2;
1288 } else if ((center_freq - channel_id) == -6) {
1289 offset = -3;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001290 }
1291 break;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001292 case eHT_CHANNEL_WIDTH_160MHZ: /* VHT160 */
1293 num_ch = 7;
1294 if ((center_freq - channel_id) == 14)
1295 offset = 1;
1296 else if ((center_freq - channel_id) == 10)
1297 offset = -1;
1298 else if ((center_freq - channel_id) == 6)
1299 offset = -2;
1300 else if ((center_freq - channel_id) == 2)
1301 offset = -3;
1302 else if ((center_freq - channel_id) == -2)
1303 offset = -4;
1304 else if ((center_freq - channel_id) == -6)
1305 offset = -5;
1306 else if ((center_freq - channel_id) == -10)
1307 offset = -6;
1308 else if ((center_freq - channel_id) == -14)
1309 offset = -7;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001310 break;
1311 default:
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001312 return;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001313 }
Liangwei Dong71ed6502016-10-20 03:40:45 -04001314 sap_update_rssi_bsscount_vht_5G(spect_ch, offset, num_ch,
1315 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001316}
1317
1318/**
1319 * sap_interference_rssi_count() - sap_interference_rssi_count
1320 * considers the Adjacent channel rssi
1321 * and data count(here number of BSS observed)
1322 * @spect_ch Channel Information
Liangwei Dong71ed6502016-10-20 03:40:45 -04001323 * @spectch_start: the start of spect ch array
1324 * @spectch_end: the end of spect ch array
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001325 *
1326 * sap_interference_rssi_count considers the Adjacent channel rssi
1327 * and data count(here number of BSS observed)
1328 *
1329 * Return: None.
1330 */
1331
Liangwei Dong71ed6502016-10-20 03:40:45 -04001332static void sap_interference_rssi_count(tSapSpectChInfo *spect_ch,
1333 tSapSpectChInfo *spectch_start,
1334 tSapSpectChInfo *spectch_end)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001335{
1336 if (NULL == spect_ch) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301337 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001338 "%s: spect_ch is NULL", __func__);
1339 return;
1340 }
1341
1342 switch (spect_ch->chNum) {
1343 case CHANNEL_1:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001344 sap_update_rssi_bsscount(spect_ch, 1, true,
1345 spectch_start, spectch_end);
1346 sap_update_rssi_bsscount(spect_ch, 2, true,
1347 spectch_start, spectch_end);
1348 sap_update_rssi_bsscount(spect_ch, 3, true,
1349 spectch_start, spectch_end);
1350 sap_update_rssi_bsscount(spect_ch, 4, true,
1351 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001352 break;
1353
1354 case CHANNEL_2:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001355 sap_update_rssi_bsscount(spect_ch, -1, true,
1356 spectch_start, spectch_end);
1357 sap_update_rssi_bsscount(spect_ch, 1, true,
1358 spectch_start, spectch_end);
1359 sap_update_rssi_bsscount(spect_ch, 2, true,
1360 spectch_start, spectch_end);
1361 sap_update_rssi_bsscount(spect_ch, 3, true,
1362 spectch_start, spectch_end);
1363 sap_update_rssi_bsscount(spect_ch, 4, true,
1364 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001365 break;
1366 case CHANNEL_3:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001367 sap_update_rssi_bsscount(spect_ch, -2, true,
1368 spectch_start, spectch_end);
1369 sap_update_rssi_bsscount(spect_ch, -1, true,
1370 spectch_start, spectch_end);
1371 sap_update_rssi_bsscount(spect_ch, 1, true,
1372 spectch_start, spectch_end);
1373 sap_update_rssi_bsscount(spect_ch, 2, true,
1374 spectch_start, spectch_end);
1375 sap_update_rssi_bsscount(spect_ch, 3, true,
1376 spectch_start, spectch_end);
1377 sap_update_rssi_bsscount(spect_ch, 4, true,
1378 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001379 break;
1380 case CHANNEL_4:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001381 sap_update_rssi_bsscount(spect_ch, -3, true,
1382 spectch_start, spectch_end);
1383 sap_update_rssi_bsscount(spect_ch, -2, true,
1384 spectch_start, spectch_end);
1385 sap_update_rssi_bsscount(spect_ch, -1, true,
1386 spectch_start, spectch_end);
1387 sap_update_rssi_bsscount(spect_ch, 1, true,
1388 spectch_start, spectch_end);
1389 sap_update_rssi_bsscount(spect_ch, 2, true,
1390 spectch_start, spectch_end);
1391 sap_update_rssi_bsscount(spect_ch, 3, true,
1392 spectch_start, spectch_end);
1393 sap_update_rssi_bsscount(spect_ch, 4, true,
1394 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001395 break;
1396
1397 case CHANNEL_5:
1398 case CHANNEL_6:
1399 case CHANNEL_7:
1400 case CHANNEL_8:
1401 case CHANNEL_9:
1402 case CHANNEL_10:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001403 sap_update_rssi_bsscount(spect_ch, -4, true,
1404 spectch_start, spectch_end);
1405 sap_update_rssi_bsscount(spect_ch, -3, true,
1406 spectch_start, spectch_end);
1407 sap_update_rssi_bsscount(spect_ch, -2, true,
1408 spectch_start, spectch_end);
1409 sap_update_rssi_bsscount(spect_ch, -1, true,
1410 spectch_start, spectch_end);
1411 sap_update_rssi_bsscount(spect_ch, 1, true,
1412 spectch_start, spectch_end);
1413 sap_update_rssi_bsscount(spect_ch, 2, true,
1414 spectch_start, spectch_end);
1415 sap_update_rssi_bsscount(spect_ch, 3, true,
1416 spectch_start, spectch_end);
1417 sap_update_rssi_bsscount(spect_ch, 4, true,
1418 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001419 break;
1420
1421 case CHANNEL_11:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001422 sap_update_rssi_bsscount(spect_ch, -4, 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, -2, true,
1427 spectch_start, spectch_end);
1428 sap_update_rssi_bsscount(spect_ch, -1, true,
1429 spectch_start, spectch_end);
1430 sap_update_rssi_bsscount(spect_ch, 1, true,
1431 spectch_start, spectch_end);
1432 sap_update_rssi_bsscount(spect_ch, 2, true,
1433 spectch_start, spectch_end);
1434 sap_update_rssi_bsscount(spect_ch, 3, true,
1435 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001436 break;
1437
1438 case CHANNEL_12:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001439 sap_update_rssi_bsscount(spect_ch, -4, true,
1440 spectch_start, spectch_end);
1441 sap_update_rssi_bsscount(spect_ch, -3, true,
1442 spectch_start, spectch_end);
1443 sap_update_rssi_bsscount(spect_ch, -2, true,
1444 spectch_start, spectch_end);
1445 sap_update_rssi_bsscount(spect_ch, -1, true,
1446 spectch_start, spectch_end);
1447 sap_update_rssi_bsscount(spect_ch, 1, true,
1448 spectch_start, spectch_end);
1449 sap_update_rssi_bsscount(spect_ch, 2, true,
1450 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001451 break;
1452
1453 case CHANNEL_13:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001454 sap_update_rssi_bsscount(spect_ch, -4, true,
1455 spectch_start, spectch_end);
1456 sap_update_rssi_bsscount(spect_ch, -3, true,
1457 spectch_start, spectch_end);
1458 sap_update_rssi_bsscount(spect_ch, -2, true,
1459 spectch_start, spectch_end);
1460 sap_update_rssi_bsscount(spect_ch, -1, true,
1461 spectch_start, spectch_end);
1462 sap_update_rssi_bsscount(spect_ch, 1, true,
1463 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001464 break;
1465
1466 case CHANNEL_14:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001467 sap_update_rssi_bsscount(spect_ch, -4, true,
1468 spectch_start, spectch_end);
1469 sap_update_rssi_bsscount(spect_ch, -3, true,
1470 spectch_start, spectch_end);
1471 sap_update_rssi_bsscount(spect_ch, -2, true,
1472 spectch_start, spectch_end);
1473 sap_update_rssi_bsscount(spect_ch, -1, true,
1474 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001475 break;
1476
1477 default:
1478 break;
1479 }
1480}
1481
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001482/**
1483 * ch_in_pcl() - Is channel in the Preferred Channel List (PCL)
1484 * @sap_ctx: SAP context which contains the current PCL
1485 * @channel: Input channel number to be checked
1486 *
1487 * Check if a channel is in the preferred channel list
1488 *
1489 * Return:
1490 * true: channel is in PCL,
1491 * false: channel is not in PCL
1492 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07001493static bool ch_in_pcl(struct sap_context *sap_ctx, uint8_t channel)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001494{
1495 uint32_t i;
1496
1497 for (i = 0; i < sap_ctx->acs_cfg->pcl_ch_count; i++) {
1498 if (channel == sap_ctx->acs_cfg->pcl_channels[i])
1499 return true;
1500 }
1501
1502 return false;
1503}
1504
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001505/**
1506 * sap_compute_spect_weight() - Compute spectrum weight
1507 * @pSpectInfoParams: Pointer to the tSpectInfoParams structure
1508 * @halHandle: Pointer to HAL handle
1509 * @pResult: Pointer to tScanResultHandle
1510 * @sap_ctx: Context of the SAP
1511 *
1512 * Main function for computing the weight of each channel in the
1513 * spectrum based on the RSSI value of the BSSes on the channel
1514 * and number of BSS
1515 */
1516static void sap_compute_spect_weight(tSapChSelSpectInfo *pSpectInfoParams,
1517 tHalHandle halHandle,
1518 tScanResultHandle pResult,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07001519 struct sap_context *sap_ctx)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001520{
1521 int8_t rssi = 0;
1522 uint8_t chn_num = 0;
1523 uint8_t channel_id = 0;
1524
1525 tCsrScanResultInfo *pScanResult;
1526 tSapSpectChInfo *pSpectCh = pSpectInfoParams->pSpectCh;
1527 uint32_t operatingBand;
1528 uint16_t channelWidth;
1529 uint16_t secondaryChannelOffset;
1530 uint16_t centerFreq;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001531 uint16_t centerFreq_2 = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001532 uint16_t vhtSupport;
1533 uint32_t ieLen = 0;
1534 tSirProbeRespBeacon *pBeaconStruct;
1535 tpAniSirGlobal pMac = (tpAniSirGlobal) halHandle;
Liangwei Dong71ed6502016-10-20 03:40:45 -04001536 tSapSpectChInfo *spectch_start = pSpectInfoParams->pSpectCh;
1537 tSapSpectChInfo *spectch_end = pSpectInfoParams->pSpectCh +
1538 pSpectInfoParams->numSpectChans;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001539
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301540 pBeaconStruct = qdf_mem_malloc(sizeof(tSirProbeRespBeacon));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001541 if (NULL == pBeaconStruct) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301542 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Kaushik, Sushantee3ed032016-08-04 16:40:46 +05301543 "Unable to allocate memory in sap_compute_spect_weight");
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001544 return;
1545 }
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301546 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001547 "In %s, Computing spectral weight", __func__);
1548
1549 /**
1550 * Soft AP specific channel weight calculation using DFS formula
1551 */
1552 SET_ACS_BAND(operatingBand, sap_ctx);
1553
1554 pScanResult = sme_scan_result_get_first(halHandle, pResult);
1555
1556 while (pScanResult) {
1557 pSpectCh = pSpectInfoParams->pSpectCh;
1558 /* Defining the default values, so that any value will hold the default values */
1559 channelWidth = eHT_CHANNEL_WIDTH_20MHZ;
1560 secondaryChannelOffset = PHY_SINGLE_CHANNEL_CENTERED;
1561 vhtSupport = 0;
1562 centerFreq = 0;
1563
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001564
Yingying Tang22facc12016-10-20 17:43:59 +08001565 ieLen = GET_IE_LEN_IN_BSS(
1566 pScanResult->BssDescriptor.length);
1567 qdf_mem_set((uint8_t *) pBeaconStruct,
1568 sizeof(tSirProbeRespBeacon), 0);
1569
1570
1571 if ((sir_parse_beacon_ie
1572 (pMac, pBeaconStruct, (uint8_t *)
1573 (pScanResult->BssDescriptor.ieFields),
1574 ieLen)) == eSIR_SUCCESS)
1575 sap_upd_chan_spec_params(
1576 pBeaconStruct,
1577 &channelWidth,
1578 &secondaryChannelOffset,
1579 &vhtSupport, &centerFreq,
1580 &centerFreq_2);
1581
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001582 /* Processing for each tCsrScanResultInfo in the tCsrScanResult DLink list */
1583 for (chn_num = 0; chn_num < pSpectInfoParams->numSpectChans;
1584 chn_num++) {
1585
1586 /*
1587 * if the Beacon has channel ID, use it other wise we will
1588 * rely on the channelIdSelf
1589 */
1590 if (pScanResult->BssDescriptor.channelId == 0)
1591 channel_id =
1592 pScanResult->BssDescriptor.channelIdSelf;
1593 else
1594 channel_id =
1595 pScanResult->BssDescriptor.channelId;
1596
1597 if (pSpectCh && (channel_id == pSpectCh->chNum)) {
1598 if (pSpectCh->rssiAgr <
1599 pScanResult->BssDescriptor.rssi)
1600 pSpectCh->rssiAgr =
1601 pScanResult->BssDescriptor.rssi;
1602
1603 ++pSpectCh->bssCount; /* Increment the count of BSS */
1604
1605 /*
1606 * Connsidering the Extension Channel
1607 * only in a channels
1608 */
1609 switch (operatingBand) {
1610 case eCSR_DOT11_MODE_11a:
1611 sap_interference_rssi_count_5G(
1612 pSpectCh, channelWidth,
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001613 secondaryChannelOffset,
1614 centerFreq,
1615 centerFreq_2,
Liangwei Dong71ed6502016-10-20 03:40:45 -04001616 channel_id,
1617 spectch_start,
1618 spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001619 break;
1620
1621 case eCSR_DOT11_MODE_11g:
Liangwei Dong71ed6502016-10-20 03:40:45 -04001622 sap_interference_rssi_count(pSpectCh,
1623 spectch_start, spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001624 break;
1625
1626 case eCSR_DOT11_MODE_abg:
Himanshu Agarwal4f503b82018-03-19 12:10:45 +05301627 if (pSpectCh->chNum >=
1628 SIR_11A_CHANNEL_BEGIN)
1629 sap_interference_rssi_count_5G(
1630 pSpectCh, channelWidth,
1631 secondaryChannelOffset,
1632 centerFreq,
1633 centerFreq_2,
1634 channel_id,
1635 spectch_start,
1636 spectch_end);
1637 else
1638 sap_interference_rssi_count(
1639 pSpectCh,
1640 spectch_start,
1641 spectch_end);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001642 break;
1643 }
1644
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301645 QDF_TRACE(QDF_MODULE_ID_SAP,
1646 QDF_TRACE_LEVEL_INFO_HIGH,
Jeff Johnsona7c0ddb2017-09-18 08:14:12 -07001647 "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 -08001648 __func__,
1649 pScanResult->BssDescriptor.
1650 channelIdSelf,
1651 pScanResult->BssDescriptor.channelId,
1652 pScanResult->BssDescriptor.rssi,
1653 pSpectCh->bssCount, pScanResult,
1654 pSpectCh->channelWidth,
1655 secondaryChannelOffset, centerFreq);
1656 pSpectCh++;
1657 break;
1658 } else {
1659 pSpectCh++;
1660 }
1661 }
1662
1663 pScanResult = sme_scan_result_get_next(halHandle, pResult);
1664 }
1665
1666 /* Calculate the weights for all channels in the spectrum pSpectCh */
1667 pSpectCh = pSpectInfoParams->pSpectCh;
1668
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301669 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001670 "In %s, Spectrum Channels Weight", __func__);
1671
1672 for (chn_num = 0; chn_num < (pSpectInfoParams->numSpectChans);
1673 chn_num++) {
1674
1675 /*
1676 rssi : Maximum received signal strength among all BSS on that channel
1677 bssCount : Number of BSS on that channel
1678 */
1679
1680 rssi = (int8_t) pSpectCh->rssiAgr;
1681 if (ch_in_pcl(sap_ctx, chn_num))
1682 rssi -= PCL_RSSI_DISCOUNT;
1683
Himanshu Agarwalfee2e362018-01-18 20:26:35 +05301684 if (pSpectCh->weight == SAP_ACS_WEIGHT_MAX)
1685 goto debug_info;
1686
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001687 pSpectCh->weight =
gaoleze5108942017-03-31 16:56:42 +08001688 SAPDFS_NORMALISE_1000 *
1689 (sapweight_rssi_count(sap_ctx, rssi,
1690 pSpectCh->bssCount) + sap_weight_channel_status(
1691 sap_ctx, sap_get_channel_status(pMac,
1692 pSpectCh->chNum)));
1693 if (pSpectCh->weight > SAP_ACS_WEIGHT_MAX)
1694 pSpectCh->weight = SAP_ACS_WEIGHT_MAX;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001695 pSpectCh->weight_copy = pSpectCh->weight;
1696
Himanshu Agarwalfee2e362018-01-18 20:26:35 +05301697debug_info:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001698 /* ------ Debug Info ------ */
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301699 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001700 "In %s, Chan=%d Weight= %d rssiAgr=%d bssCount=%d",
1701 __func__, pSpectCh->chNum, pSpectCh->weight,
1702 pSpectCh->rssiAgr, pSpectCh->bssCount);
1703 /* ------ Debug Info ------ */
1704 pSpectCh++;
1705 }
gaoleze5108942017-03-31 16:56:42 +08001706 sap_clear_channel_status(pMac);
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301707 qdf_mem_free(pBeaconStruct);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001708}
1709
1710/*==========================================================================
1711 FUNCTION sap_chan_sel_exit
1712
1713 DESCRIPTION
1714 Exit function for free out the allocated memory, to be called
1715 at the end of the dfsSelectChannel function
1716
1717 DEPENDENCIES
1718 NA.
1719
1720 PARAMETERS
1721
1722 IN
1723 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
1724
1725 RETURN VALUE
1726 void : NULL
1727
1728 SIDE EFFECTS
1729 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001730static void sap_chan_sel_exit(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001731{
1732 /* Free all the allocated memory */
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301733 qdf_mem_free(pSpectInfoParams->pSpectCh);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001734}
1735
1736/*==========================================================================
1737 FUNCTION sap_sort_chl_weight
1738
1739 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07001740 Function to sort the channels with the least weight first for 20MHz channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001741
1742 DEPENDENCIES
1743 NA.
1744
1745 PARAMETERS
1746
1747 IN
1748 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
1749
1750 RETURN VALUE
1751 void : NULL
1752
1753 SIDE EFFECTS
1754 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001755static void sap_sort_chl_weight(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001756{
1757 tSapSpectChInfo temp;
1758
1759 tSapSpectChInfo *pSpectCh = NULL;
1760 uint32_t i = 0, j = 0, minWeightIndex = 0;
1761
1762 pSpectCh = pSpectInfoParams->pSpectCh;
1763 for (i = 0; i < pSpectInfoParams->numSpectChans; i++) {
1764 minWeightIndex = i;
1765 for (j = i + 1; j < pSpectInfoParams->numSpectChans; j++) {
1766 if (pSpectCh[j].weight <
1767 pSpectCh[minWeightIndex].weight) {
1768 minWeightIndex = j;
Yeshwanth Sriram Guntuka273889e2018-02-16 17:11:46 +05301769 } else if (pSpectCh[j].weight ==
1770 pSpectCh[minWeightIndex].weight) {
1771 if (pSpectCh[j].bssCount <
1772 pSpectCh[minWeightIndex].bssCount)
1773 minWeightIndex = j;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001774 }
1775 }
1776 if (minWeightIndex != i) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301777 qdf_mem_copy(&temp, &pSpectCh[minWeightIndex],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001778 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301779 qdf_mem_copy(&pSpectCh[minWeightIndex], &pSpectCh[i],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001780 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05301781 qdf_mem_copy(&pSpectCh[i], &temp, sizeof(*pSpectCh));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001782 }
1783 }
1784}
1785
1786/**
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07001787 * set_ht80_chl_bit() - to set available channel to ht80 channel bitmap
bingse2782382017-03-23 10:34:52 +08001788 * @channel_bitmap: Pointer to the chan_bonding_bitmap structure
1789 * @spect_info_params: Pointer to the tSapChSelSpectInfo structure
1790 *
1791 * Return: none
1792 */
1793static void set_ht80_chl_bit(chan_bonding_bitmap *channel_bitmap,
1794 tSapChSelSpectInfo *spec_info_params)
1795{
1796 uint8_t i, j;
1797 tSapSpectChInfo *spec_info;
1798 int start_channel = 0;
1799
1800 channel_bitmap->chanBondingSet[0].startChannel =
1801 acs_ht80_channels[0].chStartNum;
1802 channel_bitmap->chanBondingSet[1].startChannel =
1803 acs_ht80_channels[1].chStartNum;
1804 channel_bitmap->chanBondingSet[2].startChannel =
1805 acs_ht80_channels[2].chStartNum;
1806 channel_bitmap->chanBondingSet[3].startChannel =
1807 acs_ht80_channels[3].chStartNum;
1808 channel_bitmap->chanBondingSet[4].startChannel =
1809 acs_ht80_channels[4].chStartNum;
1810 channel_bitmap->chanBondingSet[5].startChannel =
1811 acs_ht80_channels[5].chStartNum;
1812
1813 spec_info = spec_info_params->pSpectCh;
1814 for (j = 0; j < spec_info_params->numSpectChans; j++) {
1815 for (i = 0; i < MAX_80MHZ_BANDS; i++) {
1816 start_channel =
1817 channel_bitmap->chanBondingSet[i].startChannel;
1818 if (spec_info[j].chNum >= start_channel &&
1819 (spec_info[j].chNum <= start_channel + 12)) {
1820 channel_bitmap->chanBondingSet[i].channelMap |=
1821 1 << ((spec_info[j].chNum -
1822 start_channel)/4);
1823 break;
1824 }
1825 }
1826 }
1827}
1828
1829/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001830 * sap_sort_chl_weight_ht80() - to sort the channels with the least weight
1831 * @pSpectInfoParams: Pointer to the tSapChSelSpectInfo structure
1832 *
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07001833 * Function to sort the channels with the least weight first for HT80 channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001834 *
1835 * Return: none
1836 */
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001837static void sap_sort_chl_weight_ht80(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001838{
1839 uint8_t i, j, n;
1840 tSapSpectChInfo *pSpectInfo;
1841 uint8_t minIdx;
bingse2782382017-03-23 10:34:52 +08001842 int start_channel = 0;
1843 chan_bonding_bitmap *channel_bitmap;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001844
bingse2782382017-03-23 10:34:52 +08001845 channel_bitmap = qdf_mem_malloc(sizeof(chan_bonding_bitmap));
1846 if (NULL == channel_bitmap) {
1847 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_DEBUG,
1848 "%s: Failed to allocate memory", __func__);
1849 return;
1850 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001851 pSpectInfo = pSpectInfoParams->pSpectCh;
1852 /* for each HT80 channel, calculate the combined weight of the
1853 four 20MHz weight */
1854 for (i = 0; i < ARRAY_SIZE(acs_ht80_channels); i++) {
1855 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
1856 if (pSpectInfo[j].chNum ==
1857 acs_ht80_channels[i].chStartNum)
1858 break;
1859 }
1860 if (j == pSpectInfoParams->numSpectChans)
1861 continue;
1862
1863 if (!(((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 1].chNum) &&
1864 ((pSpectInfo[j].chNum + 8) ==
1865 pSpectInfo[j + 2].chNum) &&
1866 ((pSpectInfo[j].chNum + 12) ==
1867 pSpectInfo[j + 3].chNum))) {
1868 /*
1869 * some channels does not exist in pSectInfo array,
1870 * skip this channel and those in the same HT80 width
1871 */
1872 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 4;
1873 if ((pSpectInfo[j].chNum + 4) ==
1874 pSpectInfo[j + 1].chNum)
1875 pSpectInfo[j + 1].weight =
1876 SAP_ACS_WEIGHT_MAX * 4;
1877 if ((pSpectInfo[j].chNum + 8) ==
1878 pSpectInfo[j + 2].chNum)
1879 pSpectInfo[j + 2].weight =
1880 SAP_ACS_WEIGHT_MAX * 4;
1881 if ((pSpectInfo[j].chNum + 12) ==
1882 pSpectInfo[j + 3].chNum)
1883 pSpectInfo[j + 3].weight =
1884 SAP_ACS_WEIGHT_MAX * 4;
1885 continue;
1886 }
1887 /*found the channel, add the 4 adjacent channels' weight */
1888 acs_ht80_channels[i].weight = pSpectInfo[j].weight +
1889 pSpectInfo[j + 1].weight + pSpectInfo[j + 2].weight +
1890 pSpectInfo[j + 3].weight;
1891 /* find best channel among 4 channels as the primary channel */
1892 if ((pSpectInfo[j].weight + pSpectInfo[j + 1].weight) <
1893 (pSpectInfo[j + 2].weight + pSpectInfo[j + 3].weight)) {
1894 /* lower 2 channels are better choice */
1895 if (pSpectInfo[j].weight < pSpectInfo[j + 1].weight)
1896 minIdx = 0;
1897 else
1898 minIdx = 1;
1899 } else if (pSpectInfo[j + 2].weight <=
1900 pSpectInfo[j + 3].weight) {
1901 /* upper 2 channels are better choice */
1902 minIdx = 2;
1903 } else {
1904 minIdx = 3;
1905 }
1906
1907 /*
1908 * set all 4 channels to max value first, then reset the
1909 * best channel as the selected primary channel, update its
1910 * weightage with the combined weight value
1911 */
1912 for (n = 0; n < 4; n++)
1913 pSpectInfo[j + n].weight = SAP_ACS_WEIGHT_MAX * 4;
1914
1915 pSpectInfo[j + minIdx].weight = acs_ht80_channels[i].weight;
1916 }
1917
bingse2782382017-03-23 10:34:52 +08001918 /*
1919 * mark the weight of the channel that can't satisfy 80MHZ
1920 * as max value, so that it will be sorted to the bottom
1921 */
1922 set_ht80_chl_bit(channel_bitmap, pSpectInfoParams);
1923 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
1924 for (i = 0; i < MAX_80MHZ_BANDS; i++) {
1925 start_channel =
1926 channel_bitmap->chanBondingSet[i].startChannel;
1927 if (pSpectInfo[j].chNum >= start_channel &&
1928 (pSpectInfo[j].chNum <=
1929 start_channel + 12) &&
1930 channel_bitmap->chanBondingSet[i].channelMap !=
1931 SAP_80MHZ_MASK)
1932 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 4;
1933 }
1934 }
1935
Himanshu Agarwal75e74412018-02-01 20:51:47 +05301936 /*
1937 * Assign max weight(SAP_ACS_WEIGHT_MAX * 4) to 2.4 Ghz channels
1938 * and channel 165 as they cannot be part of a 80Mhz channel bonding.
1939 */
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001940 pSpectInfo = pSpectInfoParams->pSpectCh;
1941 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
Himanshu Agarwal75e74412018-02-01 20:51:47 +05301942 if ((pSpectInfo[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_1) &&
1943 pSpectInfo[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_14)) ||
1944 (CHANNEL_165 == pSpectInfo[j].chNum))
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001945 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 4;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001946 }
1947
Manishekar Chandrasekaran44e334f2016-05-30 16:42:50 +05301948 sap_sort_chl_weight(pSpectInfoParams);
1949
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001950 pSpectInfo = pSpectInfoParams->pSpectCh;
1951 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05301952 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001953 FL("Channel=%d Weight= %d rssi=%d bssCount=%d"),
1954 pSpectInfo->chNum, pSpectInfo->weight,
1955 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
1956 pSpectInfo++;
1957 }
bingse2782382017-03-23 10:34:52 +08001958 qdf_mem_free(channel_bitmap);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08001959}
1960
1961/**
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001962 * sap_sort_chl_weight_vht160() - to sort the channels with the least weight
1963 * @pSpectInfoParams: Pointer to the tSapChSelSpectInfo structure
1964 *
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07001965 * Function to sort the channels with the least weight first for VHT160 channels
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001966 *
1967 * Return: none
1968 */
Jeff Johnson464f7ea2016-10-07 10:21:26 -07001969static void sap_sort_chl_weight_vht160(tSapChSelSpectInfo *pSpectInfoParams)
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07001970{
1971 uint8_t i, j, n, idx;
1972 tSapSpectChInfo *pSpectInfo;
1973 uint8_t minIdx;
1974
1975 pSpectInfo = pSpectInfoParams->pSpectCh;
1976 /* for each VHT160 channel, calculate the combined weight of the
1977 8 20MHz weight */
1978 for (i = 0; i < ARRAY_SIZE(acs_vht160_channels); i++) {
1979 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
1980 if (pSpectInfo[j].chNum ==
1981 acs_vht160_channels[i].chStartNum)
1982 break;
1983 }
1984 if (j == pSpectInfoParams->numSpectChans)
1985 continue;
1986
1987 if (!(((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 1].chNum) &&
1988 ((pSpectInfo[j].chNum + 8) ==
1989 pSpectInfo[j + 2].chNum) &&
1990 ((pSpectInfo[j].chNum + 12) ==
1991 pSpectInfo[j + 3].chNum) &&
1992 ((pSpectInfo[j].chNum + 16) ==
1993 pSpectInfo[j + 4].chNum) &&
1994 ((pSpectInfo[j].chNum + 20) ==
1995 pSpectInfo[j + 5].chNum) &&
1996 ((pSpectInfo[j].chNum + 24) ==
1997 pSpectInfo[j + 6].chNum) &&
1998 ((pSpectInfo[j].chNum + 28) ==
1999 pSpectInfo[j + 7].chNum))) {
2000 /*
2001 * some channels does not exist in pSectInfo array,
2002 * skip this channel and those in the same VHT160 width
2003 */
2004 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 8;
2005 if ((pSpectInfo[j].chNum + 4) ==
2006 pSpectInfo[j + 1].chNum)
2007 pSpectInfo[j + 1].weight =
2008 SAP_ACS_WEIGHT_MAX * 8;
2009 if ((pSpectInfo[j].chNum + 8) ==
2010 pSpectInfo[j + 2].chNum)
2011 pSpectInfo[j + 2].weight =
2012 SAP_ACS_WEIGHT_MAX * 8;
2013 if ((pSpectInfo[j].chNum + 12) ==
2014 pSpectInfo[j + 3].chNum)
2015 pSpectInfo[j + 3].weight =
2016 SAP_ACS_WEIGHT_MAX * 8;
2017 if ((pSpectInfo[j].chNum + 16) ==
2018 pSpectInfo[j + 4].chNum)
2019 pSpectInfo[j + 4].weight =
2020 SAP_ACS_WEIGHT_MAX * 8;
2021 if ((pSpectInfo[j].chNum + 20) ==
2022 pSpectInfo[j + 5].chNum)
2023 pSpectInfo[j + 5].weight =
2024 SAP_ACS_WEIGHT_MAX * 8;
2025 if ((pSpectInfo[j].chNum + 24) ==
2026 pSpectInfo[j + 6].chNum)
2027 pSpectInfo[j + 6].weight =
2028 SAP_ACS_WEIGHT_MAX * 8;
2029 if ((pSpectInfo[j].chNum + 28) ==
2030 pSpectInfo[j + 7].chNum)
2031 pSpectInfo[j + 7].weight =
2032 SAP_ACS_WEIGHT_MAX * 8;
2033 continue;
2034 }
2035 /*found the channel, add the 7 adjacent channels' weight */
2036 acs_vht160_channels[i].weight = pSpectInfo[j].weight +
2037 pSpectInfo[j + 1].weight + pSpectInfo[j + 2].weight +
2038 pSpectInfo[j + 3].weight + pSpectInfo[j + 4].weight +
2039 pSpectInfo[j + 5].weight + pSpectInfo[j + 6].weight +
2040 pSpectInfo[j + 7].weight;
2041
2042 /* find best channel among 8 channels as the primary channel */
2043 if ((pSpectInfo[j].weight + pSpectInfo[j + 1].weight +
2044 pSpectInfo[j + 2].weight + pSpectInfo[j + 3].weight) >
2045 (pSpectInfo[j + 4].weight + pSpectInfo[j + 5].weight +
2046 pSpectInfo[j + 6].weight + pSpectInfo[j + 7].weight))
2047 idx = 4;
2048 else
2049 idx = 0;
2050 /* find best channel among 4 channels as the primary channel */
2051 if ((pSpectInfo[j + idx].weight +
2052 pSpectInfo[j + idx + 1].weight) <
2053 (pSpectInfo[j + idx + 2].weight +
2054 pSpectInfo[j + idx + 3].weight)) {
2055 /* lower 2 channels are better choice */
2056 if (pSpectInfo[j + idx].weight <
2057 pSpectInfo[j + idx + 1].weight)
2058 minIdx = 0 + idx;
2059 else
2060 minIdx = 1 + idx;
2061 } else if (pSpectInfo[j + idx + 2].weight <=
2062 pSpectInfo[j + idx + 3].weight) {
2063 /* upper 2 channels are better choice */
2064 minIdx = 2 + idx;
2065 } else {
2066 minIdx = 3 + idx;
2067 }
2068
2069 /*
2070 * set all 8 channels to max value first, then reset the
2071 * best channel as the selected primary channel, update its
2072 * weightage with the combined weight value
2073 */
2074 for (n = 0; n < 8; n++)
2075 pSpectInfo[j + n].weight = SAP_ACS_WEIGHT_MAX * 8;
2076
2077 pSpectInfo[j + minIdx].weight = acs_vht160_channels[i].weight;
2078 }
2079
Himanshu Agarwal75e74412018-02-01 20:51:47 +05302080 /*
2081 * Assign max weight(SAP_ACS_WEIGHT_MAX * 8) to 2.4 Ghz channels
2082 * and channel 132-165 as they cannot be part of a 160Mhz channel
2083 * bonding.
2084 */
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002085 pSpectInfo = pSpectInfoParams->pSpectCh;
2086 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
Himanshu Agarwal75e74412018-02-01 20:51:47 +05302087 if ((pSpectInfo[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_1) &&
2088 pSpectInfo[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_14)) ||
2089 (pSpectInfo[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_132) &&
2090 pSpectInfo[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_165)))
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002091 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 8;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002092 }
2093
Manishekar Chandrasekaran44e334f2016-05-30 16:42:50 +05302094 sap_sort_chl_weight(pSpectInfoParams);
2095
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002096 pSpectInfo = pSpectInfoParams->pSpectCh;
2097 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302098 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002099 FL("Channel=%d Weight= %d rssi=%d bssCount=%d"),
2100 pSpectInfo->chNum, pSpectInfo->weight,
2101 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
2102 pSpectInfo++;
2103 }
2104}
2105
2106/**
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302107 * sap_allocate_max_weight_ht40_24_g() - allocate max weight for 40Mhz
2108 * to all 2.4Ghz channels
2109 * @spect_info_params: Pointer to the tSapChSelSpectInfo structure
2110 *
2111 * Return: none
2112 */
2113static void sap_allocate_max_weight_ht40_24_g(
2114 tSapChSelSpectInfo *spect_info_params)
2115{
2116 tSapSpectChInfo *spect_info;
2117 uint8_t j;
2118
2119 /*
2120 * Assign max weight for 40Mhz (SAP_ACS_WEIGHT_MAX * 2) to all
2121 * 2.4 Ghz channels
2122 */
2123 spect_info = spect_info_params->pSpectCh;
2124 for (j = 0; j < spect_info_params->numSpectChans; j++) {
2125 if ((spect_info[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_1) &&
2126 spect_info[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_14)))
2127 spect_info[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2128 }
2129}
2130
2131/**
2132 * sap_allocate_max_weight_ht40_5_g() - allocate max weight for 40Mhz
2133 * to all 5Ghz channels
2134 * @spect_info_params: Pointer to the tSapChSelSpectInfo structure
2135 *
2136 * Return: none
2137 */
2138static void sap_allocate_max_weight_ht40_5_g(
2139 tSapChSelSpectInfo *spect_info_params)
2140{
2141 tSapSpectChInfo *spect_info;
2142 uint8_t j;
2143
2144 /*
2145 * Assign max weight for 40Mhz (SAP_ACS_WEIGHT_MAX * 2) to all
2146 * 5 Ghz channels
2147 */
2148 spect_info = spect_info_params->pSpectCh;
2149 for (j = 0; j < spect_info_params->numSpectChans; j++) {
2150 if ((spect_info[j].chNum >= WLAN_REG_CH_NUM(CHAN_ENUM_36) &&
2151 spect_info[j].chNum <= WLAN_REG_CH_NUM(CHAN_ENUM_165)))
2152 spect_info[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2153 }
2154}
2155
2156/**
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002157 * sap_sort_chl_weight_ht40_24_g() - to sort channel with the least weight
2158 * @pSpectInfoParams: Pointer to the tSapChSelSpectInfo structure
2159 *
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07002160 * Function to sort the channels with the least weight first for HT40 channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002161 *
2162 * Return: none
2163 */
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002164static void sap_sort_chl_weight_ht40_24_g(tSapChSelSpectInfo *pSpectInfoParams,
2165 v_REGDOMAIN_t domain)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002166{
2167 uint8_t i, j;
2168 tSapSpectChInfo *pSpectInfo;
2169 uint32_t tmpWeight1, tmpWeight2;
bingse2782382017-03-23 10:34:52 +08002170 uint32_t ht40plus2gendch = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002171
2172 pSpectInfo = pSpectInfoParams->pSpectCh;
2173 /*
2174 * for each HT40 channel, calculate the combined weight of the
2175 * two 20MHz weight
2176 */
2177 for (i = 0; i < ARRAY_SIZE(acs_ht40_channels24_g); i++) {
2178 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2179 if (pSpectInfo[j].chNum ==
2180 acs_ht40_channels24_g[i].chStartNum)
2181 break;
2182 }
2183 if (j == pSpectInfoParams->numSpectChans)
2184 continue;
2185
2186 if (!((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 4].chNum)) {
2187 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2188 continue;
2189 }
2190 /*
2191 * check if there is another channel combination possiblity
2192 * e.g., {1, 5} & {5, 9}
2193 */
2194 if ((pSpectInfo[j + 4].chNum + 4) == pSpectInfo[j + 8].chNum) {
2195 /* need to compare two channel pairs */
2196 tmpWeight1 = pSpectInfo[j].weight +
2197 pSpectInfo[j + 4].weight;
2198 tmpWeight2 = pSpectInfo[j + 4].weight +
2199 pSpectInfo[j + 8].weight;
2200 if (tmpWeight1 <= tmpWeight2) {
2201 if (pSpectInfo[j].weight <=
2202 pSpectInfo[j + 4].weight) {
2203 pSpectInfo[j].weight =
2204 tmpWeight1;
2205 pSpectInfo[j + 4].weight =
2206 SAP_ACS_WEIGHT_MAX * 2;
2207 pSpectInfo[j + 8].weight =
2208 SAP_ACS_WEIGHT_MAX * 2;
2209 } else {
2210 pSpectInfo[j + 4].weight =
2211 tmpWeight1;
2212 /* for secondary channel selection */
2213 pSpectInfo[j].weight =
2214 SAP_ACS_WEIGHT_MAX * 2
2215 - 1;
2216 pSpectInfo[j + 8].weight =
2217 SAP_ACS_WEIGHT_MAX * 2;
2218 }
2219 } else {
2220 if (pSpectInfo[j + 4].weight <=
2221 pSpectInfo[j + 8].weight) {
2222 pSpectInfo[j + 4].weight =
2223 tmpWeight2;
2224 pSpectInfo[j].weight =
2225 SAP_ACS_WEIGHT_MAX * 2;
2226 /* for secondary channel selection */
2227 pSpectInfo[j + 8].weight =
2228 SAP_ACS_WEIGHT_MAX * 2
2229 - 1;
2230 } else {
2231 pSpectInfo[j + 8].weight =
2232 tmpWeight2;
2233 pSpectInfo[j].weight =
2234 SAP_ACS_WEIGHT_MAX * 2;
2235 pSpectInfo[j + 4].weight =
2236 SAP_ACS_WEIGHT_MAX * 2;
2237 }
2238 }
2239 } else {
bingsaa6f96a2017-09-11 09:49:43 +08002240 tmpWeight1 = pSpectInfo[j].weight_copy +
2241 pSpectInfo[j + 4].weight_copy;
2242 if (pSpectInfo[j].weight_copy <=
2243 pSpectInfo[j + 4].weight_copy) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002244 pSpectInfo[j].weight = tmpWeight1;
2245 pSpectInfo[j + 4].weight =
2246 SAP_ACS_WEIGHT_MAX * 2;
2247 } else {
2248 pSpectInfo[j + 4].weight = tmpWeight1;
2249 pSpectInfo[j].weight =
2250 SAP_ACS_WEIGHT_MAX * 2;
2251 }
2252 }
2253 }
bingse2782382017-03-23 10:34:52 +08002254 /*
2255 * Every channel should be checked. Add the check for the omissive
2256 * channel. Mark the channel whose combination can't satisfy 40MHZ
2257 * as max value, so that it will be sorted to the bottom.
2258 */
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002259 if (REGDOMAIN_FCC == domain)
bingse2782382017-03-23 10:34:52 +08002260 ht40plus2gendch = HT40PLUS_2G_FCC_CH_END;
2261 else
2262 ht40plus2gendch = HT40PLUS_2G_EURJAP_CH_END;
2263 for (i = HT40MINUS_2G_CH_START; i <= ht40plus2gendch; i++) {
2264 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2265 if (pSpectInfo[j].chNum == i &&
2266 ((pSpectInfo[j].chNum + 4) !=
2267 pSpectInfo[j+4].chNum) &&
2268 ((pSpectInfo[j].chNum - 4) !=
2269 pSpectInfo[j-4].chNum))
2270 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2271 }
2272 }
2273 for (i = ht40plus2gendch + 1; i <= HT40MINUS_2G_CH_END; i++) {
2274 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2275 if (pSpectInfo[j].chNum == i &&
2276 (pSpectInfo[j].chNum - 4) !=
2277 pSpectInfo[j-4].chNum)
2278 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2279 }
2280 }
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302281
2282 pSpectInfo = pSpectInfoParams->pSpectCh;
2283 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
2284 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2285 "In %s, Channel=%d Weight= %d rssi=%d bssCount=%d",
2286 __func__, pSpectInfo->chNum, pSpectInfo->weight,
2287 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
2288 pSpectInfo++;
2289 }
2290
Manishekar Chandrasekaran44e334f2016-05-30 16:42:50 +05302291 sap_sort_chl_weight(pSpectInfoParams);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002292}
2293
2294/*==========================================================================
2295 FUNCTION sap_sort_chl_weight_ht40_5_g
2296
2297 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07002298 Function to sort the channels with the least weight first for HT40 channels
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002299
2300 DEPENDENCIES
2301 NA.
2302
2303 PARAMETERS
2304
2305 IN
2306 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
2307
2308 RETURN VALUE
2309 void : NULL
2310
2311 SIDE EFFECTS
2312 ============================================================================*/
Jeff Johnson464f7ea2016-10-07 10:21:26 -07002313static void sap_sort_chl_weight_ht40_5_g(tSapChSelSpectInfo *pSpectInfoParams)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002314{
2315 uint8_t i, j;
2316 tSapSpectChInfo *pSpectInfo;
2317
2318 pSpectInfo = pSpectInfoParams->pSpectCh;
2319 /*for each HT40 channel, calculate the combined weight of the
2320 two 20MHz weight */
2321 for (i = 0; i < ARRAY_SIZE(acs_ht40_channels5_g); i++) {
2322 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2323 if (pSpectInfo[j].chNum ==
2324 acs_ht40_channels5_g[i].chStartNum)
2325 break;
2326 }
2327 if (j == pSpectInfoParams->numSpectChans)
2328 continue;
2329
2330 /* found the channel, add the two adjacent channels' weight */
2331 if ((pSpectInfo[j].chNum + 4) == pSpectInfo[j + 1].chNum) {
2332 acs_ht40_channels5_g[i].weight = pSpectInfo[j].weight +
2333 pSpectInfo[j + 1].weight;
2334 /* select better of the adjact channel as the primary channel */
2335 if (pSpectInfo[j].weight <= pSpectInfo[j + 1].weight) {
2336 pSpectInfo[j].weight =
2337 acs_ht40_channels5_g[i].weight;
2338 /* mark the adjacent channel's weight as max value so
2339 that it will be sorted to the bottom */
2340 pSpectInfo[j + 1].weight =
2341 SAP_ACS_WEIGHT_MAX * 2;
2342 } else {
2343 pSpectInfo[j + 1].weight =
2344 acs_ht40_channels5_g[i].weight;
2345 /* mark the adjacent channel's weight as max value so
2346 that it will be sorted to the bottom */
2347 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2348 }
2349
2350 } else
2351 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2352 }
2353
bingse2782382017-03-23 10:34:52 +08002354 /*
2355 *Every channel should be checked. Add the check for the omissive
2356 * channel. Mark the channel whose combination can't satisfy 40MHZ
2357 * as max value, so that it will be sorted to the bottom
2358 */
2359 for (j = 1; j < pSpectInfoParams->numSpectChans; j++) {
2360 for (i = 0; i < ARRAY_SIZE(acs_ht40_channels5_g); i++) {
2361 if (pSpectInfo[j].chNum ==
2362 (acs_ht40_channels5_g[i].chStartNum +
2363 4) &&
2364 pSpectInfo[j - 1].chNum !=
2365 acs_ht40_channels5_g[i].chStartNum) {
2366 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2367 break;
2368 }
2369 }
2370 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002371 /* avoid channel 165 by setting its weight to max */
2372 pSpectInfo = pSpectInfoParams->pSpectCh;
2373 for (j = 0; j < pSpectInfoParams->numSpectChans; j++) {
2374 if (CHANNEL_165 == pSpectInfo[j].chNum) {
2375 pSpectInfo[j].weight = SAP_ACS_WEIGHT_MAX * 2;
2376 break;
2377 }
2378 }
2379
2380 pSpectInfo = pSpectInfoParams->pSpectCh;
2381 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302382 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002383 "In %s, Channel=%d Weight= %d rssi=%d bssCount=%d",
2384 __func__, pSpectInfo->chNum, pSpectInfo->weight,
2385 pSpectInfo->rssiAgr, pSpectInfo->bssCount);
2386 pSpectInfo++;
2387 }
2388
2389 sap_sort_chl_weight(pSpectInfoParams);
2390}
2391
2392/*==========================================================================
2393 FUNCTION sap_sort_chl_weight_all
2394
2395 DESCRIPTION
Jeff Johnsonc7e4d162018-05-12 16:20:34 -07002396 Function to sort the channels with the least weight first
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002397
2398 DEPENDENCIES
2399 NA.
2400
2401 PARAMETERS
2402
2403 IN
Jeff Johnsone13d8062017-09-28 06:54:55 -07002404 sap_ctx : Pointer to the struct sap_context *structure
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002405 pSpectInfoParams : Pointer to the tSapChSelSpectInfo structure
2406
2407 RETURN VALUE
2408 void : NULL
2409
2410 SIDE EFFECTS
2411 ============================================================================*/
Jeff Johnsone13d8062017-09-28 06:54:55 -07002412static void sap_sort_chl_weight_all(struct sap_context *sap_ctx,
Jeff Johnson464f7ea2016-10-07 10:21:26 -07002413 tSapChSelSpectInfo *pSpectInfoParams,
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002414 uint32_t operatingBand,
2415 v_REGDOMAIN_t domain)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002416{
2417 tSapSpectChInfo *pSpectCh = NULL;
2418 uint32_t j = 0;
2419#ifndef SOFTAP_CHANNEL_RANGE
2420 uint32_t i = 0;
2421#endif
2422
2423 pSpectCh = pSpectInfoParams->pSpectCh;
2424#ifdef SOFTAP_CHANNEL_RANGE
2425
Jeff Johnsone13d8062017-09-28 06:54:55 -07002426 switch (sap_ctx->acs_cfg->ch_width) {
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002427 case CH_WIDTH_40MHZ:
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302428 /*
2429 * Assign max weight to all 5Ghz channels when operating band
2430 * is 11g and to all 2.4Ghz channels when operating band is 11a
2431 * or 11abg to avoid selection in ACS algorithm for starting SAP
2432 */
2433 if (eCSR_DOT11_MODE_11g == operatingBand) {
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002434 sap_sort_chl_weight_ht40_24_g(pSpectInfoParams, domain);
Himanshu Agarwal91c5c0f2018-02-13 14:40:56 +05302435 sap_allocate_max_weight_ht40_5_g(pSpectInfoParams);
2436 } else {
2437 sap_allocate_max_weight_ht40_24_g(pSpectInfoParams);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002438 sap_sort_chl_weight_ht40_5_g(pSpectInfoParams);
2439 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002440 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002441 case CH_WIDTH_80MHZ:
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002442 case CH_WIDTH_80P80MHZ:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002443 sap_sort_chl_weight_ht80(pSpectInfoParams);
2444 break;
Kiran Kumar Lokereb3d8b5b2015-10-06 19:33:42 -07002445 case CH_WIDTH_160MHZ:
2446 sap_sort_chl_weight_vht160(pSpectInfoParams);
2447 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002448 case CH_WIDTH_20MHZ:
2449 default:
2450 /* Sorting the channels as per weights as 20MHz channels */
2451 sap_sort_chl_weight(pSpectInfoParams);
2452 }
2453
2454#else
2455 /* Sorting the channels as per weights */
2456 for (i = 0; i < SPECT_24GHZ_CH_COUNT; i++) {
2457 minWeightIndex = i;
2458 for (j = i + 1; j < SPECT_24GHZ_CH_COUNT; j++) {
2459 if (pSpectCh[j].weight <
2460 pSpectCh[minWeightIndex].weight) {
2461 minWeightIndex = j;
2462 }
2463 }
2464 if (minWeightIndex != i) {
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302465 qdf_mem_copy(&temp, &pSpectCh[minWeightIndex],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002466 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302467 qdf_mem_copy(&pSpectCh[minWeightIndex], &pSpectCh[i],
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002468 sizeof(*pSpectCh));
Anurag Chouhan600c3a02016-03-01 10:33:54 +05302469 qdf_mem_copy(&pSpectCh[i], &temp, sizeof(*pSpectCh));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002470 }
2471 }
2472#endif
2473
2474 /* For testing */
Ravi Joshi9788fcd2018-02-13 15:12:22 -08002475 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002476 "In %s, Sorted Spectrum Channels Weight", __func__);
2477 pSpectCh = pSpectInfoParams->pSpectCh;
2478 for (j = 0; j < (pSpectInfoParams->numSpectChans); j++) {
Ravi Joshi9788fcd2018-02-13 15:12:22 -08002479 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002480 "In %s, Channel=%d Weight= %d rssi=%d bssCount=%d",
2481 __func__, pSpectCh->chNum, pSpectCh->weight,
2482 pSpectCh->rssiAgr, pSpectCh->bssCount);
2483 pSpectCh++;
2484 }
2485
2486}
2487
Naveen Rawatbec64d92017-09-13 14:35:21 -07002488/**
2489 * sap_is_ch_non_overlap() - returns true if non-overlapping channel
2490 * @sap_ctx: Sap context
2491 * @ch: channel number
2492 *
2493 * Returns: true if non-overlapping (1, 6, 11) channel, false otherwise
2494 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002495static bool sap_is_ch_non_overlap(struct sap_context *sap_ctx, uint16_t ch)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002496{
Naveen Rawatbec64d92017-09-13 14:35:21 -07002497 if (sap_ctx->enableOverLapCh)
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002498 return true;
Naveen Rawatbec64d92017-09-13 14:35:21 -07002499
2500 if ((ch == CHANNEL_1) || (ch == CHANNEL_6) || (ch == CHANNEL_11))
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002501 return true;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002502
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002503 return false;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002504}
2505
Dustin Brown0ce56d32016-10-17 16:18:03 -07002506#ifdef FEATURE_WLAN_CH_AVOID
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002507/**
2508 * sap_select_channel_no_scan_result() - select SAP channel when no scan results
2509 * are available.
2510 * @sap_ctx: Sap context
2511 *
2512 * Returns: channel number if success, 0 otherwise
2513 */
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302514static uint8_t sap_select_channel_no_scan_result(tHalHandle hal,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002515 struct sap_context *sap_ctx)
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002516{
Mohit Khanna841044f2016-03-25 16:16:24 -07002517 enum channel_state ch_type;
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002518 uint8_t i, first_safe_ch_in_range = SAP_CHANNEL_NOT_SELECTED;
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302519 uint32_t dfs_master_cap_enabled;
Dustin Brown0ce56d32016-10-17 16:18:03 -07002520 uint32_t start_ch_num = sap_ctx->acs_cfg->start_ch;
2521 uint32_t end_ch_num = sap_ctx->acs_cfg->end_ch;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002522 tpAniSirGlobal mac_ctx = NULL;
2523
2524 mac_ctx = PMAC_STRUCT(hal);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002525
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002526 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2527 FL("start - end: %d - %d"), start_ch_num, end_ch_num);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002528
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302529 sme_cfg_get_int(hal, WNI_CFG_DFS_MASTER_ENABLED,
2530 &dfs_master_cap_enabled);
2531
2532 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2533 "%s: dfs_master %x", __func__, dfs_master_cap_enabled);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002534
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002535 /* get a channel in PCL and within the range */
2536 for (i = 0; i < sap_ctx->acs_cfg->pcl_ch_count; i++) {
2537 if ((sap_ctx->acs_cfg->pcl_channels[i] < start_ch_num) ||
2538 (sap_ctx->acs_cfg->pcl_channels[i] > end_ch_num))
2539 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002540
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002541 first_safe_ch_in_range = sap_ctx->acs_cfg->pcl_channels[i];
2542 break;
2543 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002544
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002545 if (SAP_CHANNEL_NOT_SELECTED != first_safe_ch_in_range)
2546 return first_safe_ch_in_range;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002547
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002548 for (i = 0; i < NUM_CHANNELS; i++) {
2549 if ((safe_channels[i].channelNumber < start_ch_num) ||
2550 (safe_channels[i].channelNumber > end_ch_num))
2551 continue;
2552
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002553 ch_type = wlan_reg_get_channel_state(mac_ctx->pdev,
2554 safe_channels[i].channelNumber);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002555
2556 if ((ch_type == CHANNEL_STATE_DISABLE) ||
2557 (ch_type == CHANNEL_STATE_INVALID))
2558 continue;
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302559 if ((!dfs_master_cap_enabled) &&
2560 (CHANNEL_STATE_DFS == ch_type)) {
2561 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2562 "%s: DFS master mode disabled. Skip DFS channel %d",
2563 __func__, safe_channels[i].channelNumber);
2564 continue;
2565 }
Agrawal Ashish65634612016-08-18 13:24:32 +05302566 if ((sap_ctx->dfs_mode == ACS_DFS_MODE_DISABLE) &&
2567 (CHANNEL_STATE_DFS == ch_type))
2568 continue;
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302569
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002570 if (safe_channels[i].isSafe == true) {
2571 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2572 FL("channel %d in the configuration is safe"),
2573 safe_channels[i].channelNumber);
2574 first_safe_ch_in_range = safe_channels[i].channelNumber;
2575 break;
2576 }
2577
2578 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2579 FL("channel %d in the configuration is unsafe"),
2580 safe_channels[i].channelNumber);
2581 }
2582
2583 /* if no channel selected return SAP_CHANNEL_NOT_SELECTED */
2584 return first_safe_ch_in_range;
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002585}
Dustin Brown0ce56d32016-10-17 16:18:03 -07002586#else
2587static uint8_t sap_select_channel_no_scan_result(tHalHandle hal,
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002588 struct sap_context *sap_ctx)
Dustin Brown0ce56d32016-10-17 16:18:03 -07002589{
2590 uint32_t start_ch_num = sap_ctx->acs_cfg->start_ch;
2591
2592 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2593 FL("start - end: %d - %d"),
2594 start_ch_num,
2595 sap_ctx->acs_cfg->end_ch);
2596
2597 sap_ctx->acs_cfg->pri_ch = start_ch_num;
2598 sap_ctx->acs_cfg->ht_sec_ch = 0;
2599
2600 /* pick the first channel in configured range */
2601 return start_ch_num;
2602}
2603#endif /* FEATURE_WLAN_CH_AVOID */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002604
2605/**
2606 * sap_select_channel() - select SAP channel
2607 * @hal: Pointer to HAL handle
2608 * @sap_ctx: Sap context
2609 * @scan_result: Pointer to tScanResultHandle
2610 *
2611 * Runs a algorithm to select the best channel to operate in based on BSS
2612 * rssi and bss count on each channel
2613 *
2614 * Returns: channel number if success, 0 otherwise
2615 */
Jeff Johnsonf1cd3c72017-09-14 07:18:06 -07002616uint8_t sap_select_channel(tHalHandle hal, struct sap_context *sap_ctx,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002617 tScanResultHandle scan_result)
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002618{
2619 /* DFS param object holding all the data req by the algo */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002620 tSapChSelSpectInfo spect_info_obj = { NULL, 0 };
2621 tSapChSelSpectInfo *spect_info = &spect_info_obj;
2622 uint8_t best_ch_num = SAP_CHANNEL_NOT_SELECTED;
bingse2782382017-03-23 10:34:52 +08002623 uint32_t ht40plus2gendch = 0;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002624 v_REGDOMAIN_t domain;
Arif Hussain21ad4342017-12-21 12:00:54 -08002625 uint8_t country[CDS_COUNTRY_CODE_LEN + 1];
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002626#ifdef SOFTAP_CHANNEL_RANGE
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002627 uint8_t count;
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002628 uint32_t start_ch_num, end_ch_num, tmp_ch_num, operating_band = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002629#endif
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002630 tpAniSirGlobal mac_ctx;
2631
2632 mac_ctx = PMAC_STRUCT(hal);
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302633 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002634 "In %s, Running SAP Ch Select", __func__);
2635
2636#ifdef FEATURE_WLAN_CH_AVOID
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002637 sap_update_unsafe_channel_list(hal, sap_ctx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002638#endif
2639
gaoleze5108942017-03-31 16:56:42 +08002640 /*
2641 * If ACS weight is not enabled on noise_floor/channel_free/tx_power,
2642 * then skip acs process if no bss found.
2643 */
2644 if (NULL == scan_result &&
2645 !(sap_ctx->auto_channel_select_weight & 0xffff00)) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302646 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002647 FL("No external AP present"));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002648
2649#ifndef SOFTAP_CHANNEL_RANGE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002650 return SAP_CHANNEL_NOT_SELECTED;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002651#else
Kondabattini, Ganesh13bb4b12016-09-04 16:16:53 +05302652 return sap_select_channel_no_scan_result(hal, sap_ctx);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002653#endif
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002654 }
2655
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002656 /* Initialize the structure pointed by spect_info */
Srinivas Girigowda74a66d62017-06-21 23:28:25 -07002657 if (sap_chan_sel_init(hal, spect_info, sap_ctx) != true) {
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302658 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_ERROR,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002659 FL("Ch Select initialization failed"));
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002660 return SAP_CHANNEL_NOT_SELECTED;
2661 }
2662 /* Compute the weight of the entire spectrum in the operating band */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002663 sap_compute_spect_weight(spect_info, hal, scan_result, sap_ctx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002664
2665#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
2666 /* process avoid channel IE to collect all channels to avoid */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002667 sap_process_avoid_ie(hal, sap_ctx, scan_result, spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002668#endif /* FEATURE_AP_MCC_CH_AVOIDANCE */
2669
Paul Zhang0f85b412018-01-18 19:14:51 +08002670 wlan_reg_read_current_country(mac_ctx->psoc, country);
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002671 wlan_reg_get_domain_from_country_code(&domain, country, SOURCE_DRIVER);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002672#ifdef SOFTAP_CHANNEL_RANGE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002673 start_ch_num = sap_ctx->acs_cfg->start_ch;
2674 end_ch_num = sap_ctx->acs_cfg->end_ch;
2675 SET_ACS_BAND(operating_band, sap_ctx);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002676
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002677 sap_ctx->acsBestChannelInfo.channelNum = 0;
2678 sap_ctx->acsBestChannelInfo.weight = SAP_ACS_WEIGHT_MAX;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002679
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002680 /* Sort the ch lst as per the computed weights, lesser weight first. */
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002681 sap_sort_chl_weight_all(sap_ctx, spect_info, operating_band, domain);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002682
2683 /*Loop till get the best channel in the given range */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002684 for (count = 0; count < spect_info->numSpectChans; count++) {
2685 if ((start_ch_num > spect_info->pSpectCh[count].chNum) ||
2686 (end_ch_num < spect_info->pSpectCh[count].chNum))
2687 continue;
2688
2689 if (best_ch_num == SAP_CHANNEL_NOT_SELECTED) {
2690 best_ch_num = spect_info->pSpectCh[count].chNum;
2691 /* check if best_ch_num is in preferred channel list */
2692 best_ch_num =
2693 sap_select_preferred_channel_from_channel_list(
2694 best_ch_num, sap_ctx, spect_info);
2695 /* if not in preferred ch lst, go to nxt best ch */
2696 if (best_ch_num == SAP_CHANNEL_NOT_SELECTED)
2697 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002698
2699#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002700 /*
2701 * Weight of the channels(device's AP is operating)
Jeff Johnson2cc31fd2018-05-05 23:54:23 -07002702 * increased to MAX+1 so that they will be chosen only
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002703 * when there is no other best channel to choose
2704 */
2705 if (sap_check_in_avoid_ch_list(sap_ctx, best_ch_num)) {
2706 best_ch_num = SAP_CHANNEL_NOT_SELECTED;
2707 continue;
2708 }
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002709#endif
2710
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002711 sap_ctx->acsBestChannelInfo.channelNum = best_ch_num;
2712 sap_ctx->acsBestChannelInfo.weight =
2713 spect_info->pSpectCh[count].weight_copy;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002714 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002715
2716 if (best_ch_num == SAP_CHANNEL_NOT_SELECTED)
2717 continue;
2718
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002719 if (operating_band != eCSR_DOT11_MODE_11g) {
2720 QDF_TRACE(QDF_MODULE_ID_SAP,
2721 QDF_TRACE_LEVEL_INFO_HIGH,
2722 "operating_band %d", operating_band);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002723 continue;
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002724 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002725
2726 /* Give preference to Non-overlap channels */
Naveen Rawatbec64d92017-09-13 14:35:21 -07002727 if (false == sap_is_ch_non_overlap(sap_ctx,
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002728 spect_info->pSpectCh[count].chNum)) {
2729 QDF_TRACE(QDF_MODULE_ID_SAP,
2730 QDF_TRACE_LEVEL_INFO_HIGH,
Naveen Rawatbec64d92017-09-13 14:35:21 -07002731 FL("ch: %d skipped as its overlapping ch"),
2732 spect_info->pSpectCh[count].chNum);
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002733 continue;
Tushnim Bhattacharyya03103fd2017-06-23 10:48:52 -07002734 }
2735
2736 if (wlan_reg_is_dfs_ch(mac_ctx->pdev,
2737 spect_info->pSpectCh[count].chNum) &&
2738 policy_mgr_disallow_mcc(mac_ctx->psoc,
2739 spect_info->pSpectCh[count].chNum)) {
2740 QDF_TRACE(QDF_MODULE_ID_SAP,
2741 QDF_TRACE_LEVEL_INFO_HIGH,
2742 "No DFS MCC");
2743 continue;
2744 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002745
bings14d1d3b2017-08-03 11:14:29 +08002746 if (spect_info->pSpectCh[count].weight_copy >
2747 sap_ctx->acsBestChannelInfo.weight)
2748 continue;
2749
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002750 tmp_ch_num = spect_info->pSpectCh[count].chNum;
gaoleze5108942017-03-31 16:56:42 +08002751 tmp_ch_num = sap_channel_in_acs_channel_list(
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002752 tmp_ch_num, sap_ctx, spect_info);
2753 if (tmp_ch_num == SAP_CHANNEL_NOT_SELECTED)
2754 continue;
2755
2756 best_ch_num = tmp_ch_num;
2757 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002758 }
2759#else
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002760 /* Sort the ch lst as per the computed weights, lesser weight first. */
2761 sap_sort_chl_weight_all(sap_ctx, hal, spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002762 /* Get the first channel in sorted array as best 20M Channel */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002763 best_ch_num = (uint8_t) spect_info->pSpectCh[0].chNum;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002764 /* Select Best Channel from Channel List if Configured */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002765 best_ch_num = sap_select_preferred_channel_from_channel_list(
2766 best_ch_num, sap_ctx, spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002767#endif
2768
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002769 /*
2770 * in case the best channel seleted is not in PCL and there is another
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002771 * channel which has same weightage and is in PCL, choose the one in
2772 * PCL
2773 */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002774 for (count = 0; count < spect_info->numSpectChans; count++) {
2775 if (!ch_in_pcl(sap_ctx, spect_info->pSpectCh[count].chNum) ||
2776 (spect_info->pSpectCh[count].weight !=
2777 sap_ctx->acsBestChannelInfo.weight))
2778 continue;
2779
2780 if (sap_select_preferred_channel_from_channel_list(
2781 spect_info->pSpectCh[count].chNum, sap_ctx, spect_info)
2782 == SAP_CHANNEL_NOT_SELECTED)
2783 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002784
2785#ifdef FEATURE_AP_MCC_CH_AVOIDANCE
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002786 if (sap_check_in_avoid_ch_list(sap_ctx, best_ch_num))
2787 continue;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002788#endif
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002789 best_ch_num = spect_info->pSpectCh[count].chNum;
2790 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
2791 FL("change best channel to %d in PCL"), best_ch_num);
2792 break;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002793 }
2794
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002795 sap_ctx->acs_cfg->pri_ch = best_ch_num;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002796 /* determine secondary channel for 2.4G channel 5, 6, 7 in HT40 */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002797 if ((operating_band != eCSR_DOT11_MODE_11g) ||
2798 (sap_ctx->acs_cfg->ch_width != CH_WIDTH_40MHZ))
2799 goto sap_ch_sel_end;
Kiran Kumar Lokerea3de2262017-04-12 12:15:04 -07002800 if (REGDOMAIN_FCC == domain)
bingse2782382017-03-23 10:34:52 +08002801 ht40plus2gendch = HT40PLUS_2G_FCC_CH_END;
2802 else
2803 ht40plus2gendch = HT40PLUS_2G_EURJAP_CH_END;
2804 if ((best_ch_num >= HT40MINUS_2G_CH_START) &&
2805 (best_ch_num <= ht40plus2gendch)) {
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002806 int weight_below, weight_above, i;
2807 tSapSpectChInfo *pspect_info;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002808
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002809 weight_below = weight_above = SAP_ACS_WEIGHT_MAX;
2810 pspect_info = spect_info->pSpectCh;
2811 for (i = 0; i < spect_info->numSpectChans; i++) {
2812 if (pspect_info[i].chNum == (best_ch_num - 4))
2813 weight_below = pspect_info[i].weight;
2814 if (pspect_info[i].chNum == (best_ch_num + 4))
2815 weight_above = pspect_info[i].weight;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002816 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002817
2818 if (weight_below < weight_above)
2819 sap_ctx->acs_cfg->ht_sec_ch =
2820 sap_ctx->acs_cfg->pri_ch - 4;
2821 else
2822 sap_ctx->acs_cfg->ht_sec_ch =
2823 sap_ctx->acs_cfg->pri_ch + 4;
2824 } else if (best_ch_num >= 1 && best_ch_num <= 4) {
2825 sap_ctx->acs_cfg->ht_sec_ch = sap_ctx->acs_cfg->pri_ch + 4;
bingse2782382017-03-23 10:34:52 +08002826 } else if (best_ch_num >= ht40plus2gendch && best_ch_num <=
2827 HT40MINUS_2G_CH_END) {
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002828 sap_ctx->acs_cfg->ht_sec_ch = sap_ctx->acs_cfg->pri_ch - 4;
2829 } else if (best_ch_num == 14) {
2830 sap_ctx->acs_cfg->ht_sec_ch = 0;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002831 }
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002832 sap_ctx->secondary_ch = sap_ctx->acs_cfg->ht_sec_ch;
2833
2834sap_ch_sel_end:
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002835 /* Free all the allocated memory */
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002836 sap_chan_sel_exit(spect_info);
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002837
Anurag Chouhanb2dc16f2016-02-25 11:47:37 +05302838 QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
Naveen Rawat365d1cb2016-02-05 12:10:43 -08002839 FL("Running SAP Ch select Completed, Ch=%d"), best_ch_num);
2840 if (best_ch_num > 0 && best_ch_num <= 252)
2841 return best_ch_num;
Prakash Dhavali7090c5f2015-11-02 17:55:19 -08002842 else
2843 return SAP_CHANNEL_NOT_SELECTED;
2844}