diff --git a/core/mac/inc/ani_global.h b/core/mac/inc/ani_global.h index 0ca4fd28ed12..4b241c473f78 100644 --- a/core/mac/inc/ani_global.h +++ b/core/mac/inc/ani_global.h @@ -679,7 +679,8 @@ struct mgmt_frm_reg_info { }; typedef struct sRrmContext { - tRrmSMEContext rrmSmeContext; + struct rrm_config_param rrmConfig; + tRrmSMEContext rrmSmeContext[MAX_MEASUREMENT_REQUEST]; tRrmPEContext rrmPEContext; } tRrmContext, *tpRrmContext; diff --git a/core/mac/src/pe/include/rrm_global.h b/core/mac/src/pe/include/rrm_global.h index 08614db37b24..3e23935db44b 100644 --- a/core/mac/src/pe/include/rrm_global.h +++ b/core/mac/src/pe/include/rrm_global.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011-2012, 2014-2019 The Linux Foundation. All rights reserved. + * Copyright (c) 2011-2012, 2014-2020 The Linux Foundation. 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 @@ -27,6 +27,9 @@ ========================================================================*/ +#define MAX_MEASUREMENT_REQUEST 2 +#define DEFAULT_RRM_IDX 0 + typedef enum eRrmRetStatus { eRRM_SUCCESS, eRRM_INCAPABLE, @@ -49,6 +52,7 @@ struct sir_channel_info { typedef struct sSirBeaconReportReqInd { uint16_t messageType; /* eWNI_SME_BEACON_REPORT_REQ_IND */ uint16_t length; + uint8_t measurement_idx; tSirMacAddr bssId; uint16_t measurementDuration[SIR_ESE_MAX_MEAS_IE_REQS]; /* ms */ uint16_t randomizationInterval; /* ms */ @@ -66,6 +70,7 @@ typedef struct sSirBeaconReportReqInd { typedef struct sSirBeaconReportXmitInd { uint16_t messageType; /* eWNI_SME_BEACON_REPORT_RESP_XMIT_IND */ uint16_t length; + uint8_t measurement_idx; tSirMacAddr bssId; uint16_t uDialogToken; uint8_t fMeasureDone; @@ -131,6 +136,7 @@ typedef struct sSirNeighborReportInd { uint16_t messageType; /* eWNI_SME_NEIGHBOR_REPORT_IND */ uint16_t length; uint8_t sessionId; + uint8_t measurement_idx; uint16_t numNeighborReports; tSirMacAddr bssId; /* For the session. */ tSirNeighborBssDescription sNeighborBssDescription[1]; @@ -148,6 +154,7 @@ typedef struct sRRMBeaconReportRequestedIes { #define BEACON_REPORTING_DETAIL_ALL_FF_IE 2 typedef struct sRRMReq { + uint8_t measurement_idx; /* Index of the measurement report in frame */ uint8_t dialog_token; /* In action frame; */ uint8_t token; /* Within individual request; */ uint8_t type; @@ -211,7 +218,7 @@ typedef struct sRrmPEContext { /* Dialog token for the request initiated from station. */ uint8_t DialogToken; uint16_t prev_rrm_report_seq_num; - tpRRMReq pCurrentReq; + tpRRMReq pCurrentReq[MAX_MEASUREMENT_REQUEST]; } tRrmPEContext, *tpRrmPEContext; /* 2008 11k spec reference: 18.4.8.5 RCPI Measurement */ diff --git a/core/mac/src/pe/lim/lim_process_action_frame.c b/core/mac/src/pe/lim/lim_process_action_frame.c index 24a0e3f81bbb..2488ce1ea221 100644 --- a/core/mac/src/pe/lim/lim_process_action_frame.c +++ b/core/mac/src/pe/lim/lim_process_action_frame.c @@ -1287,7 +1287,8 @@ __lim_process_radio_measure_request(struct mac_context *mac, uint8_t *pRxPacketI HIGH_SEQ_NUM_OFFSET) | pHdr->seqControl.seqNumLo); if (curr_seq_num == mac->rrm.rrmPEContext.prev_rrm_report_seq_num && - mac->rrm.rrmPEContext.pCurrentReq) { + (mac->rrm.rrmPEContext.pCurrentReq[DEFAULT_RRM_IDX] || + mac->rrm.rrmPEContext.pCurrentReq[DEFAULT_RRM_IDX + 1])) { pe_err("rrm report req frame, seq num: %d is already in progress, drop it", curr_seq_num); return; diff --git a/core/mac/src/pe/lim/lim_utils.c b/core/mac/src/pe/lim/lim_utils.c index e17fa554e0e8..b03135e47749 100644 --- a/core/mac/src/pe/lim/lim_utils.c +++ b/core/mac/src/pe/lim/lim_utils.c @@ -8399,7 +8399,7 @@ QDF_STATUS lim_get_capability_info(struct mac_context *mac, uint16_t *pcap, if (mac->mlme_cfg->scoring.apsd_enabled) pcap_info->apsd = 1; - pcap_info->rrm = mac->rrm.rrmSmeContext.rrmConfig.rrm_enabled; + pcap_info->rrm = mac->rrm.rrmConfig.rrm_enabled; pe_debug("RRM: %d", pcap_info->rrm); /* DSSS-OFDM */ /* FIXME : no config defined yet. */ diff --git a/core/mac/src/pe/rrm/rrm_api.c b/core/mac/src/pe/rrm/rrm_api.c index 9735aaa13bcd..f774222ab7f5 100644 --- a/core/mac/src/pe/rrm/rrm_api.c +++ b/core/mac/src/pe/rrm/rrm_api.c @@ -390,6 +390,7 @@ rrm_process_neighbor_report_response(struct mac_context *mac, pSmeNeighborRpt->messageType = eWNI_SME_NEIGHBOR_REPORT_IND; pSmeNeighborRpt->length = length; + pSmeNeighborRpt->measurement_idx = DEFAULT_RRM_IDX; pSmeNeighborRpt->sessionId = pe_session->smeSessionId; pSmeNeighborRpt->numNeighborReports = pNeighborRep->num_NeighborReport; qdf_mem_copy(pSmeNeighborRpt->bssId, pe_session->bssId, @@ -657,6 +658,7 @@ rrm_process_beacon_report_req(struct mac_context *mac, psbrr->msgSource = eRRM_MSG_SOURCE_11K; psbrr->randomizationInterval = SYS_TU_TO_MS(pBeaconReq->measurement_request.Beacon.randomization); + psbrr->measurement_idx = pCurrentReq->measurement_idx; if (!wlan_reg_is_6ghz_supported(mac->pdev) && (wlan_reg_is_6ghz_op_class(mac->pdev, @@ -690,11 +692,12 @@ rrm_process_beacon_report_req(struct mac_context *mac, } else { psbrr->channel_info.chan_freq = 0; } - sme_debug("opclass %d, ch %d freq %d AP's country code %c%c 0x%x", + sme_debug("opclass %d, ch %d freq %d AP's country code %c%c 0x%x index:%d", psbrr->channel_info.reg_class, psbrr->channel_info.chan_num, psbrr->channel_info.chan_freq, - country[0], country[1], country[2]); + country[0], country[1], country[2], + psbrr->measurement_idx); psbrr->measurementDuration[0] = measDuration; psbrr->fMeasurementtype[0] = @@ -895,7 +898,9 @@ rrm_process_beacon_report_xmit(struct mac_context *mac_ctx, tSirMacRadioMeasureReport *report = NULL; tSirMacBeaconReport *beacon_report; struct bss_description *bss_desc; - tpRRMReq curr_req = mac_ctx->rrm.rrmPEContext.pCurrentReq; + tpRRMReq curr_req = + mac_ctx->rrm.rrmPEContext. + pCurrentReq[beacon_xmit_ind->measurement_idx]; struct pe_session *session_entry; uint8_t session_id, counter; uint8_t i, j, offset = 0; @@ -905,7 +910,6 @@ rrm_process_beacon_report_xmit(struct mac_context *mac_ctx, uint8_t frag_id = 0; uint8_t num_frames, num_reports_in_frame; - pe_debug("Received beacon report xmit indication"); if (!beacon_xmit_ind) { pe_err("Received beacon_xmit_ind is NULL in PE"); @@ -918,6 +922,9 @@ rrm_process_beacon_report_xmit(struct mac_context *mac_ctx, goto end; } + pe_debug("Received beacon report xmit indication on idx:%d", + beacon_xmit_ind->measurement_idx); + if ((beacon_xmit_ind->numBssDesc) || curr_req->sendEmptyBcnRpt) { beacon_xmit_ind->numBssDesc = (beacon_xmit_ind->numBssDesc == RRM_BCN_RPT_NO_BSS_INFO) ? RRM_BCN_RPT_MIN_RPT : @@ -1090,13 +1097,19 @@ end: return status; } -static void rrm_process_beacon_request_failure(struct mac_context *mac, - struct pe_session *pe_session, - tSirMacAddr peer, - tRrmRetStatus status) +static void +rrm_process_beacon_request_failure(struct mac_context *mac, + struct pe_session *pe_session, + tSirMacAddr peer, + tRrmRetStatus status, uint8_t index) { tpSirMacRadioMeasureReport pReport = NULL; - tpRRMReq pCurrentReq = mac->rrm.rrmPEContext.pCurrentReq; + tpRRMReq pCurrentReq = mac->rrm.rrmPEContext.pCurrentReq[index]; + + if (!pCurrentReq) { + pe_err("Current request is NULL"); + return; + } pReport = qdf_mem_malloc(sizeof(tSirMacRadioMeasureReport)); if (!pReport) @@ -1134,7 +1147,6 @@ static void rrm_process_beacon_request_failure(struct mac_context *mac, * @mac_ctx: Global pointer to MAC context * @peer: Macaddress of the peer requesting the radio measurement * @session_entry: session entry - * @curr_req: Pointer to RRM request * @radiomes_report: Pointer to radio measurement report * @rrm_req: Array of Measurement request IEs * @num_report: No.of reports @@ -1147,15 +1159,16 @@ static void rrm_process_beacon_request_failure(struct mac_context *mac, */ static QDF_STATUS rrm_process_beacon_req(struct mac_context *mac_ctx, tSirMacAddr peer, - struct pe_session *session_entry, tpRRMReq curr_req, + struct pe_session *session_entry, tpSirMacRadioMeasureReport *radiomes_report, tDot11fRadioMeasurementRequest *rrm_req, uint8_t *num_report, int index) { tRrmRetStatus rrm_status = eRRM_SUCCESS; tpSirMacRadioMeasureReport report; + tpRRMReq curr_req; - if (curr_req) { + if (index >= MAX_MEASUREMENT_REQUEST) { if (!*radiomes_report) { /* * Allocate memory to send reports for @@ -1176,22 +1189,30 @@ QDF_STATUS rrm_process_beacon_req(struct mac_context *mac_ctx, tSirMacAddr peer, (*num_report)++; return QDF_STATUS_SUCCESS; } else { + curr_req = mac_ctx->rrm.rrmPEContext.pCurrentReq[index]; + if (curr_req) { + qdf_mem_free(curr_req); + curr_req = NULL; + } + curr_req = qdf_mem_malloc(sizeof(*curr_req)); if (!curr_req) { - qdf_mem_free(*radiomes_report); + qdf_mem_free(*radiomes_report); + mac_ctx->rrm.rrmPEContext.pCurrentReq[index] = NULL; return QDF_STATUS_E_NOMEM; } - pe_debug("Processing Beacon Report request"); + pe_debug("Processing Beacon Report request %d", index); curr_req->dialog_token = rrm_req->DialogToken.token; curr_req->token = rrm_req-> MeasurementRequest[index].measurement_token; curr_req->sendEmptyBcnRpt = true; - mac_ctx->rrm.rrmPEContext.pCurrentReq = curr_req; + curr_req->measurement_idx = index; + mac_ctx->rrm.rrmPEContext.pCurrentReq[index] = curr_req; rrm_status = rrm_process_beacon_report_req(mac_ctx, curr_req, &rrm_req->MeasurementRequest[index], session_entry); if (eRRM_SUCCESS != rrm_status) { rrm_process_beacon_request_failure(mac_ctx, - session_entry, peer, rrm_status); + session_entry, peer, rrm_status, index); rrm_cleanup(mac_ctx); } } @@ -1262,7 +1283,6 @@ rrm_process_radio_measurement_request(struct mac_context *mac_ctx, QDF_STATUS status = QDF_STATUS_SUCCESS; tpSirMacRadioMeasureReport report = NULL; uint8_t num_report = 0; - tpRRMReq curr_req = mac_ctx->rrm.rrmPEContext.pCurrentReq; if (!rrm_req->num_MeasurementRequest) { report = qdf_mem_malloc(sizeof(tSirMacRadioMeasureReport)); @@ -1299,9 +1319,10 @@ rrm_process_radio_measurement_request(struct mac_context *mac_ctx, case SIR_MAC_RRM_BEACON_TYPE: /* Process beacon request. */ status = rrm_process_beacon_req(mac_ctx, peer, - session_entry, curr_req, &report, rrm_req, - &num_report, i); - if (QDF_STATUS_SUCCESS != status) + session_entry, &report, + rrm_req, &num_report, + i); + if (QDF_IS_STATUS_ERROR(status)) return status; break; case SIR_MAC_RRM_LCI_TYPE: @@ -1392,7 +1413,8 @@ QDF_STATUS rrm_initialize(struct mac_context *mac) { tpRRMCaps pRRMCaps = &mac->rrm.rrmPEContext.rrmEnabledCaps; - mac->rrm.rrmPEContext.pCurrentReq = NULL; + mac->rrm.rrmPEContext.pCurrentReq[0] = NULL; + mac->rrm.rrmPEContext.pCurrentReq[1] = NULL; mac->rrm.rrmPEContext.txMgmtPower = 0; mac->rrm.rrmPEContext.DialogToken = 0; @@ -1435,17 +1457,21 @@ QDF_STATUS rrm_initialize(struct mac_context *mac) QDF_STATUS rrm_cleanup(struct mac_context *mac) { - if (mac->rrm.rrmPEContext.pCurrentReq) { - if (mac->rrm.rrmPEContext.pCurrentReq->request.Beacon.reqIes. - pElementIds) { - qdf_mem_free(mac->rrm.rrmPEContext.pCurrentReq-> - request.Beacon.reqIes.pElementIds); - } + uint8_t i; - qdf_mem_free(mac->rrm.rrmPEContext.pCurrentReq); + for (i = 0; i < MAX_MEASUREMENT_REQUEST; i++) { + if (mac->rrm.rrmPEContext.pCurrentReq[i]) { + if (mac->rrm.rrmPEContext.pCurrentReq[i]->request. + Beacon.reqIes.pElementIds) + qdf_mem_free(mac->rrm.rrmPEContext. + pCurrentReq[i]->request.Beacon. + reqIes.pElementIds); + + qdf_mem_free(mac->rrm.rrmPEContext.pCurrentReq[i]); + } + mac->rrm.rrmPEContext.pCurrentReq[i] = NULL; } - mac->rrm.rrmPEContext.pCurrentReq = NULL; return QDF_STATUS_SUCCESS; } diff --git a/core/mac/src/pe/sch/sch_beacon_gen.c b/core/mac/src/pe/sch/sch_beacon_gen.c index b6d66d7e5e66..9ed2a68dc5fa 100644 --- a/core/mac/src/pe/sch/sch_beacon_gen.c +++ b/core/mac/src/pe/sch/sch_beacon_gen.c @@ -437,7 +437,7 @@ sch_set_fixed_beacon_fields(struct mac_context *mac_ctx, struct pe_session *sess } } } - if (mac_ctx->rrm.rrmSmeContext.rrmConfig.rrm_enabled) + if (mac_ctx->rrm.rrmConfig.rrm_enabled) populate_dot11f_rrm_ie(mac_ctx, &bcn_2->RRMEnabledCap, session); diff --git a/core/sme/inc/sme_rrm_internal.h b/core/sme/inc/sme_rrm_internal.h index c590b4d7e4d7..8545ec908866 100644 --- a/core/sme/inc/sme_rrm_internal.h +++ b/core/sme/inc/sme_rrm_internal.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011-2012, 2014-2018 The Linux Foundation. All rights reserved. + * Copyright (c) 2011-2012, 2014-2018, 2020 The Linux Foundation. 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 @@ -64,6 +64,7 @@ typedef struct sRrmSMEContext { uint16_t token; struct qdf_mac_addr sessionBssId; uint8_t regClass; + uint8_t measurement_idx; /* list of all channels to be measured. */ tCsrChannelInfo channelList; uint8_t currentIndex; @@ -74,7 +75,7 @@ typedef struct sRrmSMEContext { uint16_t randnIntvl; uint16_t duration[SIR_ESE_MAX_MEAS_IE_REQS]; uint8_t measMode[SIR_ESE_MAX_MEAS_IE_REQS]; - struct rrm_config_param rrmConfig; + uint32_t scan_id; qdf_mc_timer_t IterMeasTimer; tDblLinkList neighborReportCache; tRrmNeighborRequestControlInfo neighborReqControlInfo; diff --git a/core/sme/src/common/sme_api.c b/core/sme/src/common/sme_api.c index d3900a983655..7adab7b6a0b5 100644 --- a/core/sme/src/common/sme_api.c +++ b/core/sme/src/common/sme_api.c @@ -826,12 +826,12 @@ void sme_update_fine_time_measurement_capab(mac_handle_t mac_handle, if (!val) { mac_ctx->rrm.rrmPEContext.rrmEnabledCaps.fine_time_meas_rpt = 0; - ((tpRRMCaps)mac_ctx->rrm.rrmSmeContext. - rrmConfig.rm_capability)->fine_time_meas_rpt = 0; + ((tpRRMCaps)mac_ctx->rrm.rrmConfig. + rm_capability)->fine_time_meas_rpt = 0; } else { mac_ctx->rrm.rrmPEContext.rrmEnabledCaps.fine_time_meas_rpt = 1; - ((tpRRMCaps)mac_ctx->rrm.rrmSmeContext. - rrmConfig.rm_capability)->fine_time_meas_rpt = 1; + ((tpRRMCaps)mac_ctx->rrm.rrmConfig. + rm_capability)->fine_time_meas_rpt = 1; } /* Inform this RRM IE change to FW */ @@ -1643,7 +1643,7 @@ QDF_STATUS sme_set_ese_beacon_request(mac_handle_t mac_handle, const tCsrEseBeaconReqParams *bcn_req = NULL; uint8_t counter = 0; struct csr_roam_session *session = CSR_GET_SESSION(mac, sessionId); - tpRrmSMEContext sme_rrm_ctx = &mac->rrm.rrmSmeContext; + tpRrmSMEContext sme_rrm_ctx = &mac->rrm.rrmSmeContext[0]; if (sme_rrm_ctx->eseBcnReqInProgress == true) { sme_err("A Beacon Report Req is already in progress"); @@ -1671,6 +1671,7 @@ QDF_STATUS sme_set_ese_beacon_request(mac_handle_t mac_handle, sme_bcn_rpt_req->channel_info.chan_num = 255; sme_bcn_rpt_req->channel_list.num_channels = in_req->numBcnReqIe; sme_bcn_rpt_req->msgSource = eRRM_MSG_SOURCE_ESE_UPLOAD; + sme_bcn_rpt_req->measurement_idx = 0; for (counter = 0; counter < in_req->numBcnReqIe; counter++) { bcn_req = &in_req->bcnReq[counter]; @@ -3402,7 +3403,7 @@ QDF_STATUS sme_oem_update_capability(mac_handle_t mac_handle, struct mac_context *pmac = MAC_CONTEXT(mac_handle); uint8_t *bytes; - bytes = pmac->rrm.rrmSmeContext.rrmConfig.rm_capability; + bytes = pmac->rrm.rrmConfig.rm_capability; if (cap->ftm_rr) bytes[4] |= RM_CAP_FTM_RANGE_REPORT; @@ -3430,7 +3431,7 @@ QDF_STATUS sme_oem_get_capability(mac_handle_t mac_handle, struct mac_context *pmac = MAC_CONTEXT(mac_handle); uint8_t *bytes; - bytes = pmac->rrm.rrmSmeContext.rrmConfig.rm_capability; + bytes = pmac->rrm.rrmConfig.rm_capability; cap->ftm_rr = bytes[4] & RM_CAP_FTM_RANGE_REPORT; cap->lci_capability = bytes[4] & RM_CAP_CIVIC_LOC_MEASUREMENT; diff --git a/core/sme/src/csr/csr_api_roam.c b/core/sme/src/csr/csr_api_roam.c index 2b27ed91fd7e..f5781a44721e 100644 --- a/core/sme/src/csr/csr_api_roam.c +++ b/core/sme/src/csr/csr_api_roam.c @@ -16189,7 +16189,7 @@ QDF_STATUS csr_send_join_req_msg(struct mac_context *mac, uint32_t sessionId, /* Fill rrm config parameters */ qdf_mem_copy(&csr_join_req->rrm_config, - &mac->rrm.rrmSmeContext.rrmConfig, + &mac->rrm.rrmConfig, sizeof(struct rrm_config_param)); pAP_capabilityInfo = diff --git a/core/sme/src/rrm/sme_rrm.c b/core/sme/src/rrm/sme_rrm.c index 8deef74a0930..de12cdfd534c 100644 --- a/core/sme/src/rrm/sme_rrm.c +++ b/core/sme/src/rrm/sme_rrm.c @@ -112,46 +112,45 @@ static void rrm_indicate_neighbor_report_result(struct mac_context *mac, void *callbackContext; /* Reset the neighbor response pending status */ - mac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending = - false; + mac->rrm.rrmSmeContext[DEFAULT_RRM_IDX]. + neighborReqControlInfo.isNeighborRspPending = false; /* Stop the timer if it is already running. * The timer should be running only in the SUCCESS case. */ if (QDF_TIMER_STATE_RUNNING == - qdf_mc_timer_get_current_state(&mac->rrm.rrmSmeContext. + qdf_mc_timer_get_current_state(&mac->rrm.rrmSmeContext[DEFAULT_RRM_IDX]. neighborReqControlInfo. neighborRspWaitTimer)) { sme_debug("No entry in neighbor report cache"); - qdf_mc_timer_stop(&mac->rrm.rrmSmeContext. + qdf_mc_timer_stop(&mac->rrm.rrmSmeContext[DEFAULT_RRM_IDX]. neighborReqControlInfo.neighborRspWaitTimer); } callback = - mac->rrm.rrmSmeContext.neighborReqControlInfo. + mac->rrm.rrmSmeContext[DEFAULT_RRM_IDX].neighborReqControlInfo. neighborRspCallbackInfo.neighborRspCallback; callbackContext = - mac->rrm.rrmSmeContext.neighborReqControlInfo. + mac->rrm.rrmSmeContext[DEFAULT_RRM_IDX].neighborReqControlInfo. neighborRspCallbackInfo.neighborRspCallbackContext; /* Reset the callback and the callback context before calling the * callback. It is very likely that there may be a registration in * callback itself. */ - mac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo. - neighborRspCallback = NULL; - mac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo. - neighborRspCallbackContext = NULL; + mac->rrm.rrmSmeContext[DEFAULT_RRM_IDX].neighborReqControlInfo. + neighborRspCallbackInfo.neighborRspCallback = NULL; + mac->rrm.rrmSmeContext[DEFAULT_RRM_IDX].neighborReqControlInfo. + neighborRspCallbackInfo.neighborRspCallbackContext = NULL; /* Call the callback with the status received from caller */ if (callback) callback(callbackContext, qdf_status); - - } /** * sme_RrmBeaconReportXmitInd () - Send beacon report * @mac_ctx Pointer to mac context + * @measurement_index: Measurement index * @result_arr scan results * @msrmnt_status flag to indicate that the measurement is done. * @bss_count bss count @@ -163,8 +162,8 @@ static void rrm_indicate_neighbor_report_result(struct mac_context *mac, static QDF_STATUS sme_rrm_send_beacon_report_xmit_ind(struct mac_context *mac_ctx, - tCsrScanResultInfo **result_arr, uint8_t msrmnt_status, - uint8_t bss_count) + uint8_t measurement_index, tCsrScanResultInfo **result_arr, + uint8_t msrmnt_status, uint8_t bss_count) { struct bss_description *bss_desc = NULL; tpSirBeaconReportXmitInd beacon_rep; @@ -173,7 +172,8 @@ sme_rrm_send_beacon_report_xmit_ind(struct mac_context *mac_ctx, uint8_t i = 0, j = 0, counter = 0; tCsrScanResultInfo *cur_result = NULL; QDF_STATUS status = QDF_STATUS_E_FAILURE; - tpRrmSMEContext rrm_ctx = &mac_ctx->rrm.rrmSmeContext; + tpRrmSMEContext rrm_ctx = + &mac_ctx->rrm.rrmSmeContext[measurement_index]; struct bss_description *tmp_bss_desc[SIR_BCN_REPORT_MAX_BSS_DESC] = {0}; if (!result_arr && !msrmnt_status) { @@ -192,6 +192,7 @@ sme_rrm_send_beacon_report_xmit_ind(struct mac_context *mac_ctx, beacon_rep->messageType = eWNI_SME_BEACON_REPORT_RESP_XMIT_IND; beacon_rep->length = length; + beacon_rep->measurement_idx = measurement_index; beacon_rep->uDialogToken = rrm_ctx->token; beacon_rep->duration = rrm_ctx->duration[0]; beacon_rep->regClass = rrm_ctx->regClass; @@ -253,6 +254,7 @@ sme_rrm_send_beacon_report_xmit_ind(struct mac_context *mac_ctx, /** * sme_ese_send_beacon_req_scan_results () - Send beacon report * @mac_ctx: Pointer to mac context + * @measurement_index: Measurement request index * @session_id: session id * @freq: channel frequency * @result_arr: scan results @@ -268,8 +270,9 @@ sme_rrm_send_beacon_report_xmit_ind(struct mac_context *mac_ctx, * Return: status */ static QDF_STATUS sme_ese_send_beacon_req_scan_results( - struct mac_context *mac_ctx, uint32_t session_id, - uint32_t freq, tCsrScanResultInfo **result_arr, + struct mac_context *mac_ctx, uint8_t measurement_index, + uint32_t session_id, uint32_t freq, + tCsrScanResultInfo **result_arr, uint8_t msrmnt_status, uint8_t bss_count) { QDF_STATUS status = QDF_STATUS_E_FAILURE; @@ -279,7 +282,8 @@ static QDF_STATUS sme_ese_send_beacon_req_scan_results( uint32_t out_ie_len = 0; uint8_t bss_counter = 0; tCsrScanResultInfo *cur_result = NULL; - tpRrmSMEContext rrm_ctx = &mac_ctx->rrm.rrmSmeContext; + tpRrmSMEContext rrm_ctx = + &mac_ctx->rrm.rrmSmeContext[measurement_index]; struct csr_roam_info *roam_info; struct ese_bcn_report_rsp bcn_rpt_rsp; struct ese_bcn_report_rsp *bcn_report = &bcn_rpt_rsp; @@ -419,6 +423,7 @@ void sme_reset_ese_bcn_req_in_progress(tpRrmSMEContext sme_rrm_ctx) /** * sme_rrm_send_scan_result() - to get scan result and send the beacon report * @mac_ctx: pointer to mac context + * @measurement_index: Measurement request number * @num_chan: number of channels * @freq_list: list of channel frequencies to fetch the result from * @measurementdone: Flag to indicate measurement done or no @@ -429,6 +434,7 @@ void sme_reset_ese_bcn_req_in_progress(tpRrmSMEContext sme_rrm_ctx) * Return: QDF_STATUS */ static QDF_STATUS sme_rrm_send_scan_result(struct mac_context *mac_ctx, + uint8_t measurement_index, uint8_t num_chan, uint32_t *freq_list, uint8_t measurementdone) @@ -441,7 +447,8 @@ static QDF_STATUS sme_rrm_send_scan_result(struct mac_context *mac_ctx, struct scan_result_list *result_list; QDF_STATUS status; uint8_t num_scan_results, counter = 0; - tpRrmSMEContext rrm_ctx = &mac_ctx->rrm.rrmSmeContext; + tpRrmSMEContext rrm_ctx = + &mac_ctx->rrm.rrmSmeContext[measurement_index]; uint32_t session_id; struct csr_roam_info *roam_info = NULL; tSirScanType scan_type; @@ -511,12 +518,14 @@ static QDF_STATUS sme_rrm_send_scan_result(struct mac_context *mac_ctx, #ifdef FEATURE_WLAN_ESE if (eRRM_MSG_SOURCE_ESE_UPLOAD == rrm_ctx->msgSource) status = sme_ese_send_beacon_req_scan_results(mac_ctx, - session_id, freq_list[0], - NULL, measurementdone, 0); + measurement_index, session_id, + freq_list[0], NULL, + measurementdone, 0); else #endif /* FEATURE_WLAN_ESE */ status = sme_rrm_send_beacon_report_xmit_ind(mac_ctx, - NULL, measurementdone, 0); + measurement_index, NULL, + measurementdone, 0); return status; } scan_results = sme_scan_result_get_first(mac_handle, result_handle); @@ -524,14 +533,13 @@ static QDF_STATUS sme_rrm_send_scan_result(struct mac_context *mac_ctx, #ifdef FEATURE_WLAN_ESE if (eRRM_MSG_SOURCE_ESE_UPLOAD == rrm_ctx->msgSource) { status = sme_ese_send_beacon_req_scan_results(mac_ctx, - session_id, - freq_list[0], - NULL, - measurementdone, - 0); + measurement_index, session_id, + freq_list[0], NULL, + measurementdone, 0); } else #endif /* FEATURE_WLAN_ESE */ status = sme_rrm_send_beacon_report_xmit_ind(mac_ctx, + measurement_index, NULL, measurementdone, 0); } @@ -621,14 +629,14 @@ static QDF_STATUS sme_rrm_send_scan_result(struct mac_context *mac_ctx, #ifdef FEATURE_WLAN_ESE if (eRRM_MSG_SOURCE_ESE_UPLOAD == rrm_ctx->msgSource) status = sme_ese_send_beacon_req_scan_results(mac_ctx, - session_id, freq_list[0], - scanresults_arr, measurementdone, - counter); + measurement_index, session_id, + freq_list[0], scanresults_arr, + measurementdone, counter); else #endif /* FEATURE_WLAN_ESE */ status = sme_rrm_send_beacon_report_xmit_ind(mac_ctx, - scanresults_arr, measurementdone, - counter); + measurement_index, scanresults_arr, + measurementdone, counter); } rrm_send_scan_results_done: @@ -644,6 +652,7 @@ rrm_send_scan_results_done: /** * sme_rrm_scan_request_callback() -Sends the beacon report xmit to PE * @mac_handle: Opaque handle to the MAC context + * @pSmeRrmContext: SME rrm context for measurement request * @sessionId: session id * @scanId: Scan ID. * @status: CSR Status. @@ -654,14 +663,13 @@ rrm_send_scan_results_done: * * Return : 0 for success, non zero for failure */ -static QDF_STATUS sme_rrm_scan_request_callback(mac_handle_t mac_handle, +static QDF_STATUS sme_rrm_scan_request_callback(struct mac_context *mac, + tpRrmSMEContext pSmeRrmContext, uint8_t sessionId, uint32_t scanId, eCsrScanStatus status) { uint16_t interval; - struct mac_context *mac = MAC_CONTEXT(mac_handle); - tpRrmSMEContext pSmeRrmContext = &mac->rrm.rrmSmeContext; uint32_t time_tick; QDF_STATUS qdf_status; uint32_t session_id; @@ -685,10 +693,41 @@ static QDF_STATUS sme_rrm_scan_request_callback(mac_handle_t mac_handle, * within randomization interval. */ freq_list = pSmeRrmContext->channelList.freq_list; + if (!freq_list) { + sme_err("[802.11 RRM]: Global freq list is null"); + pSmeRrmContext->channelList.numOfChannels = 0; + sme_reset_ese_bcn_req_in_progress(pSmeRrmContext); + return QDF_STATUS_E_FAILURE; + } + ch_idx = pSmeRrmContext->currentIndex; num_chan = pSmeRrmContext->channelList.numOfChannels; if (((ch_idx + 1) < num_chan) && valid_result) { - sme_rrm_send_scan_result(mac, 1, &freq_list[ch_idx], false); + if (QDF_TIMER_STATE_RUNNING == + qdf_mc_timer_get_current_state( + &pSmeRrmContext->IterMeasTimer)) { + /* + * Measurement random timer is already running, this + * should not happen because the driver doesn't support + * multiple measurements simultaneously. Also for + * multiple measurements on a single report, the + * channels in op class should be appended to the global + * frequency list + */ + sme_err("[802.11 RRM]: meas timer is already running"); + sme_rrm_send_scan_result(mac, + pSmeRrmContext->measurement_idx, + 1, &freq_list[ch_idx], true); + qdf_mem_free(pSmeRrmContext->channelList.freq_list); + pSmeRrmContext->channelList.freq_list = NULL; + pSmeRrmContext->channelList.numOfChannels = 0; + sme_reset_ese_bcn_req_in_progress(pSmeRrmContext); + return QDF_STATUS_E_FAILURE; + } + + sme_rrm_send_scan_result(mac, pSmeRrmContext->measurement_idx, + 1, &freq_list[ch_idx], false); + /* Advance the current index. */ pSmeRrmContext->currentIndex++; /* start the timer to issue next request. */ @@ -705,6 +744,7 @@ static QDF_STATUS sme_rrm_scan_request_callback(mac_handle_t mac_handle, if (QDF_IS_STATUS_ERROR(qdf_status)) { qdf_mem_free(pSmeRrmContext->channelList.freq_list); pSmeRrmContext->channelList.freq_list = NULL; + pSmeRrmContext->channelList.numOfChannels = 0; sme_reset_ese_bcn_req_in_progress(pSmeRrmContext); } @@ -712,9 +752,11 @@ static QDF_STATUS sme_rrm_scan_request_callback(mac_handle_t mac_handle, /* Done with the measurement. Clean up all context and send a * message to PE with measurement done flag set. */ - sme_rrm_send_scan_result(mac, 1, &freq_list[ch_idx], true); + sme_rrm_send_scan_result(mac, pSmeRrmContext->measurement_idx, + 1, &freq_list[ch_idx], true); qdf_mem_free(pSmeRrmContext->channelList.freq_list); pSmeRrmContext->channelList.freq_list = NULL; + pSmeRrmContext->channelList.numOfChannels = 0; sme_reset_ese_bcn_req_in_progress(pSmeRrmContext); } @@ -724,20 +766,21 @@ static QDF_STATUS sme_rrm_scan_request_callback(mac_handle_t mac_handle, static void sme_rrm_scan_event_callback(struct wlan_objmgr_vdev *vdev, struct scan_event *event, void *arg) { + struct mac_context *mac_ctx; uint32_t scan_id; - uint8_t session_id; + uint8_t session_id, i; eCsrScanStatus scan_status = eCSR_SCAN_FAILURE; - mac_handle_t mac_handle; bool success = false; + tpRrmSMEContext smerrmctx; + + mac_ctx = (struct mac_context *)arg; + if (!mac_ctx) { + sme_err("invalid mac_ctx"); + return; + } session_id = wlan_vdev_get_id(vdev); scan_id = event->scan_id; - mac_handle = cds_get_context(QDF_MODULE_ID_SME); - if (!mac_handle) { - QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_FATAL, - FL("invalid h_hal")); - return; - } qdf_mtrace(QDF_MODULE_ID_SCAN, QDF_MODULE_ID_SME, event->type, event->vdev_id, event->scan_id); @@ -748,11 +791,21 @@ static void sme_rrm_scan_event_callback(struct wlan_objmgr_vdev *vdev, if (success) scan_status = eCSR_SCAN_SUCCESS; - sme_rrm_scan_request_callback(mac_handle, session_id, + for (i = 0; i < MAX_MEASUREMENT_REQUEST; i++) { + smerrmctx = &mac_ctx->rrm.rrmSmeContext[i]; + if (smerrmctx->scan_id == scan_id) + break; + + if (i == (MAX_MEASUREMENT_REQUEST - 1)) + return; + } + + sme_debug("Scan completed for scan_id:%d measurement_idx:%d", + scan_id, smerrmctx->measurement_idx); + sme_rrm_scan_request_callback(mac_ctx, smerrmctx, session_id, scan_id, scan_status); } - /** * sme_rrm_issue_scan_req() - To issue rrm scan request * @mac_ctx: pointer to mac context @@ -761,10 +814,11 @@ static void sme_rrm_scan_event_callback(struct wlan_objmgr_vdev *vdev, * * Return: QDF_STATUS */ -static QDF_STATUS sme_rrm_issue_scan_req(struct mac_context *mac_ctx) +static QDF_STATUS +sme_rrm_issue_scan_req(struct mac_context *mac_ctx, uint8_t idx) { QDF_STATUS status = QDF_STATUS_SUCCESS; - tpRrmSMEContext sme_rrm_ctx = &mac_ctx->rrm.rrmSmeContext; + tpRrmSMEContext sme_rrm_ctx = &mac_ctx->rrm.rrmSmeContext[idx]; uint32_t session_id; tSirScanType scan_type; uint8_t ch_idx; @@ -781,7 +835,8 @@ static QDF_STATUS sme_rrm_issue_scan_req(struct mac_context *mac_ctx) if ((sme_rrm_ctx->currentIndex) >= sme_rrm_ctx->channelList.numOfChannels) { - sme_rrm_send_beacon_report_xmit_ind(mac_ctx, NULL, true, 0); + sme_rrm_send_beacon_report_xmit_ind(mac_ctx, idx, NULL, + true, 0); sme_debug("done with the complete ch lt. finish and fee now"); goto free_ch_lst; } @@ -818,6 +873,10 @@ static QDF_STATUS sme_rrm_issue_scan_req(struct mac_context *mac_ctx) } ucfg_scan_init_default_params(vdev, req); req->scan_req.scan_id = ucfg_scan_get_scan_id(mac_ctx->psoc); + sme_rrm_ctx->scan_id = req->scan_req.scan_id; + + sme_debug("RRM_SCN: rrm_idx:%d scan_id:%d", + sme_rrm_ctx->measurement_idx, sme_rrm_ctx->scan_id); req->scan_req.scan_f_passive = (scan_type == eSIR_ACTIVE_SCAN) ? false : true; req->scan_req.vdev_id = wlan_vdev_get_id(vdev); @@ -924,11 +983,11 @@ static QDF_STATUS sme_rrm_issue_scan_req(struct mac_context *mac_ctx) freq_list = sme_rrm_ctx->channelList.freq_list; ch_idx = sme_rrm_ctx->currentIndex; if ((ch_idx + 1) < sme_rrm_ctx->channelList.numOfChannels) { - sme_rrm_send_scan_result(mac_ctx, 1, + sme_rrm_send_scan_result(mac_ctx, idx, 1, &freq_list[ch_idx], false); /* Advance the current index. */ sme_rrm_ctx->currentIndex++; - sme_rrm_issue_scan_req(mac_ctx); + sme_rrm_issue_scan_req(mac_ctx, idx); #ifdef FEATURE_WLAN_ESE sme_rrm_ctx->eseBcnReqInProgress = false; #endif @@ -938,7 +997,7 @@ static QDF_STATUS sme_rrm_issue_scan_req(struct mac_context *mac_ctx) * Done with the measurement. Clean up all context and * send a message to PE with measurement done flag set. */ - sme_rrm_send_scan_result(mac_ctx, 1, + sme_rrm_send_scan_result(mac_ctx, idx, 1, &freq_list[ch_idx], true); goto free_ch_lst; } @@ -951,7 +1010,7 @@ static QDF_STATUS sme_rrm_issue_scan_req(struct mac_context *mac_ctx) * and PE will not handle subsequent Beacon requests */ send_ind: - sme_rrm_send_beacon_report_xmit_ind(mac_ctx, NULL, true, 0); + sme_rrm_send_beacon_report_xmit_ind(mac_ctx, idx, NULL, true, 0); free_ch_lst: qdf_mem_free(sme_rrm_ctx->channelList.freq_list); sme_rrm_ctx->channelList.freq_list = NULL; @@ -1023,7 +1082,7 @@ QDF_STATUS sme_rrm_process_beacon_report_req_ind(struct mac_context *mac, void *msg_buf) { tpSirBeaconReportReqInd beacon_req = (tpSirBeaconReportReqInd)msg_buf; - tpRrmSMEContext sme_rrm_ctx = &mac->rrm.rrmSmeContext; + tpRrmSMEContext sme_rrm_ctx; uint32_t len = 0, i = 0; uint8_t country[WNI_CFG_COUNTRY_CODE_LEN]; uint32_t session_id; @@ -1034,6 +1093,8 @@ QDF_STATUS sme_rrm_process_beacon_report_req_ind(struct mac_context *mac, uint32_t *rrm_freq_list; uint32_t bcn_chan_freq; + sme_rrm_ctx = &mac->rrm.rrmSmeContext[beacon_req->measurement_idx]; + status = csr_roam_get_session_id_from_bssid(mac, (struct qdf_mac_addr *) beacon_req->bssId, &session_id); @@ -1056,7 +1117,8 @@ QDF_STATUS sme_rrm_process_beacon_report_req_ind(struct mac_context *mac, else country[2] = OP_CLASS_GLOBAL; - sme_debug("Request Reg class %d, AP's country code %c%c 0x%x, channel = %d", + sme_debug("RRM_SCN: Index:%d Request Reg class %d, AP's country code %c%c 0x%x, channel = %d", + beacon_req->measurement_idx, beacon_req->channel_info.reg_class, country[0], country[1], country[2], beacon_req->channel_info.chan_num); @@ -1172,7 +1234,7 @@ QDF_STATUS sme_rrm_process_beacon_report_req_ind(struct mac_context *mac, sme_rrm_ctx->regClass = beacon_req->channel_info.reg_class; sme_rrm_ctx->randnIntvl = QDF_MAX(beacon_req->randomizationInterval, - sme_rrm_ctx->rrmConfig.max_randn_interval); + mac->rrm.rrmConfig.max_randn_interval); sme_rrm_ctx->currentIndex = 0; sme_rrm_ctx->msgSource = beacon_req->msgSource; qdf_mem_copy((uint8_t *)&sme_rrm_ctx->measMode, @@ -1188,7 +1250,7 @@ QDF_STATUS sme_rrm_process_beacon_report_req_ind(struct mac_context *mac, sme_rrm_ctx->duration[0], sme_rrm_get_meas_mode_string(sme_rrm_ctx->measMode[0])); - return sme_rrm_issue_scan_req(mac); + return sme_rrm_issue_scan_req(mac, beacon_req->measurement_idx); cleanup: if (beacon_req->msgSource == eRRM_MSG_SOURCE_11K) { @@ -1199,7 +1261,8 @@ cleanup: /* copy measurement bssid */ qdf_mem_copy(sme_rrm_ctx->bssId, beacon_req->macaddrBssid, sizeof(tSirMacAddr)); - sme_rrm_send_beacon_report_xmit_ind(mac, NULL, true, 0); + sme_rrm_send_beacon_report_xmit_ind(mac, + sme_rrm_ctx->measurement_idx, NULL, true, 0); } return status; @@ -1234,7 +1297,7 @@ QDF_STATUS sme_rrm_neighbor_report_request(struct mac_context *mac, uint8_t /* If already a report is pending, return failure */ if (true == - mac->rrm.rrmSmeContext.neighborReqControlInfo. + mac->rrm.rrmSmeContext[0].neighborReqControlInfo. isNeighborRspPending) { sme_err("Neighbor request already pending.. Not allowed"); return QDF_STATUS_E_AGAIN; @@ -1245,7 +1308,7 @@ QDF_STATUS sme_rrm_neighbor_report_request(struct mac_context *mac, uint8_t return QDF_STATUS_E_NOMEM; rrm_ll_purge_neighbor_cache(mac, - &mac->rrm.rrmSmeContext.neighborReportCache); + &mac->rrm.rrmSmeContext[0].neighborReportCache); pMsg->messageType = eWNI_SME_NEIGHBOR_REPORT_REQ_IND; pMsg->length = sizeof(tSirNeighborReportReqInd); @@ -1261,16 +1324,17 @@ QDF_STATUS sme_rrm_neighbor_report_request(struct mac_context *mac, uint8_t /* Neighbor report request message sent successfully to PE. * Now register the callbacks */ - mac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo. - neighborRspCallback = callbackInfo->neighborRspCallback; - mac->rrm.rrmSmeContext.neighborReqControlInfo.neighborRspCallbackInfo. - neighborRspCallbackContext = - callbackInfo->neighborRspCallbackContext; - mac->rrm.rrmSmeContext.neighborReqControlInfo.isNeighborRspPending = + mac->rrm.rrmSmeContext[0].neighborReqControlInfo. + neighborRspCallbackInfo.neighborRspCallback = + callbackInfo->neighborRspCallback; + mac->rrm.rrmSmeContext[0].neighborReqControlInfo. + neighborRspCallbackInfo.neighborRspCallbackContext = + callbackInfo->neighborRspCallbackContext; + mac->rrm.rrmSmeContext[0].neighborReqControlInfo.isNeighborRspPending = true; /* Start neighbor response wait timer now */ - qdf_mc_timer_start(&mac->rrm.rrmSmeContext.neighborReqControlInfo. + qdf_mc_timer_start(&mac->rrm.rrmSmeContext[0].neighborReqControlInfo. neighborRspWaitTimer, callbackInfo->timeout); return QDF_STATUS_SUCCESS; @@ -1363,7 +1427,9 @@ check_11r_assoc: /** * rrm_store_neighbor_rpt_by_roam_score()-store Neighbor BSS descriptor + * @mac: Pointer to mac context * @pNeighborReportDesc - Neighbor BSS Descriptor node to be stored in cache + * @index: RRM sme context index * * This API is called to store a given * Neighbor BSS descriptor to the neighbor cache. This function @@ -1373,9 +1439,10 @@ check_11r_assoc: * Return: void. */ static void rrm_store_neighbor_rpt_by_roam_score(struct mac_context *mac, - tpRrmNeighborReportDesc pNeighborReportDesc) + tpRrmNeighborReportDesc pNeighborReportDesc, + uint8_t index) { - tpRrmSMEContext pSmeRrmContext = &mac->rrm.rrmSmeContext; + tpRrmSMEContext pSmeRrmContext = &mac->rrm.rrmSmeContext[0]; tListElem *pEntry; tRrmNeighborReportDesc *pTempNeighborReportDesc; @@ -1451,11 +1518,11 @@ static QDF_STATUS sme_rrm_process_neighbor_report(struct mac_context *mac, QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; /* Purge the cache on reception of unsolicited neighbor report */ - if (!mac->rrm.rrmSmeContext.neighborReqControlInfo. - isNeighborRspPending) + if (!mac->rrm.rrmSmeContext[neighbor_rpt->measurement_idx]. + neighborReqControlInfo.isNeighborRspPending) rrm_ll_purge_neighbor_cache(mac, - &mac->rrm.rrmSmeContext. - neighborReportCache); + &mac->rrm.rrmSmeContext[neighbor_rpt->measurement_idx]. + neighborReportCache); for (i = 0; i < neighbor_rpt->numNeighborReports; i++) { neighbor_rpt_desc = @@ -1485,8 +1552,9 @@ static QDF_STATUS sme_rrm_process_neighbor_report(struct mac_context *mac, rrm_calculate_neighbor_ap_roam_score(mac, neighbor_rpt_desc); if (neighbor_rpt_desc->roamScore > 0) { - rrm_store_neighbor_rpt_by_roam_score(mac, - neighbor_rpt_desc); + rrm_store_neighbor_rpt_by_roam_score( + mac, neighbor_rpt_desc, + neighbor_rpt->measurement_idx); } else { sme_err("Roam score of BSSID " QDF_MAC_ADDR_STR " is 0, Ignoring..", @@ -1501,7 +1569,9 @@ static QDF_STATUS sme_rrm_process_neighbor_report(struct mac_context *mac, } end: - if (!csr_ll_count(&mac->rrm.rrmSmeContext.neighborReportCache)) + if (!csr_ll_count( + &mac->rrm.rrmSmeContext[neighbor_rpt->measurement_idx]. + neighborReportCache)) qdf_status = QDF_STATUS_E_FAILURE; rrm_indicate_neighbor_report_result(mac, qdf_status); @@ -1554,14 +1624,24 @@ QDF_STATUS sme_rrm_msg_processor(struct mac_context *mac, uint16_t msg_type, * * Return: NULL */ -static void rrm_iter_meas_timer_handle(void *userData) +static void rrm_iter_meas_timer_handle(void *data) { - struct mac_context *mac = (struct mac_context *) userData; + struct mac_context *mac; + mac_handle_t mac_handle = cds_get_context(QDF_MODULE_ID_SME); + tpRrmSMEContext sme_rrm_ctx = (tpRrmSMEContext)data; + + mac = MAC_CONTEXT(mac_handle); + if (!mac) { + sme_err("Mac ctx is NULL"); + return; + } sme_debug("Randomization timer expired...send on next channel"); + /* Issue a scan req for next channel. */ - sme_rrm_issue_scan_req(mac); + sme_rrm_issue_scan_req(mac, sme_rrm_ctx->measurement_idx); } + /** * rrm_neighbor_rsp_timeout_handler() - Timer handler to handlet the timeout * @mac - The handle returned by mac_open. @@ -1587,12 +1667,12 @@ static void rrm_neighbor_rsp_timeout_handler(void *userData) */ static void rrm_change_default_config_param(struct mac_context *mac) { - mac->rrm.rrmSmeContext.rrmConfig.rrm_enabled = + mac->rrm.rrmConfig.rrm_enabled = mac->mlme_cfg->rrm_config.rrm_enabled; - mac->rrm.rrmSmeContext.rrmConfig.max_randn_interval = + mac->rrm.rrmConfig.max_randn_interval = mac->mlme_cfg->rrm_config.rrm_rand_interval; - qdf_mem_copy(&mac->rrm.rrmSmeContext.rrmConfig.rm_capability, + qdf_mem_copy(&mac->rrm.rrmConfig.rm_capability, &mac->mlme_cfg->rrm_config.rm_capability, RMENABLEDCAP_MAX_LEN); } @@ -1609,38 +1689,46 @@ QDF_STATUS rrm_open(struct mac_context *mac) { QDF_STATUS qdf_status; - tpRrmSMEContext pSmeRrmContext = &mac->rrm.rrmSmeContext; + tpRrmSMEContext pSmeRrmContext; QDF_STATUS qdf_ret_status = QDF_STATUS_SUCCESS; + uint8_t i; - pSmeRrmContext->rrmConfig.max_randn_interval = 50; /* ms */ + mac->rrm.rrmConfig.max_randn_interval = 50; /* ms */ - qdf_status = qdf_mc_timer_init(&pSmeRrmContext->IterMeasTimer, - QDF_TIMER_TYPE_SW, - rrm_iter_meas_timer_handle, - (void *)mac); + for (i = 0; i < MAX_MEASUREMENT_REQUEST; i++) { + pSmeRrmContext = &mac->rrm.rrmSmeContext[i]; - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { - sme_err("Fail to init measurement timer"); - return QDF_STATUS_E_FAILURE; - } + qdf_status = qdf_mc_timer_init(&pSmeRrmContext->IterMeasTimer, + QDF_TIMER_TYPE_SW, + rrm_iter_meas_timer_handle, + (void *)pSmeRrmContext); - qdf_status = - qdf_mc_timer_init(&pSmeRrmContext->neighborReqControlInfo. - neighborRspWaitTimer, QDF_TIMER_TYPE_SW, - rrm_neighbor_rsp_timeout_handler, - (void *)mac); + if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { + sme_err("Fail to init measurement timer"); + return QDF_STATUS_E_FAILURE; + } - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { - sme_err("Fail to init neighbor rsp wait timer"); - return QDF_STATUS_E_FAILURE; - } + qdf_status = + qdf_mc_timer_init(&pSmeRrmContext->neighborReqControlInfo. + neighborRspWaitTimer, QDF_TIMER_TYPE_SW, + rrm_neighbor_rsp_timeout_handler, + (void *)mac); - pSmeRrmContext->neighborReqControlInfo.isNeighborRspPending = false; + if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { + sme_err("Fail to init neighbor rsp wait timer"); + return QDF_STATUS_E_FAILURE; + } - qdf_ret_status = csr_ll_open(&pSmeRrmContext->neighborReportCache); - if (QDF_STATUS_SUCCESS != qdf_ret_status) { - sme_err("Fail to open neighbor cache result"); - return QDF_STATUS_E_FAILURE; + pSmeRrmContext->measurement_idx = i; + pSmeRrmContext->neighborReqControlInfo.isNeighborRspPending = + false; + + qdf_ret_status = + csr_ll_open(&pSmeRrmContext->neighborReportCache); + if (QDF_STATUS_SUCCESS != qdf_ret_status) { + sme_err("Fail to open neighbor cache result"); + return QDF_STATUS_E_FAILURE; + } } rrm_change_default_config_param(mac); @@ -1661,81 +1749,93 @@ QDF_STATUS rrm_open(struct mac_context *mac) QDF_STATUS rrm_close(struct mac_context *mac) { - QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; - tpRrmSMEContext pSmeRrmContext = &mac->rrm.rrmSmeContext; + tpRrmSMEContext pSmeRrmContext; + uint8_t i; - if (QDF_TIMER_STATE_RUNNING == - qdf_mc_timer_get_current_state(&pSmeRrmContext->IterMeasTimer)) { - qdf_status = qdf_mc_timer_stop(&pSmeRrmContext->IterMeasTimer); - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { - QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_ERROR, - FL("Timer stop fail")); + for (i = 0; i < MAX_MEASUREMENT_REQUEST; i++) { + pSmeRrmContext = &mac->rrm.rrmSmeContext[i]; + if (QDF_TIMER_STATE_RUNNING == + qdf_mc_timer_get_current_state( + &pSmeRrmContext->IterMeasTimer)) { + qdf_status = qdf_mc_timer_stop( + &pSmeRrmContext->IterMeasTimer); + if (QDF_IS_STATUS_ERROR(qdf_status)) + sme_err("Timer stop fail"); } - } - if (pSmeRrmContext->channelList.freq_list) { - qdf_mem_free(pSmeRrmContext->channelList.freq_list); - pSmeRrmContext->channelList.freq_list = NULL; - pSmeRrmContext->channelList.numOfChannels = 0; - } - - qdf_status = qdf_mc_timer_destroy(&pSmeRrmContext->IterMeasTimer); - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { - - QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_ERROR, - FL("Fail to destroy timer")); - - } - - if (QDF_TIMER_STATE_RUNNING == - qdf_mc_timer_get_current_state(&pSmeRrmContext-> - neighborReqControlInfo. - neighborRspWaitTimer)) { - qdf_status = qdf_mc_timer_stop(&pSmeRrmContext-> - neighborReqControlInfo. - neighborRspWaitTimer); - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { - QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_ERROR, - FL("Timer stop fail")); + if (pSmeRrmContext->channelList.freq_list) { + qdf_mem_free(pSmeRrmContext->channelList.freq_list); + pSmeRrmContext->channelList.freq_list = NULL; + pSmeRrmContext->channelList.numOfChannels = 0; } + + qdf_status = + qdf_mc_timer_destroy(&pSmeRrmContext->IterMeasTimer); + if (QDF_IS_STATUS_ERROR(qdf_status)) + sme_err("Fail to destroy timer"); + + if (QDF_TIMER_STATE_RUNNING == + qdf_mc_timer_get_current_state(&pSmeRrmContext-> + neighborReqControlInfo. + neighborRspWaitTimer)) { + qdf_status = qdf_mc_timer_stop(&pSmeRrmContext-> + neighborReqControlInfo. + neighborRspWaitTimer); + if (QDF_IS_STATUS_ERROR(qdf_status)) + sme_err("Timer stop fail"); + } + + qdf_status = qdf_mc_timer_destroy( + &pSmeRrmContext->neighborReqControlInfo. + neighborRspWaitTimer); + if (!QDF_IS_STATUS_SUCCESS(qdf_status)) + sme_err("Fail to destroy timer"); + + rrm_ll_purge_neighbor_cache( + mac, &pSmeRrmContext->neighborReportCache); + csr_ll_close(&pSmeRrmContext->neighborReportCache); } - qdf_status = - qdf_mc_timer_destroy(&pSmeRrmContext->neighborReqControlInfo. - neighborRspWaitTimer); - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { - QDF_TRACE(QDF_MODULE_ID_SME, QDF_TRACE_LEVEL_ERROR, - FL("Fail to destroy timer")); - - } - - rrm_ll_purge_neighbor_cache(mac, &pSmeRrmContext->neighborReportCache); - - csr_ll_close(&pSmeRrmContext->neighborReportCache); - return qdf_status; } QDF_STATUS rrm_start(struct mac_context *mac_ctx) { - tpRrmSMEContext smerrmctx = &mac_ctx->rrm.rrmSmeContext; + tpRrmSMEContext smerrmctx; + wlan_scan_requester req_id; + uint8_t i; + /* Register with scan component */ - smerrmctx->req_id = ucfg_scan_register_requester(mac_ctx->psoc, - "RRM", - sme_rrm_scan_event_callback, - smerrmctx); + req_id = ucfg_scan_register_requester(mac_ctx->psoc, + "RRM", + sme_rrm_scan_event_callback, + mac_ctx); + + for (i = 0; i < MAX_MEASUREMENT_REQUEST; i++) { + smerrmctx = &mac_ctx->rrm.rrmSmeContext[i]; + smerrmctx->req_id = req_id; + } return QDF_STATUS_SUCCESS; } QDF_STATUS rrm_stop(struct mac_context *mac_ctx) { - tpRrmSMEContext smerrmctx = &mac_ctx->rrm.rrmSmeContext; + tpRrmSMEContext smerrmctx; + wlan_scan_requester req_id; + uint8_t i; - ucfg_scan_unregister_requester(mac_ctx->psoc, smerrmctx->req_id); + for (i = 0; i < MAX_MEASUREMENT_REQUEST; i++) { + smerrmctx = &mac_ctx->rrm.rrmSmeContext[i]; + req_id = smerrmctx->req_id; + smerrmctx->req_id = 0; + } + + ucfg_scan_unregister_requester(mac_ctx->psoc, + req_id); return QDF_STATUS_SUCCESS; } diff --git a/core/wma/src/wma_scan_roam.c b/core/wma/src/wma_scan_roam.c index 7f1c329af8d1..83e2e6abdf57 100644 --- a/core/wma/src/wma_scan_roam.c +++ b/core/wma/src/wma_scan_roam.c @@ -3923,7 +3923,7 @@ QDF_STATUS wma_roam_scan_fill_self_caps(tp_wma_handle wma_handle, if (mac->mlme_cfg->scoring.apsd_enabled) selfCaps.apsd = 1; - selfCaps.rrm = mac->rrm.rrmSmeContext.rrmConfig.rrm_enabled; + selfCaps.rrm = mac->rrm.rrmConfig.rrm_enabled; val = mac->mlme_cfg->feature_flags.enable_block_ack; selfCaps.delayedBA =