qcacld-3.0: Implement DP component for FISA feature

Add FISA feature support for DP componentization.

Change-Id: I748a20ec44d1c299aab8d31facd059eb2e35e680
CRs-Fixed: 3243693
This commit is contained in:
Azmath Mohammed
2022-09-19 15:05:13 +05:30
committed by Madan Koyyalamudi
parent 26a3f0c700
commit aacfd1d3d0
8 changed files with 137 additions and 141 deletions

View File

@@ -55,6 +55,17 @@
*/
uint32_t wlan_dp_intf_get_pkt_type_bitmap_value(void *intf_ctx);
#if defined(WLAN_SUPPORT_RX_FISA)
/**
* dp_rx_skip_fisa() - Set flags to skip fisa aggregation
* @cdp_soc: core txrx main context
* @value: allow or skip fisa
*
* Return: None
*/
void dp_rx_skip_fisa(struct cdp_soc_t *cdp_soc, uint32_t value);
#endif
/**
* dp_reset_all_intfs_connectivity_stats() - reset connectivity stats
* @dp_ctx: pointer to DP Context

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,158 @@
/*
* Copyright (c) 2020-2021, The Linux Foundation. All rights reserved.
* Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include <dp_types.h>
#include <qdf_status.h>
//#define FISA_DEBUG_ENABLE
#ifdef FISA_DEBUG_ENABLE
#define dp_fisa_debug dp_info
#else
#define dp_fisa_debug(params...)
#endif
#if defined(WLAN_SUPPORT_RX_FISA)
#define FSE_CACHE_FLUSH_TIME_OUT 5 /* milliSeconds */
#define FISA_UDP_MAX_DATA_LEN 1470 /* udp max data length */
#define FISA_UDP_HDR_LEN 8 /* udp header length */
/* single packet max cumulative ip length */
#define FISA_MAX_SINGLE_CUMULATIVE_IP_LEN \
(FISA_UDP_MAX_DATA_LEN + FISA_UDP_HDR_LEN)
/* max flow cumulative ip length */
#define FISA_FLOW_MAX_CUMULATIVE_IP_LEN \
(FISA_MAX_SINGLE_CUMULATIVE_IP_LEN * FISA_FLOW_MAX_AGGR_COUNT)
#define IPSEC_PORT 500
#define IPSEC_NAT_PORT 4500
#define DNS_SERVER_PORT 53
#define DP_FT_LOCK_MAX_RECORDS 32
struct dp_fisa_rx_fst_update_elem {
/* Do not add new entries here */
qdf_list_node_t node;
struct cdp_rx_flow_tuple_info flow_tuple_info;
struct dp_vdev *vdev;
uint32_t flow_idx;
uint32_t reo_dest_indication;
bool is_tcp_flow;
bool is_udp_flow;
u8 reo_id;
};
enum dp_ft_lock_event_type {
DP_FT_LOCK_EVENT,
DP_FT_UNLOCK_EVENT,
};
struct dp_ft_lock_record {
const char *func;
int cpu_id;
uint64_t timestamp;
enum dp_ft_lock_event_type type;
};
struct dp_ft_lock_history {
uint32_t record_idx;
struct dp_ft_lock_record ft_lock_rec[DP_FT_LOCK_MAX_RECORDS];
};
/**
* dp_rx_dump_fisa_stats() - Dump fisa stats
* @soc: core txrx main context
*
* Return: QDF_STATUS
*/
QDF_STATUS dp_rx_dump_fisa_stats(struct dp_soc *soc);
/**
* dp_fisa_rx() - FISA Rx packet delivery entry function
* @soc: core txrx main context
* @vdev: core txrx vdev
* @nbuf_list: Delivery list of nbufs
*
* Return: QDF_STATUS
*/
QDF_STATUS dp_fisa_rx(struct dp_soc *dp_fisa_rx_hdl, struct dp_vdev *vdev,
qdf_nbuf_t nbuf_list);
/**
* dp_rx_fisa_flush_by_ctx_id() - FISA Rx flush function to flush
* aggregation at end of NAPI
* @soc: core txrx main context
* @napi_id: Flows which are rxed on the NAPI ID to be flushed
*
* Return: QDF_STATUS
*/
QDF_STATUS dp_rx_fisa_flush_by_ctx_id(struct dp_soc *soc, int napi_id);
/**
* dp_rx_fisa_flush_by_vdev_id() - Flush fisa aggregates per vdev id
* @soc: core txrx main context
* @vdev_id: vdev ID
*
* Return: Success on flushing the flows for the vdev
*/
QDF_STATUS dp_rx_fisa_flush_by_vdev_id(struct dp_soc *soc, uint8_t vdev_id);
/**
* dp_set_fisa_disallowed_for_vdev() - Set fisa disallowed flag for vdev
* @cdp_soc: core txrx main context
* @vdev_id: Vdev id
* @rx_ctx_id: rx context id
* @val: value to be set
*
* Return: None
*/
void dp_set_fisa_disallowed_for_vdev(struct cdp_soc_t *cdp_soc, uint8_t vdev_id,
uint8_t rx_ctx_id, uint8_t val);
/**
* dp_fisa_rx_fst_update_work() - Work functions for FST updates
* @arg: argument passed to the work function
*
* Return: None
*/
void dp_fisa_rx_fst_update_work(void *arg);
/**
* dp_suspend_fse_cache_flush() - Suspend FSE cache flush
* @soc: core txrx main context
*
* Return: None
*/
void dp_suspend_fse_cache_flush(struct dp_soc *soc);
/**
* dp_resume_fse_cache_flush() - Resume FSE cache flush
* @soc: core txrx main context
*
* Return: None
*/
void dp_resume_fse_cache_flush(struct dp_soc *soc);
#else
static QDF_STATUS dp_rx_dump_fisa_stats(struct dp_soc *soc)
{
return QDF_STATUS_SUCCESS;
}
void dp_rx_dump_fisa_table(struct dp_soc *soc)
{
}
#endif

View File

@@ -0,0 +1,554 @@
/*
* Copyright (c) 2021, The Linux Foundation. All rights reserved.
* Copyright (c) 2021-2022 Qualcomm Innovation Center, Inc. All rights reserved.
*
* Permission to use, copy, modify, and/or distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include "dp_types.h"
#include "qdf_mem.h"
#include "qdf_nbuf.h"
#include "cfg_dp.h"
#include "wlan_cfg.h"
#include "dp_types.h"
#include "hal_rx_flow.h"
#include "dp_htt.h"
#include "dp_internal.h"
#include "hif.h"
#include "dp_txrx.h"
/* Timeout in milliseconds to wait for CMEM FST HTT response */
#define DP_RX_FST_CMEM_RESP_TIMEOUT 2000
#define INVALID_NAPI 0Xff
#ifdef WLAN_SUPPORT_RX_FISA
void dp_fisa_rx_fst_update_work(void *arg);
void dp_rx_dump_fisa_table(struct dp_soc *soc)
{
struct wlan_cfg_dp_soc_ctxt *cfg = soc->wlan_cfg_ctx;
hal_soc_handle_t hal_soc_hdl = soc->hal_soc;
struct dp_rx_fst *fst = soc->rx_fst;
struct dp_fisa_rx_sw_ft *sw_ft_entry;
int i;
/* Check if it is enabled in the INI */
if (!wlan_cfg_is_rx_fisa_enabled(cfg)) {
dp_err("RX FISA feature is disabled");
return;
}
if (!fst->fst_in_cmem)
return hal_rx_dump_fse_table(soc->rx_fst->hal_rx_fst);
sw_ft_entry = (struct dp_fisa_rx_sw_ft *)fst->base;
if (hif_force_wake_request(((struct hal_soc *)hal_soc_hdl)->hif_handle)) {
dp_err("Wake up request failed");
qdf_check_state_before_panic(__func__, __LINE__);
return;
}
for (i = 0; i < fst->max_entries; i++)
hal_rx_dump_cmem_fse(hal_soc_hdl,
sw_ft_entry[i].cmem_offset, i);
if (hif_force_wake_release(((struct hal_soc *)hal_soc_hdl)->hif_handle)) {
dp_err("Wake up release failed");
qdf_check_state_before_panic(__func__, __LINE__);
return;
}
}
void dp_print_fisa_stats(struct dp_soc *soc)
{
struct wlan_cfg_dp_soc_ctxt *cfg = soc->wlan_cfg_ctx;
struct dp_rx_fst *fst = soc->rx_fst;
/* Check if it is enabled in the INI */
if (!wlan_cfg_is_rx_fisa_enabled(cfg))
return;
dp_info("invalid flow index: %u", fst->stats.invalid_flow_index);
dp_info("reo_mismatch: cce_match: %u",
fst->stats.reo_mismatch.allow_cce_match);
dp_info("reo_mismatch: allow_fse_metdata_mismatch: %u",
fst->stats.reo_mismatch.allow_fse_metdata_mismatch);
dp_info("reo_mismatch: allow_non_aggr: %u",
fst->stats.reo_mismatch.allow_non_aggr);
}
/**
* dp_rx_flow_send_htt_operation_cmd() - Invalidate FSE cache on FT change
* @pdev: handle to DP pdev
* @fse_op: Cache operation code
* @rx_flow_tuple: flow tuple whose entry has to be invalidated
*
* Return: Success if we successfully send FW HTT command
*/
static QDF_STATUS
dp_rx_flow_send_htt_operation_cmd(struct dp_pdev *pdev,
enum dp_htt_flow_fst_operation fse_op,
struct cdp_rx_flow_tuple_info *rx_flow_tuple)
{
struct dp_htt_rx_flow_fst_operation fse_op_cmd;
struct cdp_rx_flow_info rx_flow_info;
rx_flow_info.is_addr_ipv4 = true;
rx_flow_info.op_code = CDP_FLOW_FST_ENTRY_ADD;
qdf_mem_copy(&rx_flow_info.flow_tuple_info, rx_flow_tuple,
sizeof(struct cdp_rx_flow_tuple_info));
rx_flow_info.fse_metadata = 0xDADA;
fse_op_cmd.pdev_id = pdev->pdev_id;
fse_op_cmd.op_code = fse_op;
fse_op_cmd.rx_flow = &rx_flow_info;
return dp_htt_rx_flow_fse_operation(pdev, &fse_op_cmd);
}
/**
* dp_fisa_fse_cache_flush_timer() - FSE cache flush timeout handler
* @arg: SoC handle
*
* Return: None
*/
static void dp_fisa_fse_cache_flush_timer(void *arg)
{
struct dp_soc *soc = (struct dp_soc *)arg;
struct dp_rx_fst *fisa_hdl = soc->rx_fst;
struct cdp_rx_flow_tuple_info rx_flow_tuple_info = { 0 };
static uint32_t fse_cache_flush_rec_idx;
struct fse_cache_flush_history *fse_cache_flush_rec;
QDF_STATUS status;
if (!fisa_hdl)
return;
if (fisa_hdl->pm_suspended) {
qdf_atomic_set(&fisa_hdl->fse_cache_flush_posted, 0);
return;
}
fse_cache_flush_rec = &fisa_hdl->cache_fl_rec[fse_cache_flush_rec_idx %
MAX_FSE_CACHE_FL_HST];
fse_cache_flush_rec->timestamp = qdf_get_log_timestamp();
fse_cache_flush_rec->flows_added =
qdf_atomic_read(&fisa_hdl->fse_cache_flush_posted);
fse_cache_flush_rec_idx++;
dp_info("FSE cache flush for %d flows",
fse_cache_flush_rec->flows_added);
status =
dp_rx_flow_send_htt_operation_cmd(soc->pdev_list[0],
DP_HTT_FST_CACHE_INVALIDATE_FULL,
&rx_flow_tuple_info);
if (QDF_IS_STATUS_ERROR(status)) {
dp_err("Failed to send the cache invalidation\n");
/*
* Not big impact cache entry gets updated later
*/
}
qdf_atomic_set(&fisa_hdl->fse_cache_flush_posted, 0);
}
/**
* dp_rx_fst_cmem_deinit() - De-initialize CMEM parameters
* @fst: Pointer to DP FST
*
* Return: None
*/
static void dp_rx_fst_cmem_deinit(struct dp_rx_fst *fst)
{
struct dp_fisa_rx_fst_update_elem *elem;
qdf_list_node_t *node;
int i;
qdf_cancel_work(&fst->fst_update_work);
qdf_flush_work(&fst->fst_update_work);
qdf_flush_workqueue(0, fst->fst_update_wq);
qdf_destroy_workqueue(0, fst->fst_update_wq);
qdf_spin_lock_bh(&fst->dp_rx_fst_lock);
while (qdf_list_peek_front(&fst->fst_update_list, &node) ==
QDF_STATUS_SUCCESS) {
elem = (struct dp_fisa_rx_fst_update_elem *)node;
qdf_list_remove_front(&fst->fst_update_list, &node);
qdf_mem_free(elem);
}
qdf_spin_unlock_bh(&fst->dp_rx_fst_lock);
qdf_list_destroy(&fst->fst_update_list);
qdf_event_destroy(&fst->cmem_resp_event);
for (i = 0; i < MAX_REO_DEST_RINGS; i++)
qdf_spinlock_destroy(&fst->dp_rx_sw_ft_lock[i]);
}
/**
* dp_rx_fst_cmem_init() - Initialize CMEM parameters
* @fst: Pointer to DP FST
*
* Return: Success/Failure
*/
static QDF_STATUS dp_rx_fst_cmem_init(struct dp_rx_fst *fst)
{
int i;
fst->fst_update_wq =
qdf_alloc_high_prior_ordered_workqueue("dp_rx_fst_update_wq");
if (!fst->fst_update_wq) {
dp_err("failed to allocate fst update wq\n");
return QDF_STATUS_E_FAILURE;
}
qdf_create_work(0, &fst->fst_update_work,
dp_fisa_rx_fst_update_work, fst);
qdf_list_create(&fst->fst_update_list, 128);
qdf_event_create(&fst->cmem_resp_event);
for (i = 0; i < MAX_REO_DEST_RINGS; i++)
qdf_spinlock_create(&fst->dp_rx_sw_ft_lock[i]);
return QDF_STATUS_SUCCESS;
}
#ifdef WLAN_SUPPORT_RX_FISA_HIST
static
QDF_STATUS dp_rx_sw_ft_hist_init(struct dp_fisa_rx_sw_ft *sw_ft,
uint32_t max_entries,
uint32_t rx_pkt_tlv_size)
{
int i;
QDF_STATUS qdf_status = QDF_STATUS_SUCCESS;
for (i = 0; i < max_entries; i++) {
sw_ft[i].pkt_hist.tlv_hist =
(uint8_t *)qdf_mem_malloc(rx_pkt_tlv_size *
FISA_FLOW_MAX_AGGR_COUNT);
if (!sw_ft[i].pkt_hist.tlv_hist) {
dp_err("unable to allocate tlv history");
qdf_status = QDF_STATUS_E_NOMEM;
break;
}
}
return qdf_status;
}
static void dp_rx_sw_ft_hist_deinit(struct dp_fisa_rx_sw_ft *sw_ft,
uint32_t max_entries)
{
int i;
for (i = 0; i < max_entries; i++) {
if (sw_ft[i].pkt_hist.tlv_hist)
qdf_mem_free(sw_ft[i].pkt_hist.tlv_hist);
}
}
#else
static
QDF_STATUS dp_rx_sw_ft_hist_init(struct dp_fisa_rx_sw_ft *sw_ft,
uint32_t max_entries,
uint32_t rx_pkt_tlv_size)
{
return QDF_STATUS_SUCCESS;
}
static void dp_rx_sw_ft_hist_deinit(struct dp_fisa_rx_sw_ft *sw_ft,
uint32_t max_entries)
{
}
#endif
/**
* dp_rx_fst_attach() - Initialize Rx FST and setup necessary parameters
* @soc: SoC handle
* @pdev: Pdev handle
*
* Return: Handle to flow search table entry
*/
QDF_STATUS dp_rx_fst_attach(struct dp_soc *soc, struct dp_pdev *pdev)
{
struct dp_rx_fst *fst;
struct dp_fisa_rx_sw_ft *ft_entry;
uint8_t *hash_key;
struct wlan_cfg_dp_soc_ctxt *cfg = soc->wlan_cfg_ctx;
int i = 0;
QDF_STATUS status;
/* Check if it is enabled in the INI */
if (!wlan_cfg_is_rx_fisa_enabled(cfg)) {
dp_err("RX FISA feature is disabled");
return QDF_STATUS_E_NOSUPPORT;
}
#ifdef NOT_YET /* Not required for now */
/* Check if FW supports */
if (!wlan_psoc_nif_fw_ext_cap_get((void *)pdev->ctrl_pdev,
WLAN_SOC_CEXT_RX_FSE_SUPPORT)) {
QDF_TRACE(QDF_MODULE_ID_ANY, QDF_TRACE_LEVEL_ERROR,
"rx fse disabled in FW\n");
wlan_cfg_set_rx_flow_tag_enabled(cfg, false);
return QDF_STATUS_E_NOSUPPORT;
}
#endif
if (soc->rx_fst) {
QDF_TRACE(QDF_MODULE_ID_ANY, QDF_TRACE_LEVEL_ERROR,
"RX FST already allocated\n");
return QDF_STATUS_SUCCESS;
}
fst = qdf_mem_malloc(sizeof(struct dp_rx_fst));
if (!fst)
return QDF_STATUS_E_NOMEM;
fst->max_skid_length = wlan_cfg_rx_fst_get_max_search(cfg);
fst->max_entries = wlan_cfg_get_rx_flow_search_table_size(cfg);
hash_key = wlan_cfg_rx_fst_get_hash_key(cfg);
fst->hash_mask = fst->max_entries - 1;
fst->num_entries = 0;
dp_err("FST setup params FT size %d, hash_mask 0x%x, skid_length %d",
fst->max_entries, fst->hash_mask, fst->max_skid_length);
/* Allocate the software flowtable */
fst->base = (uint8_t *)dp_context_alloc_mem(soc, DP_FISA_RX_FT_TYPE,
DP_RX_GET_SW_FT_ENTRY_SIZE * fst->max_entries);
if (!fst->base)
goto free_rx_fst;
ft_entry = (struct dp_fisa_rx_sw_ft *)fst->base;
for (i = 0; i < fst->max_entries; i++)
ft_entry[i].napi_id = INVALID_NAPI;
status = dp_rx_sw_ft_hist_init(ft_entry, fst->max_entries,
soc->rx_pkt_tlv_size);
if (QDF_IS_STATUS_ERROR(status))
goto free_hist;
fst->hal_rx_fst = hal_rx_fst_attach(soc->hal_soc,
soc->osdev,
&fst->hal_rx_fst_base_paddr,
fst->max_entries,
fst->max_skid_length, hash_key,
soc->fst_cmem_base);
if (qdf_unlikely(!fst->hal_rx_fst)) {
QDF_TRACE(QDF_MODULE_ID_ANY, QDF_TRACE_LEVEL_ERROR,
"Rx Hal fst allocation failed, #entries:%d\n",
fst->max_entries);
goto free_hist;
}
qdf_spinlock_create(&fst->dp_rx_fst_lock);
status = qdf_timer_init(soc->osdev, &fst->fse_cache_flush_timer,
dp_fisa_fse_cache_flush_timer, (void *)soc,
QDF_TIMER_TYPE_WAKE_APPS);
if (QDF_IS_STATUS_ERROR(status)) {
QDF_TRACE(QDF_MODULE_ID_ANY, QDF_TRACE_LEVEL_ERROR,
"Failed to init cache_flush_timer\n");
goto timer_init_fail;
}
qdf_atomic_init(&fst->fse_cache_flush_posted);
fst->fse_cache_flush_allow = true;
fst->soc_hdl = soc;
soc->rx_fst = fst;
soc->fisa_enable = true;
soc->fisa_lru_del_enable = wlan_cfg_is_rx_fisa_lru_del_enabled(cfg);
qdf_atomic_init(&soc->skip_fisa_param.skip_fisa);
QDF_TRACE(QDF_MODULE_ID_ANY, QDF_TRACE_LEVEL_ERROR,
"Rx FST attach successful, #entries:%d\n",
fst->max_entries);
return QDF_STATUS_SUCCESS;
timer_init_fail:
qdf_spinlock_destroy(&fst->dp_rx_fst_lock);
hal_rx_fst_detach(soc->hal_soc, fst->hal_rx_fst, soc->osdev,
soc->fst_cmem_base);
free_hist:
dp_rx_sw_ft_hist_deinit((struct dp_fisa_rx_sw_ft *)fst->base,
fst->max_entries);
dp_context_free_mem(soc, DP_FISA_RX_FT_TYPE, fst->base);
free_rx_fst:
qdf_mem_free(fst);
return QDF_STATUS_E_NOMEM;
}
/**
* dp_rx_fst_check_cmem_support() - Check if FW can allocate FSE in CMEM,
* allocate FSE in DDR if FW doesn't support CMEM allocation
* @soc: DP SoC handle
*
* Return: None
*/
static void dp_rx_fst_check_cmem_support(struct dp_soc *soc)
{
struct dp_rx_fst *fst = soc->rx_fst;
QDF_STATUS status;
/**
* FW doesn't support CMEM FSE, keep it in DDR
* soc->fst_cmem_base is non-NULL then CMEM support is already present
*/
if (!soc->fst_in_cmem && (soc->fst_cmem_base == 0))
return;
status = dp_rx_fst_cmem_init(fst);
if (status != QDF_STATUS_SUCCESS)
return;
hal_rx_fst_detach(soc->hal_soc, fst->hal_rx_fst, soc->osdev,
soc->fst_cmem_base);
fst->hal_rx_fst = NULL;
fst->hal_rx_fst_base_paddr = 0;
fst->flow_deletion_supported = true;
fst->fst_in_cmem = true;
}
/**
* dp_rx_flow_send_fst_fw_setup() - Program FST parameters in FW/HW post-attach
* @soc: SoC handle
* @pdev: Pdev handle
*
* Return: Success when fst parameters are programmed in FW, error otherwise
*/
QDF_STATUS dp_rx_flow_send_fst_fw_setup(struct dp_soc *soc,
struct dp_pdev *pdev)
{
struct dp_htt_rx_flow_fst_setup fisa_hw_fst_setup_cmd = {0};
struct dp_rx_fst *fst = soc->rx_fst;
struct wlan_cfg_dp_soc_ctxt *cfg = soc->wlan_cfg_ctx;
QDF_STATUS status;
/* check if FW has support to place FST in CMEM */
dp_rx_fst_check_cmem_support(soc);
/* mac_id = 0 is used to configure both macs with same FT */
fisa_hw_fst_setup_cmd.pdev_id = 0;
fisa_hw_fst_setup_cmd.max_entries = fst->max_entries;
fisa_hw_fst_setup_cmd.max_search = fst->max_skid_length;
if (soc->fst_cmem_base) {
fisa_hw_fst_setup_cmd.base_addr_lo =
soc->fst_cmem_base & 0xffffffff;
/* Higher order bits are mostly 0, Always use 0x10 */
fisa_hw_fst_setup_cmd.base_addr_hi =
(soc->fst_cmem_base >> 32) | 0x10;
dp_info("cmem base address 0x%llx\n", soc->fst_cmem_base);
} else {
fisa_hw_fst_setup_cmd.base_addr_lo =
fst->hal_rx_fst_base_paddr & 0xffffffff;
fisa_hw_fst_setup_cmd.base_addr_hi =
(fst->hal_rx_fst_base_paddr >> 32);
}
fisa_hw_fst_setup_cmd.ip_da_sa_prefix = HTT_RX_IPV4_COMPATIBLE_IPV6;
fisa_hw_fst_setup_cmd.hash_key_len = HAL_FST_HASH_KEY_SIZE_BYTES;
fisa_hw_fst_setup_cmd.hash_key = wlan_cfg_rx_fst_get_hash_key(cfg);
status = dp_htt_rx_flow_fst_setup(pdev, &fisa_hw_fst_setup_cmd);
if (!fst->fst_in_cmem || soc->fst_cmem_base) {
/**
* Return from here if fst_cmem is not enabled or cmem address
* is known at init time
*/
return status;
}
status = qdf_wait_single_event(&fst->cmem_resp_event,
DP_RX_FST_CMEM_RESP_TIMEOUT);
dp_err("FST params after CMEM update FT size %d, hash_mask 0x%x",
fst->max_entries, fst->hash_mask);
return status;
}
/**
* dp_rx_fst_detach() - De-initialize Rx FST
* @soc: SoC handle
* @pdev: Pdev handle
*
* Return: None
*/
void dp_rx_fst_detach(struct dp_soc *soc, struct dp_pdev *pdev)
{
struct dp_rx_fst *dp_fst;
dp_fst = soc->rx_fst;
if (qdf_likely(dp_fst)) {
qdf_timer_sync_cancel(&dp_fst->fse_cache_flush_timer);
if (dp_fst->fst_in_cmem)
dp_rx_fst_cmem_deinit(dp_fst);
else
hal_rx_fst_detach(soc->hal_soc, dp_fst->hal_rx_fst,
soc->osdev, soc->fst_cmem_base);
dp_rx_sw_ft_hist_deinit((struct dp_fisa_rx_sw_ft *)dp_fst->base,
dp_fst->max_entries);
dp_context_free_mem(soc, DP_FISA_RX_FT_TYPE, dp_fst->base);
qdf_spinlock_destroy(&dp_fst->dp_rx_fst_lock);
qdf_mem_free(dp_fst);
}
soc->rx_fst = NULL;
QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG,
"Rx FST detached\n");
}
/*
* dp_rx_fst_update_cmem_params() - Update CMEM FST params
* @soc: DP SoC context
* @num_entries: Number of flow search entries
* @cmem_ba_lo: CMEM base address low
* @cmem_ba_hi: CMEM base address high
*
* Return: None
*/
void dp_rx_fst_update_cmem_params(struct dp_soc *soc, uint16_t num_entries,
uint32_t cmem_ba_lo, uint32_t cmem_ba_hi)
{
struct dp_rx_fst *fst = soc->rx_fst;
fst->max_entries = num_entries;
fst->hash_mask = fst->max_entries - 1;
fst->cmem_ba = cmem_ba_lo;
/* Address is not NULL then address is already known during init */
if (soc->fst_cmem_base == 0)
qdf_event_set(&fst->cmem_resp_event);
}
void dp_rx_fst_update_pm_suspend_status(struct dp_soc *soc, bool suspended)
{
struct dp_rx_fst *fst = soc->rx_fst;
if (!fst)
return;
fst->pm_suspended = suspended;
}
#else /* WLAN_SUPPORT_RX_FISA */
#endif /* !WLAN_SUPPORT_RX_FISA */

View File

@@ -32,7 +32,7 @@
#include <cdp_txrx_flow_ctrl_v2.h>
#include "dp_txrx.h"
#if defined(WLAN_SUPPORT_RX_FISA)
#include "dp_fisa_rx.h"
#include "wlan_dp_fisa_rx.h"
#endif
#include "nan_public_structs.h"
#include "nan_ucfg_api.h"
@@ -56,6 +56,15 @@ uint32_t wlan_dp_intf_get_pkt_type_bitmap_value(void *intf_ctx)
return dp_intf->pkt_type_bitmap;
}
#if defined(WLAN_SUPPORT_RX_FISA)
void dp_rx_skip_fisa(struct cdp_soc_t *cdp_soc, uint32_t value)
{
struct dp_soc *soc = (struct dp_soc *)cdp_soc;
qdf_atomic_set(&soc->skip_fisa_param.skip_fisa, !value);
}
#endif
#ifdef QCA_LL_LEGACY_TX_FLOW_CONTROL
void dp_get_tx_resource(struct wlan_dp_intf *dp_intf,
struct qdf_mac_addr *mac_addr)

View File

@@ -1232,6 +1232,22 @@ void
dp_ucfg_disable_link_monitoring(struct wlan_objmgr_psoc *psoc,
struct wlan_objmgr_vdev *vdev);
#if defined(WLAN_SUPPORT_RX_FISA)
/**
* ucfg_dp_rx_skip_fisa() - Set flags to skip fisa aggregation
* @value: allow or skip fisa
*
* Return: None
*/
void ucfg_dp_rx_skip_fisa(uint32_t value);
#else
static inline
void ucfg_dp_rx_skip_fisa(uint32_t value)
{
}
#endif
#ifdef DP_TRAFFIC_END_INDICATION
/**
* ucfg_dp_traffic_end_indication_get() - Get data end indication info

View File

@@ -2311,5 +2311,16 @@ void ucfg_dp_prealloc_put_consistent_mem_unaligned(void *va_unaligned)
{
dp_prealloc_put_consistent_mem_unaligned(va_unaligned);
}
#endif
#if defined(WLAN_SUPPORT_RX_FISA)
void ucfg_dp_rx_skip_fisa(uint32_t value)
{
void *dp_soc;
dp_soc = cds_get_context(QDF_MODULE_ID_SOC);
if (dp_soc)
dp_rx_skip_fisa(dp_soc, value);
}
#endif