summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSrinivas Girigowda <sgirigow@codeaurora.org>2018-06-18 16:38:38 -0700
committerSrinivas Girigowda <sgirigow@codeaurora.org>2018-06-18 16:52:19 -0700
commitf163c6090b9aa902742a7214489629ae67a55446 (patch)
treed291573ee256b26c3accc4d3cf402f8fb77073d0
parent8c48a260cec777caf58f85316c25c3fa14a5bf60 (diff)
downloadqcacld-f163c6090b9aa902742a7214489629ae67a55446.tar.gz
qcacld-3.0: Release 5.3.1.1Q
1546cd7 Release 5.3.1.1Q 90fb661 qcacld-3.0: Fix invalid dereferencing of peer_id_to_obj_map for peer_ref 328a147 qcacld-3.0: OOB access may occur due to total numChannels exceeds max value 3820448 qcacld-3.0: Do not return if hdd_open_cesium_nl_sock fails during init af391a4 qcacld-3.0: Update correct value for low power stats c4706d2 qcacld-3.0: Add check for validity of COUNTRY driver cmd e18a9cc Release 5.3.1.1P aba1b5c qcacld-3.0: Check for minimum frame_len for action frames 3a1313a qcacld-3.0: Add suppport to forward GAS action frames to supplicant 14f6935 qcacld-3.0: Check for SAP restart after channel switch 569a17b qcacld-3.0: Use request manager for OCB 94b1bb4 qcacld-3.0: Pass correct channel in ch_in_pcl() b6f35a0 qcacld-3.0: Fix OOB read in lim_process_deauth_frame .................................. Bug: 110352942 Change-Id: Ie27e954d1cc51fc23244aec81f4fe3b0de188741 Signed-off-by: Srinivas Girigowda <sgirigow@codeaurora.org>
-rw-r--r--core/dp/htt/htt_fw_stats.c2
-rw-r--r--core/dp/htt/htt_rx.c8
-rw-r--r--core/dp/htt/htt_t2h.c25
-rw-r--r--core/dp/ol/inc/ol_txrx_htt_api.h43
-rw-r--r--core/dp/txrx/ol_rx_reorder.c103
-rw-r--r--core/dp/txrx/ol_txrx.c3
-rw-r--r--core/hdd/inc/wlan_hdd_main.h21
-rw-r--r--core/hdd/inc/wlan_hdd_wext.h16
-rw-r--r--core/hdd/src/wlan_hdd_debugfs.c3
-rw-r--r--core/hdd/src/wlan_hdd_ext_scan.c5
-rw-r--r--core/hdd/src/wlan_hdd_hostapd.c17
-rw-r--r--core/hdd/src/wlan_hdd_ioctl.c21
-rw-r--r--core/hdd/src/wlan_hdd_ipa.c8
-rw-r--r--core/hdd/src/wlan_hdd_main.c8
-rw-r--r--core/hdd/src/wlan_hdd_ocb.c628
-rw-r--r--core/hdd/src/wlan_hdd_scan.c4
-rw-r--r--core/hdd/src/wlan_hdd_wext.c315
-rw-r--r--core/mac/inc/qwlan_version.h4
-rw-r--r--core/mac/inc/sir_mac_prot_def.h5
-rw-r--r--core/mac/src/pe/lim/lim_process_action_frame.c131
-rw-r--r--core/mac/src/pe/lim/lim_process_auth_frame.c46
-rw-r--r--core/mac/src/pe/lim/lim_process_deauth_frame.c6
-rw-r--r--core/mac/src/pe/lim/lim_send_sme_rsp_messages.c19
-rw-r--r--core/mac/src/sys/legacy/src/utils/src/parser_api.c3
-rw-r--r--core/sap/src/sap_ch_select.c9
-rw-r--r--core/sap/src/sap_module.c5
-rw-r--r--core/wma/src/wma_mgmt.c3
-rw-r--r--core/wma/src/wma_nan_datapath.c42
-rw-r--r--core/wma/src/wma_utils.c4
29 files changed, 763 insertions, 744 deletions
diff --git a/core/dp/htt/htt_fw_stats.c b/core/dp/htt/htt_fw_stats.c
index a9c0a85644..966e645ebe 100644
--- a/core/dp/htt/htt_fw_stats.c
+++ b/core/dp/htt/htt_fw_stats.c
@@ -977,7 +977,7 @@ htt_t2h_tx_ppdu_log_print(struct ol_fw_tx_dbg_ppdu_msg_hdr *hdr,
p8 = (uint8_t *) record;
calculated_p8 = p8 + sizeof(struct ol_fw_tx_dbg_ppdu_base);
if (calculated_p8 < p8) {
- qdf_err("Overflow due to record %p", p8);
+ qdf_err("Overflow due to record %pK", p8);
continue;
}
p8 = calculated_p8;
diff --git a/core/dp/htt/htt_rx.c b/core/dp/htt/htt_rx.c
index 247957225d..8837723556 100644
--- a/core/dp/htt/htt_rx.c
+++ b/core/dp/htt/htt_rx.c
@@ -506,6 +506,14 @@ static int htt_rx_ring_fill_n(struct htt_pdev_t *pdev, int num)
idx = *(pdev->rx_ring.alloc_idx.vaddr);
+ if ((idx < 0) || (idx > pdev->rx_ring.size_mask) ||
+ (num > pdev->rx_ring.size)) {
+ QDF_TRACE(QDF_MODULE_ID_HTT,
+ QDF_TRACE_LEVEL_ERROR,
+ "%s:rx refill failed!", __func__);
+ return filled;
+ }
+
if (qdf_mem_smmu_s1_enabled(pdev->osdev) && pdev->is_ipa_uc_enabled &&
pdev->rx_ring.smmu_map)
ipa_smmu = true;
diff --git a/core/dp/htt/htt_t2h.c b/core/dp/htt/htt_t2h.c
index 2db3a1ca25..a0c4b44014 100644
--- a/core/dp/htt/htt_t2h.c
+++ b/core/dp/htt/htt_t2h.c
@@ -283,33 +283,12 @@ static void htt_t2h_lp_msg_handler(void *context, qdf_nbuf_t htt_t2h_msg,
}
case HTT_T2H_MSG_TYPE_RX_ADDBA:
{
- uint16_t peer_id;
- uint8_t tid;
- uint8_t win_sz;
- uint16_t start_seq_num;
-
- /*
- * FOR NOW, the host doesn't need to know the initial
- * sequence number for rx aggregation.
- * Thus, any value will do - specify 0.
- */
- start_seq_num = 0;
- peer_id = HTT_RX_ADDBA_PEER_ID_GET(*msg_word);
- tid = HTT_RX_ADDBA_TID_GET(*msg_word);
- win_sz = HTT_RX_ADDBA_WIN_SIZE_GET(*msg_word);
- ol_rx_addba_handler(pdev->txrx_pdev, peer_id, tid,
- win_sz, start_seq_num,
- 0 /* success */);
+ qdf_print("HTT_T2H_MSG_TYPE_RX_ADDBA not supported ");
break;
}
case HTT_T2H_MSG_TYPE_RX_DELBA:
{
- uint16_t peer_id;
- uint8_t tid;
-
- peer_id = HTT_RX_DELBA_PEER_ID_GET(*msg_word);
- tid = HTT_RX_DELBA_TID_GET(*msg_word);
- ol_rx_delba_handler(pdev->txrx_pdev, peer_id, tid);
+ qdf_print("HTT_T2H_MSG_TYPE_RX_DELBA not supported ");
break;
}
case HTT_T2H_MSG_TYPE_PEER_MAP:
diff --git a/core/dp/ol/inc/ol_txrx_htt_api.h b/core/dp/ol/inc/ol_txrx_htt_api.h
index c1b995978c..277569bbe5 100644
--- a/core/dp/ol/inc/ol_txrx_htt_api.h
+++ b/core/dp/ol/inc/ol_txrx_htt_api.h
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2011-2017 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2011-2018 The Linux Foundation. All rights reserved.
*
* Previously licensed under the ISC license by Qualcomm Atheros, Inc.
*
@@ -502,47 +502,6 @@ ol_rx_sec_ind_handler(ol_txrx_pdev_handle pdev,
enum htt_sec_type sec_type,
int is_unicast, uint32_t *michael_key, uint32_t *rx_pn);
-/**
- * @brief Process an ADDBA message sent by the target.
- * @details
- * When the target notifies the host of an ADDBA event for a specified
- * peer-TID, the host will set up the rx reordering state for the peer-TID.
- * Specifically, the host will create a rx reordering array whose length
- * is based on the window size specified in the ADDBA.
- *
- * @param pdev - data physical device handle
- * (registered with HTT as a context pointer during attach time)
- * @param peer_id - which peer the ADDBA event is for
- * @param tid - which traffic ID within the peer the ADDBA event is for
- * @param win_sz - how many sequence numbers are in the ARQ block ack window
- * set up by the ADDBA event
- * @param start_seq_num - the initial value of the sequence number during the
- * block ack agreement, as specified by the ADDBA request.
- * @param failed - indicate whether the target's ADDBA setup succeeded:
- * 0 -> success, 1 -> fail
- */
-void
-ol_rx_addba_handler(ol_txrx_pdev_handle pdev,
- uint16_t peer_id,
- uint8_t tid,
- uint8_t win_sz, uint16_t start_seq_num, uint8_t failed);
-
-/**
- * @brief Process a DELBA message sent by the target.
- * @details
- * When the target notifies the host of a DELBA event for a specified
- * peer-TID, the host will clean up the rx reordering state for the peer-TID.
- * Specifically, the host will remove the rx reordering array, and will
- * set the reorder window size to be 1 (stop and go ARQ).
- *
- * @param pdev - data physical device handle
- * (registered with HTT as a context pointer during attach time)
- * @param peer_id - which peer the ADDBA event is for
- * @param tid - which traffic ID within the peer the ADDBA event is for
- */
-void
-ol_rx_delba_handler(ol_txrx_pdev_handle pdev, uint16_t peer_id, uint8_t tid);
-
enum htt_rx_flush_action {
htt_rx_flush_release,
htt_rx_flush_discard,
diff --git a/core/dp/txrx/ol_rx_reorder.c b/core/dp/txrx/ol_rx_reorder.c
index 85be924ad4..ff6180d0e3 100644
--- a/core/dp/txrx/ol_rx_reorder.c
+++ b/core/dp/txrx/ol_rx_reorder.c
@@ -47,24 +47,12 @@
#include <ol_rx_defrag.h>
/*=== data types and defines ===*/
-#define OL_RX_REORDER_ROUND_PWR2(value) g_log2ceil[value]
+
+/*---*/
/*=== global variables ===*/
-static char g_log2ceil[] = {
- 1, /* 0 -> 1 */
- 1, /* 1 -> 1 */
- 2, /* 2 -> 2 */
- 4, 4, /* 3-4 -> 4 */
- 8, 8, 8, 8, /* 5-8 -> 8 */
- 16, 16, 16, 16, 16, 16, 16, 16, /* 9-16 -> 16 */
- 32, 32, 32, 32, 32, 32, 32, 32,
- 32, 32, 32, 32, 32, 32, 32, 32, /* 17-32 -> 32 */
- 64, 64, 64, 64, 64, 64, 64, 64,
- 64, 64, 64, 64, 64, 64, 64, 64,
- 64, 64, 64, 64, 64, 64, 64, 64,
- 64, 64, 64, 64, 64, 64, 64, 64, /* 33-64 -> 64 */
-};
+/*---*/
/*=== function definitions ===*/
@@ -528,91 +516,6 @@ ol_rx_reorder_peer_cleanup(struct ol_txrx_vdev_t *vdev,
/* functions called by HTT */
void
-ol_rx_addba_handler(ol_txrx_pdev_handle pdev,
- uint16_t peer_id,
- uint8_t tid,
- uint8_t win_sz, uint16_t start_seq_num, uint8_t failed)
-{
- uint8_t round_pwr2_win_sz;
- unsigned int array_size;
- struct ol_txrx_peer_t *peer;
- struct ol_rx_reorder_t *rx_reorder;
-
- if (tid >= OL_TXRX_NUM_EXT_TIDS) {
- ol_txrx_err("%s: invalid tid, %u\n", __FUNCTION__, tid);
- WARN_ON(1);
- return;
- }
-
- peer = ol_txrx_peer_find_by_id(pdev, peer_id);
- if (peer == NULL)
- return;
-
- if (pdev->cfg.host_addba) {
- ol_ctrl_rx_addba_complete(pdev->ctrl_pdev,
- &peer->mac_addr.raw[0], tid, failed);
- }
- if (failed)
- return;
-
- peer->tids_last_seq[tid] = IEEE80211_SEQ_MAX; /* invalid */
- rx_reorder = &peer->tids_rx_reorder[tid];
-
- TXRX_ASSERT2(win_sz <= 64);
- rx_reorder->win_sz = win_sz;
- round_pwr2_win_sz = OL_RX_REORDER_ROUND_PWR2(win_sz);
- array_size =
- round_pwr2_win_sz * sizeof(struct ol_rx_reorder_array_elem_t);
- rx_reorder->array = qdf_mem_malloc(array_size);
- TXRX_ASSERT1(rx_reorder->array);
-
- rx_reorder->win_sz_mask = round_pwr2_win_sz - 1;
- rx_reorder->num_mpdus = 0;
-
- peer->tids_next_rel_idx[tid] =
- OL_RX_REORDER_IDX_INIT(start_seq_num, rx_reorder->win_sz,
- rx_reorder->win_sz_mask);
-}
-
-void
-ol_rx_delba_handler(ol_txrx_pdev_handle pdev, uint16_t peer_id, uint8_t tid)
-{
- struct ol_txrx_peer_t *peer;
- struct ol_rx_reorder_t *rx_reorder;
-
- if (tid >= OL_TXRX_NUM_EXT_TIDS) {
- ol_txrx_err("%s: invalid tid, %u\n", __FUNCTION__, tid);
- WARN_ON(1);
- return;
- }
-
- peer = ol_txrx_peer_find_by_id(pdev, peer_id);
- if (peer == NULL)
- return;
-
- peer->tids_next_rel_idx[tid] = INVALID_REORDER_INDEX;
- rx_reorder = &peer->tids_rx_reorder[tid];
-
- /* check that there really was a block ack agreement */
- TXRX_ASSERT1(rx_reorder->win_sz_mask != 0);
- /*
- * Deallocate the old rx reorder array.
- * The call to ol_rx_reorder_init below
- * will reset rx_reorder->array to point to
- * the single-element statically-allocated reorder array
- * used for non block-ack cases.
- */
- if (rx_reorder->array != &rx_reorder->base) {
- ol_txrx_dbg("%s, delete reorder array, tid:%d\n",
- __func__, tid);
- qdf_mem_free(rx_reorder->array);
- }
-
- /* set up the TID with default parameters (ARQ window size = 1) */
- ol_rx_reorder_init(rx_reorder, tid);
-}
-
-void
ol_rx_flush_handler(ol_txrx_pdev_handle pdev,
uint16_t peer_id,
uint8_t tid,
diff --git a/core/dp/txrx/ol_txrx.c b/core/dp/txrx/ol_txrx.c
index 287bfd84dc..d02b180630 100644
--- a/core/dp/txrx/ol_txrx.c
+++ b/core/dp/txrx/ol_txrx.c
@@ -3522,6 +3522,9 @@ bool ol_txrx_is_peer_eligible_for_deletion(ol_txrx_peer_handle peer,
for (i = 0; i < MAX_NUM_PEER_ID_PER_PEER; i++) {
peer_id = peer->peer_ids[i];
+ if (peer_id == HTT_INVALID_PEER)
+ continue;
+
if (!pdev->peer_id_to_obj_map[peer_id].peer_ref)
continue;
diff --git a/core/hdd/inc/wlan_hdd_main.h b/core/hdd/inc/wlan_hdd_main.h
index 554ab06d45..f936818f7b 100644
--- a/core/hdd/inc/wlan_hdd_main.h
+++ b/core/hdd/inc/wlan_hdd_main.h
@@ -412,12 +412,6 @@ struct statsContext {
unsigned int magic;
};
-struct linkspeedContext {
- struct completion completion;
- hdd_adapter_t *pAdapter;
- unsigned int magic;
-};
-
extern spinlock_t hdd_context_lock;
extern struct mutex hdd_init_deinit_lock;
@@ -425,9 +419,7 @@ extern struct mutex hdd_init_deinit_lock;
#define PEER_INFO_CONTEXT_MAGIC 0x50494E46 /* PEER_INFO(PINF) */
#define POWER_CONTEXT_MAGIC 0x504F5752 /* POWR */
#define SNR_CONTEXT_MAGIC 0x534E5200 /* SNR */
-#define LINK_CONTEXT_MAGIC 0x4C494E4B /* LINKSPEED */
#define LINK_STATUS_MAGIC 0x4C4B5354 /* LINKSTATUS(LNST) */
-#define TEMP_CONTEXT_MAGIC 0x74656d70 /* TEMP (temperature) */
#define APF_CONTEXT_MAGIC 0x4575354 /* APF */
#define POWER_STATS_MAGIC 0x14111990
#define ACTION_FRAME_RANDOM_CONTEXT_MAGIC 0x87878787
@@ -1395,8 +1387,9 @@ struct hdd_adapter_s {
struct net_device_stats stats;
/** HDD statistics*/
hdd_stats_t hdd_stats;
- /** linkspeed statistics */
- tSirLinkSpeedInfo ls_stats;
+
+ /* estimated link speed */
+ u32 estimated_linkspeed;
/* SAP peer station info */
struct sir_peer_sta_info peer_sta_info;
@@ -1565,14 +1558,8 @@ struct hdd_adapter_s {
/* Time stamp for start RoC request */
uint64_t start_roc_ts;
- /* State for synchronous OCB requests to WMI */
- struct sir_ocb_set_config_response ocb_set_config_resp;
- struct sir_ocb_get_tsf_timer_response ocb_get_tsf_timer_resp;
- struct sir_dcc_get_stats_response *dcc_get_stats_resp;
- struct sir_dcc_update_ndl_response dcc_update_ndl_resp;
-
- /* MAC addresses used for OCB interfaces */
#ifdef WLAN_FEATURE_DSRC
+ /* MAC addresses used for OCB interfaces */
struct qdf_mac_addr ocb_mac_address[QDF_MAX_CONCURRENCY_PERSONA];
int ocb_mac_addr_count;
#endif
diff --git a/core/hdd/inc/wlan_hdd_wext.h b/core/hdd/inc/wlan_hdd_wext.h
index 7f20207947..775f76c8b7 100644
--- a/core/hdd/inc/wlan_hdd_wext.h
+++ b/core/hdd/inc/wlan_hdd_wext.h
@@ -374,8 +374,20 @@ extern int hdd_priv_get_data(struct iw_point *p_priv_data,
extern void *mem_alloc_copy_from_user_helper(const void *wrqu_data, size_t len);
-int wlan_hdd_get_linkspeed_for_peermac(hdd_adapter_t *pAdapter,
- struct qdf_mac_addr mac_address);
+/**
+ * wlan_hdd_get_linkspeed_for_peermac() - Get link speed for a peer
+ * @adapter: adapter upon which the peer is active
+ * @mac_address: MAC address of the peer
+ * @linkspeed: pointer to memory where returned link speed is to be placed
+ *
+ * This function will send a query to SME for the linkspeed of the
+ * given peer, and then wait for the callback to be invoked.
+ *
+ * Return: 0 if linkspeed data is available, negative errno otherwise
+ */
+int wlan_hdd_get_linkspeed_for_peermac(hdd_adapter_t *adapter,
+ struct qdf_mac_addr *mac_address,
+ uint32_t *linkspeed);
void hdd_clear_roam_profile_ie(hdd_adapter_t *pAdapter);
uint8_t *wlan_hdd_get_vendor_oui_ie_ptr(uint8_t *oui, uint8_t oui_size,
diff --git a/core/hdd/src/wlan_hdd_debugfs.c b/core/hdd/src/wlan_hdd_debugfs.c
index e0a65be053..adc3576e7d 100644
--- a/core/hdd/src/wlan_hdd_debugfs.c
+++ b/core/hdd/src/wlan_hdd_debugfs.c
@@ -602,7 +602,8 @@ static void hdd_power_debugstats_cb(struct power_stats_response *response,
power_stats->cumulative_sleep_time_ms
= response->cumulative_sleep_time_ms;
power_stats->cumulative_total_on_time_ms
- = response->cumulative_total_on_time_ms;
+ = response->cumulative_total_on_time_ms -
+ response->cumulative_sleep_time_ms;
power_stats->deep_sleep_enter_counter
= response->deep_sleep_enter_counter;
power_stats->last_deep_sleep_enter_tstamp_ms
diff --git a/core/hdd/src/wlan_hdd_ext_scan.c b/core/hdd/src/wlan_hdd_ext_scan.c
index eee24657a1..d7811a8adb 100644
--- a/core/hdd/src/wlan_hdd_ext_scan.c
+++ b/core/hdd/src/wlan_hdd_ext_scan.c
@@ -3045,6 +3045,11 @@ static int hdd_extscan_start_fill_bucket_channel_spec(
total_channels++;
}
+ if (j != req_msg->buckets[bkt_index].numChannels) {
+ hdd_err("Input parameters didn't match");
+ goto fail;
+ }
+
hdd_extscan_update_dwell_time_limits(
req_msg, bkt_index,
min_dwell_time_active_bucket,
diff --git a/core/hdd/src/wlan_hdd_hostapd.c b/core/hdd/src/wlan_hdd_hostapd.c
index c2536968fb..40444746a1 100644
--- a/core/hdd/src/wlan_hdd_hostapd.c
+++ b/core/hdd/src/wlan_hdd_hostapd.c
@@ -1614,6 +1614,7 @@ QDF_STATUS hdd_hostapd_sap_event_cb(tpSap_Event pSapEvent,
tSap_StationDisassocCompleteEvent *disassoc_comp;
hdd_station_info_t *stainfo;
cds_context_type *cds_ctx;
+ hdd_adapter_t *sta_adapter;
dev = (struct net_device *)usrDataForCallback;
if (!dev) {
@@ -1840,6 +1841,12 @@ QDF_STATUS hdd_hostapd_sap_event_cb(tpSap_Event pSapEvent,
we_custom_event_generic = we_custom_start_event;
cds_dump_concurrency_info();
+ sta_adapter = hdd_get_adapter(pHddCtx, QDF_STA_MODE);
+ if (sta_adapter != NULL) {
+ hdd_debug("check for SAP restart");
+ cds_check_concurrent_intf_and_restart_sap(sta_adapter);
+ }
+
if (cds_is_hw_mode_change_after_vdev_up()) {
hdd_debug("check for possible hw mode change");
status = cds_set_hw_mode_on_channel_switch(
@@ -5664,15 +5671,13 @@ int __iw_get_softap_linkspeed(struct net_device *dev,
hdd_err("Invalid peer macaddress");
return -EINVAL;
}
- errno = wlan_hdd_get_linkspeed_for_peermac(pHostapdAdapter,
- macAddress);
- if (errno) {
+ rc = wlan_hdd_get_linkspeed_for_peermac(pHostapdAdapter, &macAddress,
+ &link_speed);
+ if (rc) {
hdd_err("Unable to retrieve SME linkspeed: %d", errno);
- return errno;
+ return rc;
}
- link_speed = pHostapdAdapter->ls_stats.estLinkSpeed;
-
/* linkspeed in units of 500 kbps */
link_speed = link_speed / 500;
wrqu->data.length = len;
diff --git a/core/hdd/src/wlan_hdd_ioctl.c b/core/hdd/src/wlan_hdd_ioctl.c
index 6e456eb4f7..bf521ae228 100644
--- a/core/hdd/src/wlan_hdd_ioctl.c
+++ b/core/hdd/src/wlan_hdd_ioctl.c
@@ -2973,7 +2973,26 @@ static int drv_cmd_country(hdd_adapter_t *adapter,
char *country_code;
int32_t cc_from_db;
- country_code = command + 8;
+ country_code = strnchr(command, strlen(command), ' ');
+ /* no argument after the command*/
+ if (!country_code)
+ return -EINVAL;
+
+ /* no space after the command*/
+ if (SPACE_ASCII_VALUE != *country_code)
+ return -EINVAL;
+
+ country_code++;
+
+ /* removing empty spaces*/
+ while ((SPACE_ASCII_VALUE == *country_code) &&
+ ('\0' != *country_code))
+ country_code++;
+
+ /* no or less than 2 arguments followed by spaces*/
+ if (*country_code == '\0' || *(country_code + 1) == '\0')
+ return -EINVAL;
+
if (!((country_code[0] == 'X' && country_code[1] == 'X') ||
(country_code[0] == '0' && country_code[1] == '0'))) {
cc_from_db = cds_get_country_from_alpha2(country_code);
diff --git a/core/hdd/src/wlan_hdd_ipa.c b/core/hdd/src/wlan_hdd_ipa.c
index f35371cf2c..fe13fdeef2 100644
--- a/core/hdd/src/wlan_hdd_ipa.c
+++ b/core/hdd/src/wlan_hdd_ipa.c
@@ -6391,9 +6391,11 @@ static void hdd_ipa_cleanup_iface(struct hdd_ipa_iface_context *iface_context)
if (iface_context == NULL)
return;
- if (hdd_validate_adapter(iface_context->adapter))
+ if (hdd_validate_adapter(iface_context->adapter)) {
HDD_IPA_LOG(QDF_TRACE_LEVEL_DEBUG, "Invalid adapter: 0x%pK",
iface_context->adapter);
+ return;
+ }
hdd_ipa_wdi_dereg_intf(iface_context->hdd_ipa,
iface_context->adapter->dev->name);
@@ -7200,11 +7202,13 @@ hdd_ipa_uc_proc_pending_event(struct hdd_ipa_priv *hdd_ipa, bool is_loading)
qdf_list_remove_front(&hdd_ipa->pending_event,
(qdf_list_node_t **)&pending_event);
while (pending_event != NULL) {
- if (pending_event->is_loading == is_loading)
+ if (pending_event->is_loading == is_loading &&
+ !hdd_validate_adapter(pending_event->adapter)) {
__hdd_ipa_wlan_evt(pending_event->adapter,
pending_event->sta_id,
pending_event->type,
pending_event->mac_addr);
+ }
qdf_mem_free(pending_event);
pending_event = NULL;
qdf_list_remove_front(&hdd_ipa->pending_event,
diff --git a/core/hdd/src/wlan_hdd_main.c b/core/hdd/src/wlan_hdd_main.c
index 91c9738d43..ace17b1c3a 100644
--- a/core/hdd/src/wlan_hdd_main.c
+++ b/core/hdd/src/wlan_hdd_main.c
@@ -750,8 +750,7 @@ int hdd_validate_adapter(hdd_adapter_t *adapter)
}
if (adapter->magic != WLAN_HDD_ADAPTER_MAGIC) {
- hdd_err("bad adapter magic: 0x%x (should be 0x%x)",
- adapter->magic, WLAN_HDD_ADAPTER_MAGIC);
+ hdd_err("bad adapter magic");
return -EINVAL;
}
@@ -6186,10 +6185,8 @@ static int hdd_init_netlink_services(hdd_context_t *hdd_ctx)
ptt_sock_activate_svc();
ret = hdd_open_cesium_nl_sock();
- if (ret) {
+ if (ret)
hdd_err("hdd_open_cesium_nl_sock failed ret: %d", ret);
- goto err_ptt_sock;
- }
ret = cnss_diag_activate_service();
if (ret) {
@@ -6209,7 +6206,6 @@ err_cnss_diag:
cnss_diag_deactivate_service();
err_close_cesium:
hdd_close_cesium_nl_sock();
-err_ptt_sock:
ptt_sock_deactivate_svc();
oem_deactivate_service();
err_nl_srv:
diff --git a/core/hdd/src/wlan_hdd_ocb.c b/core/hdd/src/wlan_hdd_ocb.c
index d3fc052271..3cc55703d8 100644
--- a/core/hdd/src/wlan_hdd_ocb.c
+++ b/core/hdd/src/wlan_hdd_ocb.c
@@ -36,6 +36,7 @@
#include "wlan_hdd_main.h"
#include "wlan_hdd_ocb.h"
#include "wlan_hdd_trace.h"
+#include "wlan_hdd_request_manager.h"
#include "target_if_def_config.h"
#include "sch_api.h"
#include "wma_api.h"
@@ -50,20 +51,6 @@
/* Maximum time(ms) to wait for OCB operations */
#define WLAN_WAIT_TIME_OCB_CMD 1500
-#define HDD_OCB_MAGIC 0x489a154f
-
-/**
- * struct hdd_ocb_ctxt - Context for OCB operations
- * adapter: the ocb adapter
- * completion_evt: the completion event
- * status: status of the request
- */
-struct hdd_ocb_ctxt {
- uint32_t magic;
- hdd_adapter_t *adapter;
- struct completion completion_evt;
- int status;
-};
/**
* hdd_set_dot11p_config() - Set 802.11p config flag
@@ -348,6 +335,11 @@ fail:
return NULL;
}
+struct hdd_ocb_set_config_priv {
+ int status;
+};
+
+
/**
* hdd_ocb_set_config_callback() - OCB set config callback function
* @context_ptr: OCB call context
@@ -358,47 +350,27 @@ fail:
*/
static void hdd_ocb_set_config_callback(void *context_ptr, void *response_ptr)
{
- struct hdd_ocb_ctxt *context = context_ptr;
- struct sir_ocb_set_config_response *resp = response_ptr;
+ struct hdd_request *hdd_request;
+ struct hdd_ocb_set_config_priv *priv;
+ struct sir_ocb_set_config_response *response = response_ptr;
- if (!context)
+ hdd_request = hdd_request_get(context_ptr);
+ if (!hdd_request) {
+ hdd_err("Obsolete request");
return;
+ }
+ priv = hdd_request_priv(hdd_request);
- if (resp && resp->status)
- hdd_warn("Operation failed: %d", resp->status);
-
- spin_lock(&hdd_context_lock);
- if (context->magic == HDD_OCB_MAGIC) {
- hdd_adapter_t *adapter = context->adapter;
+ if (response && response->status)
+ hdd_warn("Operation failed: %d", response->status);
- if (!resp) {
- context->status = -EINVAL;
- complete(&context->completion_evt);
- spin_unlock(&hdd_context_lock);
- return;
- }
-
- context->adapter->ocb_set_config_resp = *resp;
- spin_unlock(&hdd_context_lock);
- if (!resp->status) {
- /*
- * OCB set config command successful.
- * Open the TX data path
- */
- if (!hdd_ocb_register_sta(adapter)) {
- wlan_hdd_netif_queue_control(adapter,
- WLAN_START_ALL_NETIF_QUEUE_N_CARRIER,
- WLAN_CONTROL_PATH);
- }
- }
+ if (response && (0 == response->status))
+ priv->status = 0;
+ else
+ priv->status = -EINVAL;
- spin_lock(&hdd_context_lock);
- if (context->magic == HDD_OCB_MAGIC)
- complete(&context->completion_evt);
- spin_unlock(&hdd_context_lock);
- } else {
- spin_unlock(&hdd_context_lock);
- }
+ hdd_request_complete(hdd_request);
+ hdd_request_put(hdd_request);
}
/**
@@ -412,59 +384,70 @@ static int hdd_ocb_set_config_req(hdd_adapter_t *adapter,
struct sir_ocb_config *config)
{
int rc;
- QDF_STATUS qdf_status;
- struct hdd_ocb_ctxt context = {0};
+ QDF_STATUS status;
+ hdd_context_t *hdd_ctx = WLAN_HDD_GET_CTX(adapter);
+ void *cookie;
+ struct hdd_request *hdd_request;
+ struct hdd_ocb_set_config_priv *priv;
+ static const struct hdd_request_params params = {
+ .priv_size = sizeof(*priv),
+ .timeout_ms = WLAN_WAIT_TIME_OCB_CMD,
+ };
if (hdd_ocb_validate_config(adapter, config)) {
hdd_err("The configuration is invalid");
return -EINVAL;
}
- init_completion(&context.completion_evt);
- context.adapter = adapter;
- context.magic = HDD_OCB_MAGIC;
+ hdd_request = hdd_request_alloc(&params);
+ if (!hdd_request) {
+ hdd_err("Request allocation failure");
+ return -ENOMEM;
+ }
+ cookie = hdd_request_cookie(hdd_request);
- hdd_info("Disabling queues");
+ hdd_debug("Disabling queues");
wlan_hdd_netif_queue_control(adapter,
WLAN_STOP_ALL_NETIF_QUEUE_N_CARRIER,
WLAN_CONTROL_PATH);
- /* Call the SME API to set the config */
- qdf_status = sme_ocb_set_config(
- ((hdd_context_t *)adapter->pHddCtx)->hHal, &context,
- hdd_ocb_set_config_callback, config);
- if (qdf_status != QDF_STATUS_SUCCESS) {
- hdd_err("Error calling SME function.");
- /* Convert from qdf_status to errno */
- return -EINVAL;
+ status = sme_ocb_set_config(hdd_ctx->hHal, cookie,
+ hdd_ocb_set_config_callback,
+ config);
+ if (QDF_IS_STATUS_ERROR(status)) {
+ hdd_err("Failed to set channel config.");
+ /* Convert from eHalStatus to errno */
+ rc = qdf_status_to_os_return(status);
+ goto end;
}
/* Wait for the function to complete. */
- rc = wait_for_completion_timeout(&context.completion_evt,
- msecs_to_jiffies(WLAN_WAIT_TIME_OCB_CMD));
- if (rc == 0) {
- rc = -ETIMEDOUT;
+ rc = hdd_request_wait_for_response(hdd_request);
+ if (rc) {
+ hdd_err("Operation timed out");
goto end;
}
- rc = 0;
- if (context.status) {
- rc = context.status;
+ priv = hdd_request_priv(hdd_request);
+ rc = priv->status;
+ if (rc) {
+ hdd_err("Operation failed: %d", rc);
goto end;
}
- if (adapter->ocb_set_config_resp.status) {
- rc = -EINVAL;
- goto end;
- }
+ /*
+ * OCB set config command successful.
+ * Open the TX data path
+ */
+ if (!hdd_ocb_register_sta(adapter))
+ wlan_hdd_netif_queue_control(adapter,
+ WLAN_START_ALL_NETIF_QUEUE_N_CARRIER,
+ WLAN_CONTROL_PATH);
/* fall through */
end:
- spin_lock(&hdd_context_lock);
- context.magic = 0;
- spin_unlock(&hdd_context_lock);
- if (rc)
- hdd_err("Operation failed: %d", rc);
+ hdd_request_put(hdd_request);
+
return rc;
}
@@ -1314,6 +1297,11 @@ int wlan_hdd_cfg80211_ocb_stop_timing_advert(struct wiphy *wiphy,
return ret;
}
+struct hdd_ocb_get_tsf_timer_priv {
+ struct sir_ocb_get_tsf_timer_response response;
+ int status;
+};
+
/**
* hdd_ocb_get_tsf_timer_callback() - Callback to get TSF command
* @context_ptr: request context
@@ -1322,23 +1310,67 @@ int wlan_hdd_cfg80211_ocb_stop_timing_advert(struct wiphy *wiphy,
static void hdd_ocb_get_tsf_timer_callback(void *context_ptr,
void *response_ptr)
{
- struct hdd_ocb_ctxt *context = context_ptr;
+ struct hdd_request *hdd_request;
+ struct hdd_ocb_get_tsf_timer_priv *priv;
struct sir_ocb_get_tsf_timer_response *response = response_ptr;
- if (!context)
+ hdd_request = hdd_request_get(context_ptr);
+ if (!hdd_request) {
+ hdd_err("Obsolete request");
return;
+ }
- spin_lock(&hdd_context_lock);
- if (context->magic == HDD_OCB_MAGIC) {
- if (response) {
- context->adapter->ocb_get_tsf_timer_resp = *response;
- context->status = 0;
- } else {
- context->status = -EINVAL;
- }
- complete(&context->completion_evt);
+ if (response) {
+ priv->response = *response;
+ priv->status = 0;
+ } else {
+ priv->status = -EINVAL;
}
- spin_unlock(&hdd_context_lock);
+ hdd_request_complete(hdd_request);
+ hdd_request_put(hdd_request);
+}
+
+static int
+hdd_ocb_get_tsf_timer_reply(struct wiphy *wiphy,
+ struct sir_ocb_get_tsf_timer_response *response)
+{
+ uint32_t nl_buf_len;
+ struct sk_buff *nl_resp;
+ int rc;
+
+ /* Allocate the buffer for the response. */
+ nl_buf_len = NLMSG_HDRLEN;
+ nl_buf_len += 2 * (NLA_HDRLEN + sizeof(uint32_t));
+ nl_resp = cfg80211_vendor_cmd_alloc_reply_skb(wiphy, nl_buf_len);
+ if (!nl_resp) {
+ hdd_err("cfg80211_vendor_cmd_alloc_reply_skb failed");
+ return -ENOMEM;
+ }
+
+ /* Populate the response. */
+ rc = nla_put_u32(nl_resp,
+ QCA_WLAN_VENDOR_ATTR_OCB_GET_TSF_RESP_TIMER_HIGH,
+ response->timer_high);
+ if (rc)
+ goto end;
+ rc = nla_put_u32(nl_resp,
+ QCA_WLAN_VENDOR_ATTR_OCB_GET_TSF_RESP_TIMER_LOW,
+ response->timer_low);
+ if (rc)
+ goto end;
+
+ /* Send the response. */
+ rc = cfg80211_vendor_cmd_reply(nl_resp);
+ nl_resp = NULL;
+ if (rc) {
+ hdd_err("cfg80211_vendor_cmd_reply failed: %d", rc);
+ goto end;
+ }
+end:
+ if (nl_resp)
+ kfree_skb(nl_resp);
+
+ return rc;
}
/**
@@ -1356,18 +1388,25 @@ __wlan_hdd_cfg80211_ocb_get_tsf_timer(struct wiphy *wiphy,
const void *data,
int data_len)
{
- struct sk_buff *nl_resp = 0;
hdd_context_t *hdd_ctx = wiphy_priv(wiphy);
struct net_device *dev = wdev->netdev;
hdd_adapter_t *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
- int rc = -EINVAL;
+ int rc;
struct sir_ocb_get_tsf_timer request = {0};
- struct hdd_ocb_ctxt context = {0};
+ QDF_STATUS status;
+ void *cookie;
+ struct hdd_request *hdd_request;
+ struct hdd_ocb_get_tsf_timer_priv *priv;
+ static const struct hdd_request_params params = {
+ .priv_size = sizeof(*priv),
+ .timeout_ms = WLAN_WAIT_TIME_OCB_CMD,
+ };
ENTER_DEV(dev);
- if (wlan_hdd_validate_context(hdd_ctx))
- return -EINVAL;
+ rc = wlan_hdd_validate_context(hdd_ctx);
+ if (rc)
+ return rc;
if (adapter->device_mode != QDF_OCB_MODE) {
hdd_err("Device not in OCB mode!");
@@ -1379,77 +1418,52 @@ __wlan_hdd_cfg80211_ocb_get_tsf_timer(struct wiphy *wiphy,
return -EINVAL;
}
- /* Initialize the callback context */
- init_completion(&context.completion_evt);
- context.adapter = adapter;
- context.magic = HDD_OCB_MAGIC;
+ hdd_request = hdd_request_alloc(&params);
+ if (!hdd_request) {
+ hdd_err("Request allocation failure");
+ return -ENOMEM;
+ }
+ cookie = hdd_request_cookie(hdd_request);
request.vdev_id = adapter->sessionId;
/* Call the SME function */
- rc = sme_ocb_get_tsf_timer(hdd_ctx->hHal, &context,
- hdd_ocb_get_tsf_timer_callback,
- &request);
- if (rc) {
- hdd_err("Error calling SME function");
- /* Need to convert from qdf_status to errno. */
- return -EINVAL;
- }
-
- rc = wait_for_completion_timeout(&context.completion_evt,
- msecs_to_jiffies(WLAN_WAIT_TIME_OCB_CMD));
- if (rc == 0) {
- hdd_err("Operation timed out");
- rc = -ETIMEDOUT;
+ status = sme_ocb_get_tsf_timer(hdd_ctx->hHal, cookie,
+ hdd_ocb_get_tsf_timer_callback,
+ &request);
+ if (QDF_IS_STATUS_ERROR(status)) {
+ hdd_err("Failed to get tsf timer.");
+ rc = qdf_status_to_os_return(status);
goto end;
}
- rc = 0;
- if (context.status) {
- hdd_err("Operation failed: %d", context.status);
- rc = context.status;
+ rc = hdd_request_wait_for_response(hdd_request);
+ if (rc) {
+ hdd_err("Operation timed out");
goto end;
}
- /* Allocate the buffer for the response. */
- nl_resp = cfg80211_vendor_cmd_alloc_reply_skb(wiphy,
- 2 * sizeof(uint32_t) + NLMSG_HDRLEN);
-
- if (!nl_resp) {
- hdd_err("cfg80211_vendor_cmd_alloc_reply_skb failed");
- rc = -ENOMEM;
+ priv = hdd_request_priv(hdd_request);
+ rc = priv->status;
+ if (rc) {
+ hdd_err("Operation failed: %d", rc);
goto end;
}
hdd_debug("Got TSF timer response, high=%d, low=%d",
- adapter->ocb_get_tsf_timer_resp.timer_high,
- adapter->ocb_get_tsf_timer_resp.timer_low);
-
- /* Populate the response. */
- rc = nla_put_u32(nl_resp,
- QCA_WLAN_VENDOR_ATTR_OCB_GET_TSF_RESP_TIMER_HIGH,
- adapter->ocb_get_tsf_timer_resp.timer_high);
- if (rc)
- goto end;
- rc = nla_put_u32(nl_resp,
- QCA_WLAN_VENDOR_ATTR_OCB_GET_TSF_RESP_TIMER_LOW,
- adapter->ocb_get_tsf_timer_resp.timer_low);
- if (rc)
- goto end;
+ priv->response.timer_high,
+ priv->response.timer_low);
/* Send the response. */
- rc = cfg80211_vendor_cmd_reply(nl_resp);
- nl_resp = NULL;
+ rc = hdd_ocb_get_tsf_timer_reply(wiphy, &priv->response);
if (rc) {
- hdd_err("cfg80211_vendor_cmd_reply failed: %d", rc);
+ hdd_err("hdd_ocb_get_tsf_timer_reply failed: %d", rc);
goto end;
}
+ /* fall through */
end:
- spin_lock(&hdd_context_lock);
- context.magic = 0;
- spin_unlock(&hdd_context_lock);
- if (nl_resp)
- kfree_skb(nl_resp);
+ hdd_request_put(hdd_request);
+
return rc;
}
@@ -1477,6 +1491,19 @@ int wlan_hdd_cfg80211_ocb_get_tsf_timer(struct wiphy *wiphy,
return ret;
}
+struct hdd_dcc_stats_priv {
+ struct sir_dcc_get_stats_response *response;
+ int status;
+};
+
+static void hdd_dcc_get_stats_dealloc(void *context_ptr)
+{
+ struct hdd_dcc_stats_priv *priv = context_ptr;
+
+ qdf_mem_free(priv->response);
+ priv->response = NULL;
+}
+
/**
* hdd_dcc_get_stats_callback() - Callback to get stats command
* @context_ptr: request context
@@ -1484,46 +1511,86 @@ int wlan_hdd_cfg80211_ocb_get_tsf_timer(struct wiphy *wiphy,
*/
static void hdd_dcc_get_stats_callback(void *context_ptr, void *response_ptr)
{
- struct hdd_ocb_ctxt *context = context_ptr;
+ struct hdd_request *hdd_request;
+ struct hdd_dcc_stats_priv *priv;
struct sir_dcc_get_stats_response *response = response_ptr;
struct sir_dcc_get_stats_response *hdd_resp;
- if (!context)
+ hdd_request = hdd_request_get(context_ptr);
+ if (!hdd_request) {
+ hdd_err("Obsolete request");
return;
+ }
- spin_lock(&hdd_context_lock);
- if (context->magic == HDD_OCB_MAGIC) {
- if (response) {
- /*
- * If the response is hanging around from the previous
- * request, delete it
- */
- if (context->adapter->dcc_get_stats_resp) {
- qdf_mem_free(
- context->adapter->dcc_get_stats_resp);
- }
- context->adapter->dcc_get_stats_resp =
- qdf_mem_malloc(sizeof(
- *context->adapter->dcc_get_stats_resp) +
- response->channel_stats_array_len);
- if (context->adapter->dcc_get_stats_resp) {
- hdd_resp = context->adapter->dcc_get_stats_resp;
- *hdd_resp = *response;
- hdd_resp->channel_stats_array =
- (void *)hdd_resp + sizeof(*hdd_resp);
- qdf_mem_copy(hdd_resp->channel_stats_array,
- response->channel_stats_array,
- response->channel_stats_array_len);
- context->status = 0;
- } else {
- context->status = -ENOMEM;
- }
- } else {
- context->status = -EINVAL;
- }
- complete(&context->completion_evt);
+ priv = hdd_request_priv(hdd_request);
+ if (!response) {
+ priv->status = -EINVAL;
+ goto end;
}
- spin_unlock(&hdd_context_lock);
+
+ priv->response = qdf_mem_malloc(sizeof(*response) +
+ response->channel_stats_array_len);
+ if (!priv->response) {
+ priv->status = -ENOMEM;
+ goto end;
+ }
+
+ hdd_resp = priv->response;
+ *hdd_resp = *response;
+ hdd_resp->channel_stats_array = (void *)hdd_resp + sizeof(*hdd_resp);
+ qdf_mem_copy(hdd_resp->channel_stats_array,
+ response->channel_stats_array,
+ response->channel_stats_array_len);
+ priv->status = 0;
+
+end:
+ hdd_request_complete(hdd_request);
+ hdd_request_put(hdd_request);
+}
+
+static int
+hdd_dcc_get_stats_send_reply(struct wiphy *wiphy,
+ struct sir_dcc_get_stats_response *response)
+{
+ uint32_t nl_buf_len;
+ struct sk_buff *nl_resp;
+ int rc;
+
+ /* Allocate the buffer for the response. */
+ nl_buf_len = NLMSG_HDRLEN;
+ nl_buf_len += NLA_HDRLEN + sizeof(uint32_t);
+ nl_buf_len += NLA_HDRLEN + response->channel_stats_array_len;
+ nl_resp = cfg80211_vendor_cmd_alloc_reply_skb(wiphy, nl_buf_len);
+ if (!nl_resp) {
+ hdd_err("cfg80211_vendor_cmd_alloc_reply_skb failed");
+ return -ENOMEM;
+ }
+
+ /* Populate the response. */
+ rc = nla_put_u32(nl_resp,
+ QCA_WLAN_VENDOR_ATTR_DCC_GET_STATS_RESP_CHANNEL_COUNT,
+ response->num_channels);
+ if (rc)
+ goto end;
+ rc = nla_put(nl_resp,
+ QCA_WLAN_VENDOR_ATTR_DCC_GET_STATS_RESP_STATS_ARRAY,
+ response->channel_stats_array_len,
+ response->channel_stats_array);
+ if (rc)
+ goto end;
+
+ /* Send the response. */
+ rc = cfg80211_vendor_cmd_reply(nl_resp);
+ nl_resp = NULL;
+ if (rc) {
+ hdd_err("cfg80211_vendor_cmd_reply failed: %d", rc);
+ goto end;
+ }
+end:
+ if (nl_resp)
+ kfree_skb(nl_resp);
+
+ return rc;
}
/**
@@ -1547,15 +1614,23 @@ static int __wlan_hdd_cfg80211_dcc_get_stats(struct wiphy *wiphy,
struct net_device *dev = wdev->netdev;
hdd_adapter_t *adapter = WLAN_HDD_GET_PRIV_PTR(dev);
struct nlattr *tb[QCA_WLAN_VENDOR_ATTR_DCC_GET_STATS_MAX + 1];
- struct sk_buff *nl_resp = 0;
- int rc = -EINVAL;
+ int rc;
struct sir_dcc_get_stats request = {0};
- struct hdd_ocb_ctxt context = {0};
+ QDF_STATUS status;
+ void *cookie;
+ struct hdd_request *hdd_request;
+ struct hdd_dcc_stats_priv *priv;
+ static const struct hdd_request_params params = {
+ .priv_size = sizeof(*priv),
+ .timeout_ms = WLAN_WAIT_TIME_OCB_CMD,
+ .dealloc = hdd_dcc_get_stats_dealloc,
+ };
ENTER_DEV(dev);
- if (wlan_hdd_validate_context(hdd_ctx))
- return -EINVAL;
+ rc = wlan_hdd_validate_context(hdd_ctx);
+ if (rc)
+ return rc;
if (adapter->device_mode != QDF_OCB_MODE) {
hdd_err("Device not in OCB mode!");
@@ -1588,10 +1663,12 @@ static int __wlan_hdd_cfg80211_dcc_get_stats(struct wiphy *wiphy,
request_array = nla_data(
tb[QCA_WLAN_VENDOR_ATTR_DCC_GET_STATS_REQUEST_ARRAY]);
- /* Initialize the callback context */
- init_completion(&context.completion_evt);
- context.adapter = adapter;
- context.magic = HDD_OCB_MAGIC;
+ hdd_request = hdd_request_alloc(&params);
+ if (!hdd_request) {
+ hdd_err("Request allocation failure");
+ return -ENOMEM;
+ }
+ cookie = hdd_request_cookie(hdd_request);
request.vdev_id = adapter->sessionId;
request.channel_count = channel_count;
@@ -1599,76 +1676,40 @@ static int __wlan_hdd_cfg80211_dcc_get_stats(struct wiphy *wiphy,
request.request_array = request_array;
/* Call the SME function. */
- rc = sme_dcc_get_stats(hdd_ctx->hHal, &context,
- hdd_dcc_get_stats_callback,
- &request);
- if (rc) {
- hdd_err("Error calling SME function");
- /* Need to convert from qdf_status to errno. */
- return -EINVAL;
- }
-
- /* Wait for the function to complete. */
- rc = wait_for_completion_timeout(&context.completion_evt,
- msecs_to_jiffies(WLAN_WAIT_TIME_OCB_CMD));
- if (rc == 0) {
- hdd_err("Operation failed: %d", rc);
- rc = -ETIMEDOUT;
- goto end;
- }
-
- if (context.status) {
- hdd_err("There was error: %d", context.status);
- rc = context.status;
+ status = sme_dcc_get_stats(hdd_ctx->hHal, cookie,
+ hdd_dcc_get_stats_callback,
+ &request);
+ if (QDF_IS_STATUS_ERROR(status)) {
+ hdd_err("Error calling SME function.");
+ rc = qdf_status_to_os_return(status);
goto end;
}
- if (!adapter->dcc_get_stats_resp) {
- hdd_err("The response was NULL");
- rc = -EINVAL;
+ /* Wait for the function to complete. */
+ rc = hdd_request_wait_for_response(hdd_request);
+ if (rc) {
+ hdd_err("Operation timed out");
goto end;
}
- /* Allocate the buffer for the response. */
- nl_resp = cfg80211_vendor_cmd_alloc_reply_skb(wiphy, sizeof(uint32_t) +
- adapter->dcc_get_stats_resp->channel_stats_array_len +
- NLMSG_HDRLEN);
- if (!nl_resp) {
- hdd_err("cfg80211_vendor_cmd_alloc_reply_skb failed");
- rc = -ENOMEM;
+ priv = hdd_request_priv(hdd_request);
+ rc = priv->status;
+ if (rc) {
+ hdd_err("Operation failed: %d", rc);
goto end;
}
- /* Populate the response. */
- rc = nla_put_u32(nl_resp,
- QCA_WLAN_VENDOR_ATTR_DCC_GET_STATS_RESP_CHANNEL_COUNT,
- adapter->dcc_get_stats_resp->num_channels);
- if (rc)
- goto end;
- rc = nla_put(nl_resp,
- QCA_WLAN_VENDOR_ATTR_DCC_GET_STATS_RESP_STATS_ARRAY,
- adapter->dcc_get_stats_resp->channel_stats_array_len,
- adapter->dcc_get_stats_resp->channel_stats_array);
- if (rc)
- goto end;
-
/* Send the response. */
- rc = cfg80211_vendor_cmd_reply(nl_resp);
- nl_resp = NULL;
+ rc = hdd_dcc_get_stats_send_reply(wiphy, priv->response);
if (rc) {
- hdd_err("cfg80211_vendor_cmd_reply failed: %d", rc);
+ hdd_err("hdd_dcc_get_stats_send_reply failed: %d", rc);
goto end;
}
/* fall through */
end:
- spin_lock(&hdd_context_lock);
- context.magic = 0;
- qdf_mem_free(adapter->dcc_get_stats_resp);
- adapter->dcc_get_stats_resp = NULL;
- spin_unlock(&hdd_context_lock);
- if (nl_resp)
- kfree_skb(nl_resp);
+ hdd_request_put(hdd_request);
+
return rc;
}
@@ -1779,6 +1820,10 @@ int wlan_hdd_cfg80211_dcc_clear_stats(struct wiphy *wiphy,
return ret;
}
+struct hdd_dcc_update_ndl_priv {
+ int status;
+};
+
/**
* hdd_dcc_update_ndl_callback() - Callback to update NDL command
* @context_ptr: request context
@@ -1786,23 +1831,22 @@ int wlan_hdd_cfg80211_dcc_clear_stats(struct wiphy *wiphy,
*/
static void hdd_dcc_update_ndl_callback(void *context_ptr, void *response_ptr)
{
- struct hdd_ocb_ctxt *context = context_ptr;
+ struct hdd_request *hdd_request;
+ struct hdd_dcc_update_ndl_priv *priv;
struct sir_dcc_update_ndl_response *response = response_ptr;
- if (!context)
+ hdd_request = hdd_request_get(context_ptr);
+ if (!hdd_request) {
+ hdd_err("Obsolete request");
return;
-
- spin_lock(&hdd_context_lock);
- if (context->magic == HDD_OCB_MAGIC) {
- if (response) {
- context->adapter->dcc_update_ndl_resp = *response;
- context->status = 0;
- } else {
- context->status = -EINVAL;
- }
- complete(&context->completion_evt);
}
- spin_unlock(&hdd_context_lock);
+ priv = hdd_request_priv(hdd_request);
+ if (response && (0 == response->status))
+ priv->status = 0;
+ else
+ priv->status = -EINVAL;
+ hdd_request_complete(hdd_request);
+ hdd_request_put(hdd_request);
}
/**
@@ -1829,17 +1873,25 @@ static int __wlan_hdd_cfg80211_dcc_update_ndl(struct wiphy *wiphy,
void *ndl_channel_array;
uint32_t ndl_active_state_array_len;
void *ndl_active_state_array;
- int rc = -EINVAL;
- struct hdd_ocb_ctxt context = {0};
+ int rc;
+ QDF_STATUS status;
+ void *cookie;
+ struct hdd_request *hdd_request;
+ struct hdd_dcc_update_ndl_priv *priv;
+ static const struct hdd_request_params params = {
+ .priv_size = sizeof(*priv),
+ .timeout_ms = WLAN_WAIT_TIME_OCB_CMD,
+ };
ENTER_DEV(dev);
- if (wlan_hdd_validate_context(hdd_ctx))
- goto end;
+ rc = wlan_hdd_validate_context(hdd_ctx);
+ if (rc)
+ return rc;
if (adapter->device_mode != QDF_OCB_MODE) {
hdd_err("Device not in OCB mode!");
- goto end;
+ return -EINVAL;
}
if (!wma_is_vdev_up(adapter->sessionId)) {
@@ -1851,7 +1903,7 @@ static int __wlan_hdd_cfg80211_dcc_update_ndl(struct wiphy *wiphy,
if (hdd_nla_parse(tb, QCA_WLAN_VENDOR_ATTR_DCC_UPDATE_NDL_MAX, data,
data_len, qca_wlan_vendor_dcc_update_ndl)) {
hdd_err("Invalid ATTR");
- goto end;
+ return -EINVAL;
}
/* Verify that the parameter is present */
@@ -1873,10 +1925,12 @@ static int __wlan_hdd_cfg80211_dcc_update_ndl(struct wiphy *wiphy,
ndl_active_state_array = nla_data(
tb[QCA_WLAN_VENDOR_ATTR_DCC_UPDATE_NDL_ACTIVE_STATE_ARRAY]);
- /* Initialize the callback context */
- init_completion(&context.completion_evt);
- context.adapter = adapter;
- context.magic = HDD_OCB_MAGIC;
+ hdd_request = hdd_request_alloc(&params);
+ if (!hdd_request) {
+ hdd_err("Request allocation failure");
+ return -ENOMEM;
+ }
+ cookie = hdd_request_cookie(hdd_request);
/* Copy the parameters to the request structure. */
request.vdev_id = adapter->sessionId;
@@ -1887,43 +1941,33 @@ static int __wlan_hdd_cfg80211_dcc_update_ndl(struct wiphy *wiphy,
request.dcc_ndl_active_state_list = ndl_active_state_array;
/* Call the SME function */
- rc = sme_dcc_update_ndl(hdd_ctx->hHal, &context,
- hdd_dcc_update_ndl_callback,
- &request);
- if (rc) {
+ status = sme_dcc_update_ndl(hdd_ctx->hHal, cookie,
+ hdd_dcc_update_ndl_callback,
+ &request);
+ if (QDF_IS_STATUS_ERROR(status)) {
hdd_err("Error calling SME function.");
- /* Convert from qdf_status to errno */
- return -EINVAL;
+ rc = qdf_status_to_os_return(status);
+ goto end;
}
/* Wait for the function to complete. */
- rc = wait_for_completion_timeout(&context.completion_evt,
- msecs_to_jiffies(WLAN_WAIT_TIME_OCB_CMD));
- if (rc == 0) {
+ rc = hdd_request_wait_for_response(hdd_request);
+ if (rc) {
hdd_err("Operation timed out");
- rc = -ETIMEDOUT;
- goto end;
- }
- rc = 0;
-
- if (context.status) {
- hdd_err("Operation failed: %d", context.status);
- rc = context.status;
goto end;
}
- if (adapter->dcc_update_ndl_resp.status) {
- hdd_err("Operation returned: %d",
- adapter->dcc_update_ndl_resp.status);
- rc = -EINVAL;
+ priv = hdd_request_priv(hdd_request);
+ rc = priv->status;
+ if (rc) {
+ hdd_err("Operation failed: %d", rc);
goto end;
}
/* fall through */
end:
- spin_lock(&hdd_context_lock);
- context.magic = 0;
- spin_unlock(&hdd_context_lock);
+ hdd_request_put(hdd_request);
+
return rc;
}
diff --git a/core/hdd/src/wlan_hdd_scan.c b/core/hdd/src/wlan_hdd_scan.c
index 41c3577593..8b7fe10eae 100644
--- a/core/hdd/src/wlan_hdd_scan.c
+++ b/core/hdd/src/wlan_hdd_scan.c
@@ -95,6 +95,10 @@ struct nla_policy scan_policy[QCA_WLAN_VENDOR_ATTR_SCAN_MAX + 1] = {
[QCA_WLAN_VENDOR_ATTR_SCAN_COOKIE] = {.type = NLA_U64},
[QCA_WLAN_VENDOR_ATTR_SCAN_IE] = {.type = NLA_BINARY,
.len = MAX_DEFAULT_SCAN_IE_LEN},
+ [QCA_WLAN_VENDOR_ATTR_SCAN_MAC] = {.type = NLA_UNSPEC,
+ .len = QDF_MAC_ADDR_SIZE},
+ [QCA_WLAN_VENDOR_ATTR_SCAN_MAC_MASK] = {.type = NLA_UNSPEC,
+ .len = QDF_MAC_ADDR_SIZE},
};
/**
diff --git a/core/hdd/src/wlan_hdd_wext.c b/core/hdd/src/wlan_hdd_wext.c
index 2dbb292176..d177e7b61f 100644
--- a/core/hdd/src/wlan_hdd_wext.c
+++ b/core/hdd/src/wlan_hdd_wext.c
@@ -52,6 +52,7 @@
#include <wlan_hdd_wmm.h>
#include "utils_api.h"
#include "wlan_hdd_p2p.h"
+#include "wlan_hdd_request_manager.h"
#ifdef FEATURE_WLAN_TDLS
#include "wlan_hdd_tdls.h"
#endif
@@ -3694,139 +3695,92 @@ QDF_STATUS wlan_hdd_get_snr(hdd_adapter_t *pAdapter, int8_t *snr)
return QDF_STATUS_SUCCESS;
}
-/**
- * hdd_get_link_speed_cb() - Get link speed callback function
- * @pLinkSpeed: pointer to the link speed record
- * @pContext: pointer to the user context passed to SME
- *
- * This function is passed as the callback function to
- * sme_get_link_speed() by wlan_hdd_get_linkspeed_for_peermac(). By
- * agreement a &struct linkspeedContext is passed as @pContext. If
- * the context is valid, then the contents of @pLinkSpeed are copied
- * into the adapter record referenced by @pContext where they can be
- * subsequently retrieved. If the context is invalid, then this
- * function does nothing since it is assumed the caller has already
- * timed-out and destroyed the context.
- *
- * Return: None.
- */
+struct linkspeed_priv {
+ tSirLinkSpeedInfo linkspeed_info;
+};
+
static void
-hdd_get_link_speed_cb(tSirLinkSpeedInfo *pLinkSpeed, void *pContext)
+hdd_get_link_speed_cb(tSirLinkSpeedInfo *linkspeed_info, void *context)
{
- struct linkspeedContext *pLinkSpeedContext;
- hdd_adapter_t *pAdapter;
+ struct hdd_request *request;
+ struct linkspeed_priv *priv;
- if ((NULL == pLinkSpeed) || (NULL == pContext)) {
- hdd_err("Bad param, pLinkSpeed [%pK] pContext [%pK]",
- pLinkSpeed, pContext);
+ if (!linkspeed_info) {
+ hdd_err("NULL linkspeed");
return;
}
- spin_lock(&hdd_context_lock);
- pLinkSpeedContext = pContext;
- pAdapter = pLinkSpeedContext->pAdapter;
- /* there is a race condition that exists between this callback
- * function and the caller since the caller could time out either
- * before or while this code is executing. we use a spinlock to
- * serialize these actions
- */
-
- if ((NULL == pAdapter) ||
- (LINK_CONTEXT_MAGIC != pLinkSpeedContext->magic)) {
- /* the caller presumably timed out so there is nothing
- * we can do
- */
- spin_unlock(&hdd_context_lock);
- hdd_warn("Invalid context, pAdapter [%pK] magic [%08x]",
- pAdapter, pLinkSpeedContext->magic);
+ request = hdd_request_get(context);
+ if (!request) {
+ hdd_err("Obsolete request");
return;
}
- /* context is valid so caller is still waiting */
-
- /* paranoia: invalidate the magic */
- pLinkSpeedContext->magic = 0;
-
- /* copy over the stats. do so as a struct copy */
- pAdapter->ls_stats = *pLinkSpeed;
-
- /* notify the caller */
- complete(&pLinkSpeedContext->completion);
-
- /* serialization is complete */
- spin_unlock(&hdd_context_lock);
+ priv = hdd_request_priv(request);
+ priv->linkspeed_info = *linkspeed_info;
+ hdd_request_complete(request);
+ hdd_request_put(request);
}
-/**
- * wlan_hdd_get_linkspeed_for_peermac() - Get link speed for a peer
- * @pAdapter: adapter upon which the peer is active
- * @macAddress: MAC address of the peer
- *
- * This function will send a query to SME for the linkspeed of the
- * given peer, and then wait for the callback to be invoked.
- *
- * Return: Errno
- */
-int wlan_hdd_get_linkspeed_for_peermac(hdd_adapter_t *pAdapter,
- struct qdf_mac_addr macAddress)
+int wlan_hdd_get_linkspeed_for_peermac(hdd_adapter_t *adapter,
+ struct qdf_mac_addr *mac_address,
+ uint32_t *linkspeed)
{
+ int ret;
QDF_STATUS status;
- int errno;
- unsigned long rc;
- static struct linkspeedContext context;
- tSirLinkSpeedInfo *linkspeed_req;
+ void *cookie;
+ tSirLinkSpeedInfo *linkspeed_info;
+ struct hdd_request *request;
+ struct linkspeed_priv *priv;
+ static const struct hdd_request_params params = {
+ .priv_size = sizeof(*priv),
+ .timeout_ms = WLAN_WAIT_TIME_STATS,
+ };
- if (NULL == pAdapter) {
- hdd_err("pAdapter is NULL");
+ if ((!adapter) || (!linkspeed)) {
+ hdd_err("NULL argument");
return -EINVAL;
}
- linkspeed_req = qdf_mem_malloc(sizeof(*linkspeed_req));
- if (NULL == linkspeed_req) {
- hdd_err("Request Buffer Alloc Fail");
- return -ENOMEM;
+ request = hdd_request_alloc(&params);
+ if (!request) {
+ hdd_err("Request allocation failure");
+ ret = -ENOMEM;
+ goto return_cached_value;
}
- init_completion(&context.completion);
- context.pAdapter = pAdapter;
- context.magic = LINK_CONTEXT_MAGIC;
+ cookie = hdd_request_cookie(request);
+ priv = hdd_request_priv(request);
- qdf_copy_macaddr(&linkspeed_req->peer_macaddr, &macAddress);
- status = sme_get_link_speed(WLAN_HDD_GET_HAL_CTX(pAdapter),
- linkspeed_req,
- &context, hdd_get_link_speed_cb);
- qdf_mem_free(linkspeed_req);
- errno = qdf_status_to_os_return(status);
- if (errno) {
+ linkspeed_info = &priv->linkspeed_info;
+ qdf_copy_macaddr(&linkspeed_info->peer_macaddr, mac_address);
+ status = sme_get_link_speed(WLAN_HDD_GET_HAL_CTX(adapter),
+ linkspeed_info,
+ cookie, hdd_get_link_speed_cb);
+ if (QDF_IS_STATUS_ERROR(status)) {
hdd_err("Unable to retrieve statistics for link speed");
- } else {
- rc = wait_for_completion_timeout
- (&context.completion,
- msecs_to_jiffies(WLAN_WAIT_TIME_STATS));
- if (!rc) {
- hdd_err("SME timed out while retrieving link speed");
- errno = -ETIMEDOUT;
- }
- }
-
- /* either we never sent a request, we sent a request and
- * received a response or we sent a request and timed out. if
- * we never sent a request or if we sent a request and got a
- * response, we want to clear the magic out of paranoia. if
- * we timed out there is a race condition such that the
- * callback function could be executing at the same time we
- * are. of primary concern is if the callback function had
- * already verified the "magic" but had not yet set the
- * completion variable when a timeout occurred. we serialize
- * these activities by invalidating the magic while holding a
- * shared spinlock which will cause us to block if the
- * callback is currently executing
+ ret = qdf_status_to_os_return(status);
+ goto cleanup;
+ }
+ ret = hdd_request_wait_for_response(request);
+ if (ret) {
+ hdd_err("SME timed out while retrieving link speed");
+ goto cleanup;
+ }
+ adapter->estimated_linkspeed = linkspeed_info->estLinkSpeed;
+
+cleanup:
+ /*
+ * either we never sent a request, we sent a request and
+ * received a response or we sent a request and timed out.
+ * regardless we are done with the request.
*/
- spin_lock(&hdd_context_lock);
- context.magic = 0;
- spin_unlock(&hdd_context_lock);
+ hdd_request_put(request);
- return errno;
+return_cached_value:
+ *linkspeed = adapter->estimated_linkspeed;
+
+ return ret;
}
/**
@@ -3867,12 +3821,12 @@ int wlan_hdd_get_link_speed(hdd_adapter_t *sta_adapter, uint32_t *link_speed)
qdf_copy_macaddr(&bssid, &hdd_stactx->conn_info.bssId);
- errno = wlan_hdd_get_linkspeed_for_peermac(sta_adapter, bssid);
+ errno = wlan_hdd_get_linkspeed_for_peermac(sta_adapter, &bssid,
+ link_speed);
if (errno) {
hdd_err("Unable to retrieve SME linkspeed: %d", errno);
return errno;
}
- *link_speed = sta_adapter->ls_stats.estLinkSpeed;
/* linkspeed in units of 500 kbps */
*link_speed = (*link_speed) / 500;
}
@@ -4888,7 +4842,8 @@ static int __iw_set_bitrate(struct net_device *dev,
hdd_adapter_t *pAdapter = WLAN_HDD_GET_PRIV_PTR(dev);
hdd_wext_state_t *pWextState;
hdd_station_ctx_t *pHddStaCtx = WLAN_HDD_GET_STATION_CTX_PTR(pAdapter);
- uint8_t supp_rates[WNI_CFG_SUPPORTED_RATES_11A_LEN];
+ uint8_t supp_rates[WNI_CFG_SUPPORTED_RATES_11A_LEN +
+ WNI_CFG_SUPPORTED_RATES_11B_LEN];
uint32_t a_len = WNI_CFG_SUPPORTED_RATES_11A_LEN;
uint32_t b_len = WNI_CFG_SUPPORTED_RATES_11B_LEN;
uint32_t i, rate;
@@ -4924,7 +4879,8 @@ static int __iw_set_bitrate(struct net_device *dev,
&a_len) == QDF_STATUS_SUCCESS)
&&
(sme_cfg_get_str(WLAN_HDD_GET_HAL_CTX(pAdapter),
- WNI_CFG_SUPPORTED_RATES_11B, supp_rates,
+ WNI_CFG_SUPPORTED_RATES_11B,
+ supp_rates + a_len,
&b_len) == QDF_STATUS_SUCCESS)) {
for (i = 0; i < (b_len + a_len); ++i) {
/* supported rates returned is double
@@ -7304,10 +7260,14 @@ free:
return retval;
}
+struct temperature_priv {
+ int temperature;
+};
+
/**
* hdd_get_temperature_cb() - "Get Temperature" callback function
* @temperature: measured temperature
- * @pContext: callback context
+ * @context: callback context
*
* This function is passed to sme_get_temperature() as the callback
* function to be invoked when the temperature measurement is
@@ -7315,30 +7275,24 @@ free:
*
* Return: None
*/
-static void hdd_get_temperature_cb(int temperature, void *pContext)
+static void hdd_get_temperature_cb(int temperature, void *context)
{
- struct statsContext *pTempContext;
- hdd_adapter_t *pAdapter;
+ struct hdd_request *request;
+ struct temperature_priv *priv;
ENTER();
- if (NULL == pContext) {
- hdd_err("pContext is NULL");
- return;
- }
- pTempContext = pContext;
- pAdapter = pTempContext->pAdapter;
- spin_lock(&hdd_context_lock);
- if ((NULL == pAdapter) || (TEMP_CONTEXT_MAGIC != pTempContext->magic)) {
- spin_unlock(&hdd_context_lock);
- hdd_warn("Invalid context, pAdapter [%pK] magic [%08x]",
- pAdapter, pTempContext->magic);
+
+ request = hdd_request_get(context);
+ if (!request) {
+ hdd_err("Obsolete request");
return;
}
- if (temperature != 0)
- pAdapter->temperature = temperature;
- complete(&pTempContext->completion);
- spin_unlock(&hdd_context_lock);
+ priv = hdd_request_priv(request);
+ priv->temperature = temperature;
+ hdd_request_complete(request);
+ hdd_request_put(request);
+
EXIT();
}
@@ -7351,35 +7305,54 @@ static void hdd_get_temperature_cb(int temperature, void *pContext)
* returned, otherwise a negative errno is returned.
*
*/
-int wlan_hdd_get_temperature(hdd_adapter_t *pAdapter, int *temperature)
+int wlan_hdd_get_temperature(hdd_adapter_t *p_adapter, int *temperature)
{
QDF_STATUS status;
- static struct statsContext tempContext;
- unsigned long rc;
+ int ret;
+ void *cookie;
+ struct hdd_request *request;
+ struct temperature_priv *priv;
+ static const struct hdd_request_params params = {
+ .priv_size = sizeof(*priv),
+ .timeout_ms = WLAN_WAIT_TIME_STATS,
+ };
ENTER();
- if (NULL == pAdapter) {
+ if (!p_adapter) {
hdd_err("pAdapter is NULL");
return -EPERM;
}
- init_completion(&tempContext.completion);
- tempContext.pAdapter = pAdapter;
- tempContext.magic = TEMP_CONTEXT_MAGIC;
- status = sme_get_temperature(WLAN_HDD_GET_HAL_CTX(pAdapter),
- &tempContext, hdd_get_temperature_cb);
+
+ request = hdd_request_alloc(&params);
+ if (!request) {
+ hdd_err("Request allocation failure");
+ return -ENOMEM;
+ }
+ cookie = hdd_request_cookie(request);
+ status = sme_get_temperature(WLAN_HDD_GET_HAL_CTX(p_adapter),
+ cookie, hdd_get_temperature_cb);
if (QDF_STATUS_SUCCESS != status) {
hdd_err("Unable to retrieve temperature");
} else {
- rc = wait_for_completion_timeout(&tempContext.completion,
- msecs_to_jiffies
- (WLAN_WAIT_TIME_STATS));
- if (!rc)
+ ret = hdd_request_wait_for_response(request);
+ if (ret) {
hdd_err("SME timed out while retrieving temperature");
+ } else {
+ /* update the adapter with the fresh results */
+ priv = hdd_request_priv(request);
+ if (priv->temperature)
+ p_adapter->temperature = priv->temperature;
+ }
}
- spin_lock(&hdd_context_lock);
- tempContext.magic = 0;
- spin_unlock(&hdd_context_lock);
- *temperature = pAdapter->temperature;
+
+ /*
+ * either we never sent a request, we sent a request and
+ * received a response or we sent a request and timed out.
+ * regardless we are done with the request.
+ */
+ hdd_request_put(request);
+
+ *temperature = p_adapter->temperature;
EXIT();
return 0;
}
@@ -11523,6 +11496,38 @@ int wlan_hdd_set_filter(hdd_context_t *hdd_ctx,
}
/**
+ * validate_packet_filter_params_size() - Validate the size of the params rcvd
+ * @priv_data: Pointer to the priv data from user space
+ * @request: Pointer to the struct containing the copied data from user space
+ *
+ * Return: False on invalid length, true otherwise
+ */
+static bool validate_packet_filter_params_size(struct pkt_filter_cfg *request,
+ uint16_t length)
+{
+ int max_params_size, rcvd_params_size;
+
+ max_params_size = HDD_MAX_CMP_PER_PACKET_FILTER *
+ sizeof(struct pkt_filter_param_cfg);
+
+ if (length < sizeof(struct pkt_filter_cfg) - max_params_size) {
+ hdd_err("Less than minimum number of arguments needed");
+ return false;
+ }
+
+ rcvd_params_size = request->num_params *
+ sizeof(struct pkt_filter_param_cfg);
+
+ if (length != sizeof(struct pkt_filter_cfg) -
+ max_params_size + rcvd_params_size) {
+ hdd_err("Arguments do not match the number of params provided");
+ return false;
+ }
+
+ return true;
+}
+
+/**
* __iw_set_packet_filter_params() - set packet filter parameters in target
* @dev: Pointer to netdev
* @info: Pointer to iw request info
@@ -11558,8 +11563,7 @@ static int __iw_set_packet_filter_params(struct net_device *dev,
return -EINVAL;
}
- if ((NULL == priv_data.pointer) || (0 == priv_data.length) ||
- priv_data.length < sizeof(struct pkt_filter_cfg)) {
+ if ((NULL == priv_data.pointer) || (0 == priv_data.length)) {
hdd_err("invalid priv data %pK or invalid priv data length %d",
priv_data.pointer, priv_data.length);
return -EINVAL;
@@ -11579,11 +11583,18 @@ static int __iw_set_packet_filter_params(struct net_device *dev,
/* copy data using copy_from_user */
request = mem_alloc_copy_from_user_helper(priv_data.pointer,
priv_data.length);
+
if (NULL == request) {
hdd_err("mem_alloc_copy_from_user_helper fail");
return -ENOMEM;
}
+ if (!validate_packet_filter_params_size(request, priv_data.length)) {
+ hdd_err("Invalid priv data length %d", priv_data.length);
+ qdf_mem_free(request);
+ return -EINVAL;
+ }
+
if (request->filter_action == HDD_RCV_FILTER_SET)
hdd_ctx->user_configured_pkt_filter_rules |=
1 << request->filter_id;
diff --git a/core/mac/inc/qwlan_version.h b/core/mac/inc/qwlan_version.h
index 3c191f71af..b4b97af4f1 100644
--- a/core/mac/inc/qwlan_version.h
+++ b/core/mac/inc/qwlan_version.h
@@ -41,9 +41,9 @@
#define QWLAN_VERSION_MAJOR 5
#define QWLAN_VERSION_MINOR 3
#define QWLAN_VERSION_PATCH 1
-#define QWLAN_VERSION_EXTRA "O"
+#define QWLAN_VERSION_EXTRA "Q"
#define QWLAN_VERSION_BUILD 1
-#define QWLAN_VERSIONSTR "5.3.1.1O"
+#define QWLAN_VERSIONSTR "5.3.1.1Q"
#endif /* QWLAN_VERSION_H */
diff --git a/core/mac/inc/sir_mac_prot_def.h b/core/mac/inc/sir_mac_prot_def.h
index 2795e8b11c..ddc7bc201e 100644
--- a/core/mac/inc/sir_mac_prot_def.h
+++ b/core/mac/inc/sir_mac_prot_def.h
@@ -217,6 +217,11 @@
#define SIR_MAC_ACTION_EXT_CHANNEL_SWITCH_ID 4
#define SIR_MAC_ACTION_MEASUREMENT_PILOT 7
+/* Public Action frames for GAS */
+#define SIR_MAC_ACTION_GAS_INITIAL_REQUEST 0x0A
+#define SIR_MAC_ACTION_GAS_INITIAL_RESPONSE 0x0B
+#define SIR_MAC_ACTION_GAS_COMEBACK_REQUEST 0x0C
+#define SIR_MAC_ACTION_GAS_COMEBACK_RESPONSE 0x0D
#ifdef WLAN_FEATURE_11W
/* 11w SA query request/response action frame category code */
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 67f9a877ef..bdaa51564e 100644
--- a/core/mac/src/pe/lim/lim_process_action_frame.c
+++ b/core/mac/src/pe/lim/lim_process_action_frame.c
@@ -1656,7 +1656,7 @@ static void lim_process_action_vendor_specific(tpAniSirGlobal mac_ctx,
mac_hdr = WMA_GET_RX_MAC_HEADER(pkt_info);
frame_len = WMA_GET_RX_PAYLOAD_LEN(pkt_info);
- if (frame_len < sizeof(action_hdr)) {
+ if (frame_len < sizeof(*action_hdr)) {
pe_debug("Received action frame of invalid len %d", frame_len);
return;
}
@@ -1705,11 +1705,17 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
#endif
tpSirMacMgmtHdr mac_hdr = NULL;
int8_t rssi;
- uint32_t frame_len;
+ uint32_t frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
tpSirMacVendorSpecificFrameHdr vendor_specific;
uint8_t oui[] = { 0x00, 0x00, 0xf0 };
tpSirMacVendorSpecificPublicActionFrameHdr pub_action;
+ if (frame_len < sizeof(*action_hdr)) {
+ pe_debug("frame_len %d less than Action Frame Hdr size",
+ frame_len);
+ return;
+ }
+
#ifdef WLAN_FEATURE_11W
if (lim_is_robust_mgmt_action_frame(action_hdr->category) &&
lim_drop_unprotected_action_frame(mac_ctx, session,
@@ -1717,8 +1723,6 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
return;
#endif
- frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
-
switch (action_hdr->category) {
case SIR_MAC_ACTION_QOS_MGMT:
if ((session->limQosEnabled) ||
@@ -1911,10 +1915,14 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
case SIR_MAC_ACTION_VENDOR_SPECIFIC_CATEGORY:
vendor_specific = (tpSirMacVendorSpecificFrameHdr) action_hdr;
mac_hdr = NULL;
- frame_len = 0;
mac_hdr = WMA_GET_RX_MAC_HEADER(rx_pkt_info);
- frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
+
+ if (frame_len < sizeof(*vendor_specific)) {
+ pe_debug("frame len %d less than Vendor Specific Hdr len",
+ frame_len);
+ return;
+ }
/* Check if it is a vendor specific action frame. */
if (LIM_IS_STA_ROLE(session) &&
@@ -1950,7 +1958,12 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
}
break;
case SIR_MAC_ACTION_PUBLIC_USAGE:
+ mac_hdr = WMA_GET_RX_MAC_HEADER(rx_pkt_info);
switch (action_hdr->actionID) {
+ case SIR_MAC_ACTION_EXT_CHANNEL_SWITCH_ID:
+ lim_process_ext_channel_switch_action_frame(mac_ctx,
+ rx_pkt_info, session);
+ break;
case SIR_MAC_ACTION_VENDOR_SPECIFIC:
pub_action =
(tpSirMacVendorSpecificPublicActionFrameHdr)
@@ -1959,58 +1972,30 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
lim_process_action_vendor_specific(mac_ctx, rx_pkt_info,
pub_action, session);
break;
- /* Handle vendor specific action */
case SIR_MAC_ACTION_VENDOR_SPECIFIC_CATEGORY:
- {
- tpSirMacMgmtHdr header;
- uint32_t frame_len;
-
- header = WMA_GET_RX_MAC_HEADER(rx_pkt_info);
- frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
- lim_send_sme_mgmt_frame_ind(mac_ctx, header->fc.subType,
- (uint8_t *)header, frame_len + sizeof(tSirMacMgmtHdr), 0,
- WMA_GET_RX_CH(rx_pkt_info), NULL,
- WMA_GET_RX_RSSI_RAW(rx_pkt_info));
- break;
- }
-
case SIR_MAC_ACTION_2040_BSS_COEXISTENCE:
- mac_hdr = NULL;
- frame_len = 0;
-
- mac_hdr = WMA_GET_RX_MAC_HEADER(rx_pkt_info);
- frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
-
- lim_send_sme_mgmt_frame_ind(mac_ctx,
- mac_hdr->fc.subType,
- (uint8_t *) mac_hdr,
- frame_len + sizeof(tSirMacMgmtHdr),
- session->smeSessionId,
- WMA_GET_RX_CH(rx_pkt_info), session,
- WMA_GET_RX_RSSI_NORMALIZED(
- rx_pkt_info));
- break;
+ case SIR_MAC_ACTION_GAS_INITIAL_REQUEST:
+ case SIR_MAC_ACTION_GAS_INITIAL_RESPONSE:
+ case SIR_MAC_ACTION_GAS_COMEBACK_REQUEST:
+ case SIR_MAC_ACTION_GAS_COMEBACK_RESPONSE:
#ifdef FEATURE_WLAN_TDLS
case SIR_MAC_TDLS_DIS_RSP:
- mac_hdr = NULL;
- frame_len = 0;
-
- mac_hdr = WMA_GET_RX_MAC_HEADER(rx_pkt_info);
- frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
- rssi = WMA_GET_RX_RSSI_NORMALIZED(rx_pkt_info);
- pe_debug("Public Action TDLS Discovery RSP");
+#endif
+ /*
+ * Frame forwarded to SME to HDD to supplicant
+ * type is action
+ */
+ pe_debug("Public Action Frame %d received",
+ action_hdr->actionID);
lim_send_sme_mgmt_frame_ind(mac_ctx,
- mac_hdr->fc.subType, (uint8_t *) mac_hdr,
+ mac_hdr->fc.subType,
+ (uint8_t *) mac_hdr,
frame_len + sizeof(tSirMacMgmtHdr),
session->smeSessionId,
WMA_GET_RX_CH(rx_pkt_info), session,
WMA_GET_RX_RSSI_NORMALIZED(rx_pkt_info));
break;
-#endif
- case SIR_MAC_ACTION_EXT_CHANNEL_SWITCH_ID:
- lim_process_ext_channel_switch_action_frame(mac_ctx,
- rx_pkt_info, session);
- break;
+
default:
pe_warn("Unhandled public action frame: %x",
action_hdr->actionID);
@@ -2062,10 +2047,8 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
break;
case SIR_MAC_ACTION_FST: {
tpSirMacMgmtHdr hdr;
- uint32_t frame_len;
hdr = WMA_GET_RX_MAC_HEADER(rx_pkt_info);
- frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
pe_debug("Received FST MGMT action frame");
/* Forward to the SME to HDD */
@@ -2088,7 +2071,6 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
case SIR_MAC_PDPA_GAS_COMEBACK_REQ:
case SIR_MAC_PDPA_GAS_COMEBACK_RSP:
mac_hdr = WMA_GET_RX_MAC_HEADER(rx_pkt_info);
- frame_len = WMA_GET_RX_PAYLOAD_LEN(rx_pkt_info);
rssi = WMA_GET_RX_RSSI_NORMALIZED(rx_pkt_info);
lim_send_sme_mgmt_frame_ind(mac_ctx,
mac_hdr->fc.subType, (uint8_t *) mac_hdr,
@@ -2130,31 +2112,58 @@ void lim_process_action_frame(tpAniSirGlobal mac_ctx,
void lim_process_action_frame_no_session(tpAniSirGlobal pMac, uint8_t *pBd)
{
+ tpSirMacMgmtHdr mac_hdr = WMA_GET_RX_MAC_HEADER(pBd);
+ uint32_t frame_len = WMA_GET_RX_PAYLOAD_LEN(pBd);
uint8_t *pBody = WMA_GET_RX_MPDU_DATA(pBd);
- tpSirMacVendorSpecificPublicActionFrameHdr pActionHdr =
- (tpSirMacVendorSpecificPublicActionFrameHdr) pBody;
+ tpSirMacActionFrameHdr action_hdr = (tpSirMacActionFrameHdr) pBody;
+ tpSirMacVendorSpecificPublicActionFrameHdr vendor_specific;
pe_debug("Received a Action frame -- no session");
- switch (pActionHdr->category) {
+ if (frame_len < sizeof(*action_hdr)) {
+ pe_debug("frame_len %d less than action frame header len",
+ frame_len);
+ return;
+ }
+
+ switch (action_hdr->category) {
case SIR_MAC_ACTION_PUBLIC_USAGE:
- switch (pActionHdr->actionID) {
+ switch (action_hdr->actionID) {
case SIR_MAC_ACTION_VENDOR_SPECIFIC:
- {
+ vendor_specific =
+ (tpSirMacVendorSpecificPublicActionFrameHdr)
+ action_hdr;
lim_process_action_vendor_specific(pMac, pBd,
- pActionHdr, NULL);
- }
+ vendor_specific,
+ NULL);
+ break;
+ case SIR_MAC_ACTION_GAS_INITIAL_REQUEST:
+ case SIR_MAC_ACTION_GAS_INITIAL_RESPONSE:
+ case SIR_MAC_ACTION_GAS_COMEBACK_REQUEST:
+ case SIR_MAC_ACTION_GAS_COMEBACK_RESPONSE:
+ /*
+ * Frame forwarded to SME to HDD to supplicant
+ * type is action
+ */
+ pe_debug("Public Action Frame %d received",
+ action_hdr->actionID);
+ lim_send_sme_mgmt_frame_ind(pMac,
+ mac_hdr->fc.subType,
+ (uint8_t *) mac_hdr,
+ frame_len + sizeof(tSirMacMgmtHdr), 0,
+ WMA_GET_RX_CH(pBd), NULL,
+ WMA_GET_RX_RSSI_NORMALIZED(pBd));
+
break;
default:
pe_warn("Unhandled public action frame: %x",
- pActionHdr->actionID);
+ action_hdr->actionID);
break;
}
break;
default:
pe_warn("Unhandled action frame without session: %x",
- pActionHdr->category);
+ action_hdr->category);
break;
-
}
}
diff --git a/core/mac/src/pe/lim/lim_process_auth_frame.c b/core/mac/src/pe/lim/lim_process_auth_frame.c
index 829b217585..eea7cc96a0 100644
--- a/core/mac/src/pe/lim/lim_process_auth_frame.c
+++ b/core/mac/src/pe/lim/lim_process_auth_frame.c
@@ -106,12 +106,12 @@ static void lim_process_auth_shared_system_algo(tpAniSirGlobal mac_ctx,
tpSirMacMgmtHdr mac_hdr,
tSirMacAuthFrameBody *rx_auth_frm_body,
tSirMacAuthFrameBody *auth_frame,
- uint8_t *challenge_txt_arr,
tpPESession pe_session)
{
uint32_t val;
- uint8_t cfg_privacy_opt_imp, *challenge;
+ uint8_t cfg_privacy_opt_imp;
struct tLimPreAuthNode *auth_node;
+ uint8_t challenge_txt_arr[SIR_MAC_SAP_AUTH_CHALLENGE_LENGTH] = {0};
pe_debug("=======> eSIR_SHARED_KEY");
if (LIM_IS_AP_ROLE(pe_session))
@@ -192,19 +192,39 @@ static void lim_process_auth_shared_system_algo(tpAniSirGlobal mac_ctx,
lim_delete_pre_auth_node(mac_ctx, mac_hdr->sa);
return;
}
- lim_activate_auth_rsp_timer(mac_ctx, auth_node);
- auth_node->fTimerStarted = 1;
+
/*
* get random bytes and use as challenge text.
- * If it fails we already have random stack bytes.
*/
- if (!QDF_IS_STATUS_SUCCESS(cds_rand_get_bytes(0,
- (uint8_t *) challenge_txt_arr,
- SIR_MAC_SAP_AUTH_CHALLENGE_LENGTH)))
+ get_random_bytes(challenge_txt_arr,
+ SIR_MAC_SAP_AUTH_CHALLENGE_LENGTH);
+ qdf_mem_zero(auth_node->challengeText,
+ SIR_MAC_SAP_AUTH_CHALLENGE_LENGTH);
+ if (!qdf_mem_cmp(challenge_txt_arr,
+ auth_node->challengeText,
+ SIR_MAC_SAP_AUTH_CHALLENGE_LENGTH)) {
pe_err("Challenge text preparation failed");
- challenge = auth_node->challengeText;
- qdf_mem_copy(challenge, (uint8_t *)challenge_txt_arr,
- sizeof(challenge_txt_arr));
+ lim_print_mac_addr(mac_ctx, mac_hdr->sa, LOGW);
+ auth_frame->authAlgoNumber =
+ rx_auth_frm_body->authAlgoNumber;
+ auth_frame->authTransactionSeqNumber =
+ rx_auth_frm_body->authTransactionSeqNumber + 1;
+ auth_frame->authStatusCode = eSIR_MAC_TRY_AGAIN_LATER;
+ lim_send_auth_mgmt_frame(mac_ctx,
+ auth_frame,
+ mac_hdr->sa,
+ LIM_NO_WEP_IN_FC,
+ pe_session);
+ lim_delete_pre_auth_node(mac_ctx, mac_hdr->sa);
+ return;
+ }
+
+ lim_activate_auth_rsp_timer(mac_ctx, auth_node);
+ auth_node->fTimerStarted = 1;
+
+ qdf_mem_copy(auth_node->challengeText,
+ challenge_txt_arr,
+ sizeof(challenge_txt_arr));
/*
* Sending Authenticaton frame with challenge.
*/
@@ -273,7 +293,6 @@ static void lim_process_auth_frame_type1(tpAniSirGlobal mac_ctx,
{
tpDphHashNode sta_ds_ptr = NULL;
struct tLimPreAuthNode *auth_node;
- uint8_t challenge_txt_arr[SIR_MAC_SAP_AUTH_CHALLENGE_LENGTH];
uint32_t maxnum_preauth;
uint16_t associd = 0;
@@ -455,8 +474,7 @@ static void lim_process_auth_frame_type1(tpAniSirGlobal mac_ctx,
case eSIR_SHARED_KEY:
lim_process_auth_shared_system_algo(mac_ctx, mac_hdr,
- rx_auth_frm_body, auth_frame,
- challenge_txt_arr, pe_session);
+ rx_auth_frm_body, auth_frame, pe_session);
break;
default:
pe_err("rx Auth frm for unsupported auth algo %d "
diff --git a/core/mac/src/pe/lim/lim_process_deauth_frame.c b/core/mac/src/pe/lim/lim_process_deauth_frame.c
index 02837a61cf..7f654b5d0d 100644
--- a/core/mac/src/pe/lim/lim_process_deauth_frame.c
+++ b/core/mac/src/pe/lim/lim_process_deauth_frame.c
@@ -84,6 +84,11 @@ lim_process_deauth_frame(tpAniSirGlobal pMac, uint8_t *pRxPacketInfo,
pBody = WMA_GET_RX_MPDU_DATA(pRxPacketInfo);
frame_rssi = (int32_t)WMA_GET_RX_RSSI_NORMALIZED(pRxPacketInfo);
+ frameLen = WMA_GET_RX_PAYLOAD_LEN(pRxPacketInfo);
+ if (frameLen < sizeof(reasonCode)) {
+ pe_err("Deauth Frame length invalid %d", frameLen);
+ return ;
+ }
if (LIM_IS_STA_ROLE(psessionEntry) &&
((eLIM_SME_WT_DISASSOC_STATE == psessionEntry->limSmeState) ||
@@ -135,7 +140,6 @@ lim_process_deauth_frame(tpAniSirGlobal pMac, uint8_t *pRxPacketInfo,
/* If the frame received is unprotected, forward it to the supplicant to initiate */
/* an SA query */
- frameLen = WMA_GET_RX_PAYLOAD_LEN(pRxPacketInfo);
/* send the unprotected frame indication to SME */
lim_send_sme_unprotected_mgmt_frame_ind(pMac, pHdr->fc.subType,
diff --git a/core/mac/src/pe/lim/lim_send_sme_rsp_messages.c b/core/mac/src/pe/lim/lim_send_sme_rsp_messages.c
index 2aa5a3abd6..c0aa521e23 100644
--- a/core/mac/src/pe/lim/lim_send_sme_rsp_messages.c
+++ b/core/mac/src/pe/lim/lim_send_sme_rsp_messages.c
@@ -2214,6 +2214,12 @@ void lim_handle_csa_offload_msg(tpAniSirGlobal mac_ctx, tpSirMsgQ msg)
return;
}
+ csa_offload_ind = qdf_mem_malloc(sizeof(tSmeCsaOffloadInd));
+ if (NULL == csa_offload_ind) {
+ pe_err("memalloc fail eWNI_SME_CSA_OFFLOAD_EVENT");
+ goto err;
+ }
+
session_entry =
pe_find_session_by_bssid(mac_ctx,
csa_params->bssId, &session_id);
@@ -2409,12 +2415,15 @@ void lim_handle_csa_offload_msg(tpAniSirGlobal mac_ctx, tpSirMsgQ msg)
goto err;
}
+ if (CDS_IS_CHANNEL_24GHZ(csa_params->channel) &&
+ (session_entry->dot11mode == WNI_CFG_DOT11_MODE_11A))
+ session_entry->dot11mode = WNI_CFG_DOT11_MODE_11G;
+ else if (CDS_IS_CHANNEL_5GHZ(csa_params->channel) &&
+ ((session_entry->dot11mode == WNI_CFG_DOT11_MODE_11G) ||
+ (session_entry->dot11mode == WNI_CFG_DOT11_MODE_11G_ONLY)))
+ session_entry->dot11mode = WNI_CFG_DOT11_MODE_11A;
+
lim_prepare_for11h_channel_switch(mac_ctx, session_entry);
- csa_offload_ind = qdf_mem_malloc(sizeof(tSmeCsaOffloadInd));
- if (NULL == csa_offload_ind) {
- pe_err("memalloc fail eWNI_SME_CSA_OFFLOAD_EVENT");
- goto err;
- }
csa_offload_ind->mesgType = eWNI_SME_CSA_OFFLOAD_EVENT;
csa_offload_ind->mesgLen = sizeof(tSmeCsaOffloadInd);
diff --git a/core/mac/src/sys/legacy/src/utils/src/parser_api.c b/core/mac/src/sys/legacy/src/utils/src/parser_api.c
index de235ce52a..fe44364e91 100644
--- a/core/mac/src/sys/legacy/src/utils/src/parser_api.c
+++ b/core/mac/src/sys/legacy/src/utils/src/parser_api.c
@@ -3195,8 +3195,7 @@ sir_convert_assoc_resp_frame2_struct(tpAniSirGlobal pMac,
for (cnt = 0; cnt < ar->num_WMMTSPEC; cnt++) {
qdf_mem_copy(&pAssocRsp->TSPECInfo[cnt],
&ar->WMMTSPEC[cnt],
- (sizeof(tDot11fIEWMMTSPEC) *
- ar->num_WMMTSPEC));
+ sizeof(tDot11fIEWMMTSPEC));
}
pAssocRsp->tspecPresent = true;
}
diff --git a/core/sap/src/sap_ch_select.c b/core/sap/src/sap_ch_select.c
index f636f7199d..f8352dc541 100644
--- a/core/sap/src/sap_ch_select.c
+++ b/core/sap/src/sap_ch_select.c
@@ -1738,9 +1738,12 @@ static void sap_compute_spect_weight(tSapChSelSpectInfo *pSpectInfoParams,
*/
rssi = (int8_t) pSpectCh->rssiAgr;
- if (ch_in_pcl(sap_ctx, chn_num))
+ if (ch_in_pcl(sap_ctx, pSpectCh->chNum))
rssi -= PCL_RSSI_DISCOUNT;
+ if (rssi < SOFTAP_MIN_RSSI)
+ rssi = SOFTAP_MIN_RSSI;
+
if (pSpectCh->weight == SAP_ACS_WEIGHT_MAX)
goto debug_info;
@@ -1757,9 +1760,9 @@ static void sap_compute_spect_weight(tSapChSelSpectInfo *pSpectInfoParams,
debug_info:
/* ------ Debug Info ------ */
QDF_TRACE(QDF_MODULE_ID_SAP, QDF_TRACE_LEVEL_INFO_HIGH,
- "In %s, Chan=%d Weight= %d rssiAgr=%d bssCount=%d",
+ "In %s, Chan=%d Weight= %d rssiAgr=%d, rssi_pcl_discount: %d, bssCount=%d",
__func__, pSpectCh->chNum, pSpectCh->weight,
- pSpectCh->rssiAgr, pSpectCh->bssCount);
+ pSpectCh->rssiAgr, rssi, pSpectCh->bssCount);
/* ------ Debug Info ------ */
pSpectCh++;
}
diff --git a/core/sap/src/sap_module.c b/core/sap/src/sap_module.c
index 9e5c0aadb2..c759ed7a73 100644
--- a/core/sap/src/sap_module.c
+++ b/core/sap/src/sap_module.c
@@ -233,6 +233,11 @@ void wlansap_context_put(ptSapContext ctx)
for (i = 0; i < SAP_MAX_NUM_SESSION; i++) {
if (gp_sap_ctx[i] == ctx) {
if (qdf_atomic_dec_and_test(&sap_ctx_ref_count[i])) {
+ if (ctx->channelList) {
+ qdf_mem_free(ctx->channelList);
+ ctx->channelList = NULL;
+ ctx->num_of_channel = 0;
+ }
qdf_mem_free(ctx);
gp_sap_ctx[i] = NULL;
QDF_TRACE(QDF_MODULE_ID_SAP,
diff --git a/core/wma/src/wma_mgmt.c b/core/wma/src/wma_mgmt.c
index 32c79179fc..6fa8ea84e1 100644
--- a/core/wma/src/wma_mgmt.c
+++ b/core/wma/src/wma_mgmt.c
@@ -3664,6 +3664,9 @@ static int wma_mgmt_rx_process(void *handle, uint8_t *data,
qdf_nbuf_put_tail(wbuf, hdr->buf_len);
qdf_nbuf_set_protocol(wbuf, ETH_P_CONTROL);
wh = (struct ieee80211_frame *)qdf_nbuf_data(wbuf);
+ qdf_mem_zero(((uint8_t *)wh + hdr->buf_len), roundup(hdr->buf_len +
+ RESERVE_BYTES, 4) -
+ hdr->buf_len);
rx_pkt->pkt_meta.mpdu_hdr_ptr = qdf_nbuf_data(wbuf);
rx_pkt->pkt_meta.mpdu_data_ptr = rx_pkt->pkt_meta.mpdu_hdr_ptr +
diff --git a/core/wma/src/wma_nan_datapath.c b/core/wma/src/wma_nan_datapath.c
index 720b627008..56b3e1fe95 100644
--- a/core/wma/src/wma_nan_datapath.c
+++ b/core/wma/src/wma_nan_datapath.c
@@ -464,6 +464,7 @@ static int wma_ndp_indication_event_handler(void *handle, uint8_t *event_info,
wmi_ndp_indication_event_fixed_param *fixed_params;
struct ndp_indication_event ind_event = {0};
tp_wma_handle wma_handle = handle;
+ size_t total_array_len;
event = (WMI_NDP_INDICATION_EVENTID_param_tlvs *)event_info;
fixed_params =
@@ -482,6 +483,38 @@ static int wma_ndp_indication_event_handler(void *handle, uint8_t *event_info,
return -EINVAL;
}
+ if (fixed_params->nan_scid_len > event->num_ndp_scid) {
+ WMA_LOGE(FL("Invalid nan_scid_len: %d"),
+ fixed_params->nan_scid_len);
+ return -EINVAL;
+ }
+
+ if (fixed_params->ndp_cfg_len >
+ (WMI_SVC_MSG_MAX_SIZE - sizeof(*fixed_params))) {
+ WMA_LOGE("%s: excess wmi buffer: ndp_cfg_len %d",
+ __func__, fixed_params->ndp_cfg_len);
+ return -EINVAL;
+ }
+
+ total_array_len = fixed_params->ndp_cfg_len +
+ sizeof(*fixed_params);
+
+ if (fixed_params->ndp_app_info_len >
+ (WMI_SVC_MSG_MAX_SIZE - total_array_len)) {
+ WMA_LOGE("%s: excess wmi buffer: ndp_cfg_len %d",
+ __func__, fixed_params->ndp_app_info_len);
+ return -EINVAL;
+ }
+
+ total_array_len += fixed_params->ndp_app_info_len;
+
+ if (fixed_params->nan_scid_len >
+ (WMI_SVC_MSG_MAX_SIZE - total_array_len)) {
+ WMA_LOGE("%s: excess wmi buffer: ndp_cfg_len %d",
+ __func__, fixed_params->nan_scid_len);
+ return -EINVAL;
+ }
+
ind_event.vdev_id = fixed_params->vdev_id;
ind_event.service_instance_id = fixed_params->service_instance_id;
ind_event.ndp_instance_id = fixed_params->ndp_instance_id;
@@ -517,15 +550,6 @@ static int wma_ndp_indication_event_handler(void *handle, uint8_t *event_info,
ind_event.ncs_sk_type = fixed_params->nan_csid;
ind_event.scid.scid_len = fixed_params->nan_scid_len;
- if (fixed_params->ndp_cfg_len > event->num_ndp_cfg ||
- fixed_params->ndp_app_info_len > event->num_ndp_app_info ||
- fixed_params->nan_scid_len > event->num_ndp_scid) {
- WMA_LOGD(FL("Invalid ndp_cfg_len: %d, ndp_app_info_len: %d, nan_scid_len: %d"),
- fixed_params->ndp_cfg_len,
- fixed_params->ndp_app_info_len,
- fixed_params->nan_scid_len);
- return -EINVAL;
- }
if (ind_event.ndp_config.ndp_cfg_len) {
ind_event.ndp_config.ndp_cfg =
qdf_mem_malloc(fixed_params->ndp_cfg_len);
diff --git a/core/wma/src/wma_utils.c b/core/wma/src/wma_utils.c
index 7bfa295e4a..c201226a70 100644
--- a/core/wma/src/wma_utils.c
+++ b/core/wma/src/wma_utils.c
@@ -1349,7 +1349,7 @@ static int wma_unified_link_peer_stats_event_handler(void *handle,
} while (0);
if (excess_data ||
- (sizeof(*fixed_param) > WMI_SVC_MSG_MAX_SIZE - buf_len)) {
+ (buf_len > WMI_SVC_MSG_MAX_SIZE - sizeof(*fixed_param))) {
WMA_LOGE("excess wmi buffer: rates:%d, peers:%d",
peer_stats->num_rates, fixed_param->num_peers);
return -EINVAL;
@@ -3186,7 +3186,7 @@ int wma_stats_event_handler(void *handle, uint8_t *cmd_param_info,
} while (0);
if (excess_data ||
- (sizeof(*event) > WMI_SVC_MSG_MAX_SIZE - buf_len)) {
+ (buf_len > WMI_SVC_MSG_MAX_SIZE - sizeof(*event))) {
WMA_LOGE("excess wmi buffer: stats pdev %d vdev %d peer %d",
event->num_pdev_stats, event->num_vdev_stats,
event->num_peer_stats);