qcacld-3.0: Find best 6 GHz power type for connection

Find the best 6 GHz power type for connection
according to following regulatory policy:
1) SP power type is selected only if AP advertises
   SP and client supports SP.
2) LPI power type is selected only if AP advertises
   LPI and client supports LPI.
3) VLP power type is selected for the below cases,
   a) AP advertises VLP and client supports VLP
   b) AP advertises SP but client doesn't support
      SP but supports VLP.
   c) AP advertises LPI but client doesn't support
      LPI but supports VLP.

Change-Id: I582fb582e1e11b731a1c6cda01f4fc366f166143
CRs-Fixed: 3456192
This commit is contained in:
Surya Prakash Sivaraj 2024-01-09 14:54:21 +05:30 • committed by Ravindra Konda
commit 3ec26461cd
10 changed files with 54 additions and 64 deletions

View file

@ -1,6 +1,6 @@
/*
* Copyright (c) 2012-2020 The Linux Foundation. All rights reserved.
* Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2022,2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -1048,9 +1048,8 @@ struct join_req {
struct supported_channels supportedChannels;
bool enable_bcast_probe_rsp;
bool sae_pmk_cached;
bool same_ctry_code; /* If AP Country IE has same country code as */
/* STA programmed country */
uint8_t ap_power_type_6g; /* AP power type for 6G (LPI, SP, or VLP) */
uint8_t best_6g_power_type; /* AP power type for 6G (LPI, SP, or VLP) */
/* Pls make this as last variable in struct */
bool force_24ghz_in_ht20;
bool force_rsne_override;

View file

@ -1,5 +1,6 @@
/*
* Copyright (c) 2012-2020 The Linux Foundation. All rights reserved.
* Copyright (c) 2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -577,8 +578,8 @@ struct pe_session {
uint16_t prot_status_code;
tSirResultCodes result_code;
uint32_t dfs_regdomain;
/* AP power type */
uint8_t ap_power_type;
uint8_t ap_defined_power_type_6g;
uint8_t best_6g_power_type;
};
/*-------------------------------------------------------------------------

View file

@ -1,6 +1,6 @@
/*
* Copyright (c) 2012-2021 The Linux Foundation. All rights reserved.
* Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2022-2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -2325,7 +2325,7 @@ void lim_handle_add_bss_rsp(struct mac_context *mac_ctx,
}
tx_ops = wlan_reg_get_tx_ops(mac_ctx->psoc);
lim_calculate_tpc(mac_ctx, session_entry, 0, false);
lim_calculate_tpc(mac_ctx, session_entry);
if (tx_ops->set_tpc_power)
tx_ops->set_tpc_power(mac_ctx->psoc,
@ -2810,7 +2810,7 @@ static void lim_process_switch_channel_join_req(
goto error;
}
lim_calculate_tpc(mac_ctx, session_entry, 0, false);
lim_calculate_tpc(mac_ctx, session_entry);
if (tx_ops->set_tpc_power)
tx_ops->set_tpc_power(mac_ctx->psoc,

View file

@ -1617,6 +1617,8 @@ __lim_process_sme_join_req(struct mac_context *mac_ctx, void *msg_buf)
mlme_obj->reg_tpc_obj.is_power_constraint_abs =
!is_pwr_constraint;
session->best_6g_power_type = sme_join_req->best_6g_power_type;
if (wlan_reg_is_ext_tpc_supported(mac_ctx->psoc)) {
mlme_obj->reg_tpc_obj.ap_constraint_power =
local_power_constraint;
@ -2019,9 +2021,7 @@ uint8_t lim_get_max_tx_power(struct mac_context *mac,
}
void lim_calculate_tpc(struct mac_context *mac,
struct pe_session *session,
uint8_t ap_pwr_type,
bool ctry_code_match)
struct pe_session *session)
{
bool is_psd_power = false;
bool is_tpe_present = false, is_6ghz_freq = false;
@ -2061,18 +2061,8 @@ void lim_calculate_tpc(struct mac_context *mac,
} else {
is_6ghz_freq = true;
is_psd_power = wlan_reg_is_6g_psd_power(mac->pdev);
/* Power mode calculation for 6G*/
ap_power_type_6g = session->ap_power_type;
if (LIM_IS_STA_ROLE(session)) {
if (!session->lim_join_req) {
if (!ctry_code_match)
ap_power_type_6g = ap_pwr_type;
} else {
if (!session->lim_join_req->same_ctry_code)
ap_power_type_6g =
session->lim_join_req->ap_power_type_6g;
}
}
if (LIM_IS_STA_ROLE(session))
ap_power_type_6g = session->best_6g_power_type;
}
if (mlme_obj->reg_tpc_obj.num_pwr_levels) {

View file

@ -1,6 +1,6 @@
/*
* Copyright (c) 2011-2020 The Linux Foundation. All rights reserved.
* Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2022,2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -121,6 +121,7 @@ static void lim_extract_he_op(struct pe_session *session,
return;
if (!session->he_op.oper_info_6g_present) {
pe_debug("6GHz op not present in 6G beacon");
session->ap_defined_power_type_6g = REG_VERY_LOW_POWER_AP;
return;
}
session->ch_width = session->he_op.oper_info_6g.info.ch_width;
@ -128,11 +129,17 @@ static void lim_extract_he_op(struct pe_session *session,
session->he_op.oper_info_6g.info.center_freq_seg0;
session->ch_center_freq_seg1 =
session->he_op.oper_info_6g.info.center_freq_seg1;
session->ap_power_type =
session->ap_defined_power_type_6g =
session->he_op.oper_info_6g.info.reg_info;
if (session->ap_defined_power_type_6g < REG_INDOOR_AP ||
session->ap_defined_power_type_6g > REG_MAX_SUPP_AP_TYPE) {
session->ap_defined_power_type_6g = REG_VERY_LOW_POWER_AP;
pe_debug("AP power type invalid, defaulting to VLP");
}
pe_debug("6G op info: ch_wd %d cntr_freq_seg0 %d cntr_freq_seg1 %d ap pwr type %d",
session->ch_width, session->ch_center_freq_seg0,
session->ch_center_freq_seg1, session->ap_power_type);
session->ch_center_freq_seg1, session->ap_defined_power_type_6g);
if (!session->ch_center_freq_seg1)
return;
@ -706,9 +713,6 @@ void lim_extract_ap_capability(struct mac_context *mac_ctx, uint8_t *p_ie,
}
}
mac_ctx->roam.roamSession[session_id].ap_power_type =
session->ap_power_type;
get_ese_version_ie_probe_response(mac_ctx, beacon_struct, session);
session->country_info_present = false;

View file

@ -1,6 +1,6 @@
/*
* Copyright (c) 2012-2020 The Linux Foundation. All rights reserved.
* Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2022-2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -188,8 +188,6 @@ uint8_t lim_get_max_tx_power(struct mac_context *mac,
* lim_calculate_tpc() - Utility to get maximum tx power
* @mac: mac handle
* @session: PE Session Entry
* @ap_pwr_type: Ap power type for 6G
* @ctry_code_match: check for country IE and sta programmed ctry match
*
* This function is used to get the maximum possible tx power from the list
* of tx powers mentioned in @attr.
@ -197,9 +195,7 @@ uint8_t lim_get_max_tx_power(struct mac_context *mac,
* Return: None
*/
void lim_calculate_tpc(struct mac_context *mac,
struct pe_session *session,
uint8_t ap_pwr_type,
bool ctry_code_match);
struct pe_session *session);
/* AID pool management functions */
void lim_init_peer_idxpool(struct mac_context *, struct pe_session *);

View file

@ -1,6 +1,6 @@
/*
* Copyright (c) 2012-2020 The Linux Foundation. All rights reserved.
* Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2023-2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -273,7 +273,7 @@ rrm_process_link_measurement_request(struct mac_context *mac,
pLinkReq->MaxTxPower.maxTxPower;
/* Set is_power_constraint_abs to true to calculate tpc power */
mlme_obj->reg_tpc_obj.is_power_constraint_abs = true;
lim_calculate_tpc(mac, pe_session, 0, false);
lim_calculate_tpc(mac, pe_session);
LinkReport.txPower =
mlme_obj->reg_tpc_obj.chan_power_info[0].tx_power;

View file

@ -1,6 +1,6 @@
/*
* Copyright (c) 2012-2021 The Linux Foundation. All rights reserved.
* Copyright (c) 2021-2023 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2021-2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -609,9 +609,7 @@ static void __sch_beacon_process_for_session(struct mac_context *mac_ctx,
int8_t regMax = 0, maxTxPower = 0;
QDF_STATUS status;
bool skip_tpe = false;
uint8_t programmed_country[REG_ALPHA2_LEN + 1];
enum reg_6g_ap_type pwr_type_6g = REG_INDOOR_AP;
bool ctry_code_match = false;
enum reg_6g_ap_type pwr_type_6g;
bool is_power_constraint_abs = false;
qdf_mem_zero(&beaconParams, sizeof(tUpdateBeaconParams));
@ -651,15 +649,28 @@ static void __sch_beacon_process_for_session(struct mac_context *mac_ctx,
pe_err("Channel is 6G but country IE not present");
return;
}
wlan_reg_read_current_country(mac_ctx->psoc,
programmed_country);
status = wlan_reg_get_6g_power_type_for_ctry(mac_ctx->psoc,
mac_ctx->pdev,
bcn->countryInfoParam.countryString,
programmed_country, &pwr_type_6g,
&ctry_code_match, REG_MAX_AP_TYPE);
if (bcn->he_op.oper_info_6g_present) {
session->ap_defined_power_type_6g =
bcn->he_op.oper_info_6g.info.reg_info;
if (session->ap_defined_power_type_6g < REG_INDOOR_AP ||
session->ap_defined_power_type_6g >
REG_MAX_SUPP_AP_TYPE) {
session->ap_defined_power_type_6g =
REG_VERY_LOW_POWER_AP;
pe_debug("AP power type is invalid, defaulting to VLP");
}
} else {
pe_debug("AP power type is null, defaulting to VLP");
session->ap_defined_power_type_6g =
REG_VERY_LOW_POWER_AP;
}
status = wlan_reg_get_best_6g_power_type(
mac_ctx->psoc, mac_ctx->pdev, &pwr_type_6g,
session->ap_defined_power_type_6g);
if (QDF_IS_STATUS_ERROR(status))
return;
session->best_6g_power_type = pwr_type_6g;
}
if (wlan_reg_is_ext_tpc_supported(mac_ctx->psoc)) {
@ -693,8 +704,7 @@ static void __sch_beacon_process_for_session(struct mac_context *mac_ctx,
if ((ap_constraint_change && local_constraint) ||
(tpe_change && !skip_tpe)) {
lim_calculate_tpc(mac_ctx, session, pwr_type_6g,
ctry_code_match);
lim_calculate_tpc(mac_ctx, session);
if (tx_ops->set_tpc_power)
tx_ops->set_tpc_power(mac_ctx->psoc,

View file

@ -619,8 +619,6 @@ struct csr_roam_session {
qdf_mc_timer_t roam_invoke_timer;
struct csr_timer_info roam_invoke_timer_info;
#endif
/* AP power type */
uint8_t ap_power_type;
};
struct csr_roamstruct {

View file

@ -1,6 +1,6 @@
/*
* Copyright (c) 2012-2020 The Linux Foundation. All rights reserved.
* Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved.
* Copyright (c) 2022-2024 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for
* any purpose with or without fee is hereby granted, provided that the
@ -15028,9 +15028,7 @@ QDF_STATUS csr_send_join_req_msg(struct mac_context *mac, uint32_t sessionId,
struct wlan_objmgr_vdev *vdev;
bool follow_ap_edca;
bool reconn_after_assoc_timeout = false;
uint8_t programmed_country[REG_ALPHA2_LEN + 1];
enum reg_6g_ap_type power_type_6g;
bool ctry_code_match;
uint8_t reg_cc[REG_ALPHA2_LEN + 1];
if (!pSession) {
@ -15839,18 +15837,12 @@ QDF_STATUS csr_send_join_req_msg(struct mac_context *mac, uint32_t sessionId,
if (wlan_reg_is_6ghz_chan_freq(pBssDescription->chan_freq)) {
if (!pIes->Country.present)
sme_debug("Channel is 6G but country IE not present");
wlan_reg_read_current_country(mac->psoc,
programmed_country);
status = wlan_reg_get_6g_power_type_for_ctry(mac->psoc,
mac->pdev,
pIes->Country.country,
programmed_country, &power_type_6g,
&ctry_code_match,
status = wlan_reg_get_best_6g_power_type(mac->psoc,
mac->pdev, &power_type_6g,
ap_6g_power_type);
if (QDF_IS_STATUS_ERROR(status))
break;
csr_join_req->ap_power_type_6g = power_type_6g;
csr_join_req->same_ctry_code = ctry_code_match;
csr_join_req->best_6g_power_type = power_type_6g;
status = csr_iterate_triplets(pIes->Country);
}