drivers: wifi: Create dedicated mem pool for Wi-Fi driver

Create dedicated memory pools for Wi-Fi management and
data operations (defaults: 20KB for management and 130KB for data).
Setting Data pool to 110KB for non-Nordic SOCs to resolve
RAM overflows seen in twister runs.

Remove the `HEAP_MEM_POOL_ADD_SIZE_NRF70` hint since we are
creating separate heaps for driver and not allocating from
system heap.

Signed-off-by: Ravi Dondaputi <ravi.dondaputi@nordicsemi.no>
This commit is contained in:
Ravi Dondaputi 2024-04-29 22:46:24 +05:30 committed by Carles Cufí
commit aa0cb68c6f
8 changed files with 144 additions and 52 deletions

View file

@ -66,12 +66,6 @@ endchoice
config NET_L2_ETHERNET
default y if (!NRF70_RADIO_TEST && !NRF70_OFFLOADED_RAW_TX)
config HEAP_MEM_POOL_ADD_SIZE_NRF70
# Use a maximum that works for typical use cases and boards, each sample/app can override
# this value if needed by using CONFIG_HEAP_MEM_POOL_IGNORE_MIN
def_int 25000 if NRF70_SCAN_ONLY
def_int 150000
if NRF70_SYSTEM_MODE
config NRF70_STA_MODE
bool "nRF70 STA mode"
@ -529,8 +523,19 @@ config NRF70_RSSI_STALE_TIMEOUT_MS
value as the driver does not store it and requires RPU to provide the
information.
config NRF_WIFI_CTRL_HEAP_SIZE
int "Dedicated memory pool for control plane"
default 20000
config NRF_WIFI_DATA_HEAP_SIZE
int "Dedicated memory pool for data plane"
default 6000 if NRF70_SCAN_ONLY
default 110000 if !SOC_FAMILY_NORDIC_NRF
default 130000
if NETWORKING
# Finetune defaults for certain system components used by the driver
config SYSTEM_WORKQUEUE_STACK_SIZE
default 4096

View file

@ -465,7 +465,8 @@ void reg_change_callbk_fn(void *vif_ctx,
return;
}
fmac_dev_ctx->reg_change = k_malloc(sizeof(struct nrf_wifi_event_regulatory_change));
fmac_dev_ctx->reg_change = nrf_wifi_osal_mem_alloc(sizeof(struct
nrf_wifi_event_regulatory_change));
if (!fmac_dev_ctx->reg_change) {
LOG_ERR("%s: Failed to allocate memory for reg_change", __func__);
return;
@ -677,9 +678,9 @@ enum nrf_wifi_status nrf_wifi_fmac_dev_rem_zep(struct nrf_wifi_drv_priv_zep *drv
nrf_wifi_fmac_dev_rem(rpu_ctx_zep->rpu_ctx);
k_free(rpu_ctx_zep->extended_capa);
nrf_wifi_osal_mem_free(rpu_ctx_zep->extended_capa);
rpu_ctx_zep->extended_capa = NULL;
k_free(rpu_ctx_zep->extended_capa_mask);
nrf_wifi_osal_mem_free(rpu_ctx_zep->extended_capa_mask);
rpu_ctx_zep->extended_capa_mask = NULL;
rpu_ctx_zep->rpu_ctx = NULL;

View file

@ -459,7 +459,7 @@ static void ip_maddr_event_handler(struct net_if *iface,
goto unlock;
}
mcast_info = k_calloc(sizeof(*mcast_info), sizeof(char));
mcast_info = nrf_wifi_osal_mem_zalloc(sizeof(*mcast_info));
if (!mcast_info) {
LOG_ERR("%s: Unable to allocate memory of size %d "
@ -501,7 +501,7 @@ static void ip_maddr_event_handler(struct net_if *iface,
sizeof(mac_string_buf)));
}
unlock:
k_free(mcast_info);
nrf_wifi_osal_mem_free(mcast_info);
k_mutex_unlock(&vif_ctx_zep->vif_lock);
}
#endif /* CONFIG_NRF70_STA_MODE */

View file

@ -109,10 +109,9 @@ int nrf_wifi_disp_scan_zep(const struct device *dev, struct wifi_scan_params *pa
vif_ctx_zep->disp_scan_cb = cb;
scan_info = k_calloc(sizeof(*scan_info) +
scan_info = nrf_wifi_osal_mem_zalloc(sizeof(*scan_info) +
(num_scan_channels *
sizeof(scan_info->scan_params.center_frequency[0])),
sizeof(char));
sizeof(scan_info->scan_params.center_frequency[0])));
if (!scan_info) {
LOG_ERR("%s: Unable to allocate memory for scan_info (size: %d bytes)",
@ -226,7 +225,7 @@ int nrf_wifi_disp_scan_zep(const struct device *dev, struct wifi_scan_params *pa
ret = 0;
out:
if (scan_info) {
k_free(scan_info);
nrf_wifi_osal_mem_free(scan_info);
}
k_mutex_unlock(&vif_ctx_zep->vif_lock);
return ret;

View file

@ -174,7 +174,7 @@ void nrf_wifi_wpa_supp_event_proc_scan_res(void *if_priv,
beacon_ie_len = scan_res->beacon_ies_len;
}
r = k_calloc(sizeof(*r) + ie_len + beacon_ie_len, sizeof(char));
r = nrf_wifi_osal_mem_zalloc(sizeof(*r) + ie_len + beacon_ie_len);
if (!r) {
LOG_ERR("%s: Unable to allocate memory for scan result", __func__);
@ -254,7 +254,7 @@ void nrf_wifi_wpa_supp_event_proc_scan_res(void *if_priv,
vif_ctx_zep->scan_in_progress = false;
}
k_free(r);
nrf_wifi_osal_mem_free(r);
}
void nrf_wifi_wpa_supp_event_proc_auth_resp(void *if_priv,
@ -519,8 +519,8 @@ int nrf_wifi_wpa_supp_scan2(void *if_priv, struct wpa_driver_scan_params *params
}
}
scan_info = k_calloc(sizeof(*scan_info) + (num_freqs * sizeof(unsigned int)),
sizeof(char));
scan_info = nrf_wifi_osal_mem_zalloc(sizeof(*scan_info) +
(num_freqs * sizeof(unsigned int)));
if (!scan_info) {
LOG_ERR("%s: Unable to allocate memory for scan info", __func__);
@ -579,7 +579,7 @@ int nrf_wifi_wpa_supp_scan2(void *if_priv, struct wpa_driver_scan_params *params
ret = 0;
out:
if (scan_info) {
k_free(scan_info);
nrf_wifi_osal_mem_free(scan_info);
}
k_mutex_unlock(&vif_ctx_zep->vif_lock);
return ret;
@ -1414,7 +1414,7 @@ int nrf_wifi_nl80211_send_mlme(void *if_priv, const u8 *data,
k_mutex_lock(&mgmt_tx_lock, K_FOREVER);
mgmt_tx_info = k_calloc(sizeof(*mgmt_tx_info), sizeof(char));
mgmt_tx_info = nrf_wifi_osal_mem_zalloc(sizeof(*mgmt_tx_info));
if (!mgmt_tx_info) {
LOG_ERR("%s: Unable to allocate memory", __func__);
@ -1491,7 +1491,7 @@ int nrf_wifi_nl80211_send_mlme(void *if_priv, const u8 *data,
out:
if (mgmt_tx_info) {
k_free(mgmt_tx_info);
nrf_wifi_osal_mem_free(mgmt_tx_info);
}
k_mutex_unlock(&mgmt_tx_lock);
k_mutex_unlock(&vif_ctx_zep->vif_lock);
@ -1610,22 +1610,24 @@ void nrf_wifi_wpa_supp_event_get_wiphy(void *if_priv,
if ((wiphy_info->params_valid & NRF_WIFI_GET_WIPHY_VALID_EXTENDED_CAPABILITIES) &&
rpu_ctx_zep->extended_capa == NULL) {
/* To avoid overflowing the 100 column limit */
unsigned char ec_len = wiphy_info->extended_capabilities_len;
rpu_ctx_zep->extended_capa = k_malloc(wiphy_info->extended_capabilities_len);
rpu_ctx_zep->extended_capa = nrf_wifi_osal_mem_alloc(ec_len);
if (rpu_ctx_zep->extended_capa) {
memcpy(rpu_ctx_zep->extended_capa, wiphy_info->extended_capabilities,
wiphy_info->extended_capabilities_len);
ec_len);
}
rpu_ctx_zep->extended_capa_mask = k_malloc(wiphy_info->extended_capabilities_len);
rpu_ctx_zep->extended_capa_mask = nrf_wifi_osal_mem_alloc(ec_len);
if (rpu_ctx_zep->extended_capa_mask) {
memcpy(rpu_ctx_zep->extended_capa_mask,
wiphy_info->extended_capabilities_mask,
wiphy_info->extended_capabilities_len);
ec_len);
} else {
free(rpu_ctx_zep->extended_capa);
nrf_wifi_osal_mem_free(rpu_ctx_zep->extended_capa);
rpu_ctx_zep->extended_capa = NULL;
rpu_ctx_zep->extended_capa_len = 0;
}

View file

@ -24,6 +24,7 @@
#include <hal/nrf_gpio.h>
#include "spi_nor.h"
#include "osal_api.h"
/* The QSPI bus node which the NRF70 is on */
#define QSPI_IF_BUS_NODE DT_NODELABEL(qspi)
@ -1287,7 +1288,7 @@ int qspi_hl_readw(unsigned int addr, void *data)
len = len + (4 * qspi_cfg->qspi_slave_latency);
rxb = k_malloc(len);
rxb = nrf_wifi_osal_mem_alloc(len);
if (rxb == NULL) {
LOG_ERR("%s: ERROR ENOMEM line %d", __func__, __LINE__);
@ -1306,7 +1307,7 @@ int qspi_hl_readw(unsigned int addr, void *data)
*(uint32_t *)data = *(uint32_t *)(rxb + (len - 4));
k_free(rxb);
nrf_wifi_osal_mem_free(rxb);
return status;
}

View file

@ -9,6 +9,7 @@ add_subdirectory(${ZEPHYR_NRF_WIFI_MODULE_DIR} nrf_wifi_osal)
zephyr_library_named(nrf-wifi-shim)
zephyr_include_directories(${CMAKE_CURRENT_LIST_DIR})
zephyr_include_directories(${ZEPHYR_NRF_WIFI_MODULE_DIR}/os_if/inc)
zephyr_library_sources(
shim.c
timer.c

View file

@ -20,6 +20,7 @@
#include <zephyr/sys/__assert.h>
#include <zephyr/drivers/wifi/nrf_wifi/bus/rpu_hw_if.h>
#include <zephyr/drivers/wifi/nrf_wifi/bus/qspi_if.h>
#include <zephyr/sys/math_extras.h>
#include "shim.h"
#include "work.h"
@ -27,6 +28,14 @@
#include "osal_ops.h"
LOG_MODULE_REGISTER(wifi_nrf, CONFIG_WIFI_NRF70_LOG_LEVEL);
#if defined(CONFIG_NOCACHE_MEMORY)
K_HEAP_DEFINE_NOCACHE(wifi_drv_ctrl_mem_pool, CONFIG_NRF_WIFI_CTRL_HEAP_SIZE);
K_HEAP_DEFINE_NOCACHE(wifi_drv_data_mem_pool, CONFIG_NRF_WIFI_DATA_HEAP_SIZE);
#else
K_HEAP_DEFINE(wifi_drv_ctrl_mem_pool, CONFIG_NRF_WIFI_CTRL_HEAP_SIZE);
K_HEAP_DEFINE(wifi_drv_data_mem_pool, CONFIG_NRF_WIFI_DATA_HEAP_SIZE);
#endif /* CONFIG_NOCACHE_MEMORY */
#define WORD_SIZE 4
struct zep_shim_intr_priv *intr_priv;
@ -34,14 +43,66 @@ static void *zep_shim_mem_alloc(size_t size)
{
size_t size_aligned = ROUND_UP(size, 4);
return k_malloc(size_aligned);
return k_heap_aligned_alloc(&wifi_drv_ctrl_mem_pool, WORD_SIZE, size_aligned, K_FOREVER);
}
static void *zep_shim_data_mem_alloc(size_t size)
{
size_t size_aligned = ROUND_UP(size, 4);
return k_heap_aligned_alloc(&wifi_drv_data_mem_pool, WORD_SIZE, size_aligned, K_FOREVER);
}
static void *zep_shim_mem_zalloc(size_t size)
{
void *ret;
size_t bounds;
size_t size_aligned = ROUND_UP(size, 4);
return k_calloc(size_aligned, sizeof(char));
if (size_mul_overflow(size_aligned, sizeof(char), &bounds)) {
return NULL;
}
ret = zep_shim_mem_alloc(bounds);
if (ret != NULL) {
(void)memset(ret, 0, bounds);
}
return ret;
}
static void *zep_shim_data_mem_zalloc(size_t size)
{
void *ret;
size_t bounds;
size_t size_aligned = ROUND_UP(size, 4);
if (size_mul_overflow(size_aligned, sizeof(char), &bounds)) {
return NULL;
}
ret = zep_shim_data_mem_alloc(bounds);
if (ret != NULL) {
(void)memset(ret, 0, bounds);
}
return ret;
}
static void zep_shim_mem_free(void *buf)
{
if (buf) {
k_heap_free(&wifi_drv_ctrl_mem_pool, buf);
}
}
static void zep_shim_data_mem_free(void *buf)
{
if (buf) {
k_heap_free(&wifi_drv_data_mem_pool, buf);
}
}
static void *zep_shim_mem_cpy(void *dest, const void *src, size_t count)
@ -118,7 +179,7 @@ static void *zep_shim_spinlock_alloc(void)
{
struct k_mutex *lock = NULL;
lock = k_malloc(sizeof(*lock));
lock = zep_shim_mem_zalloc(sizeof(*lock));
if (!lock) {
LOG_ERR("%s: Unable to allocate memory for spinlock", __func__);
@ -129,7 +190,7 @@ static void *zep_shim_spinlock_alloc(void)
static void zep_shim_spinlock_free(void *lock)
{
k_free(lock);
k_heap_free(&wifi_drv_ctrl_mem_pool, lock);
}
static void zep_shim_spinlock_init(void *lock)
@ -213,16 +274,16 @@ static void *zep_shim_nbuf_alloc(unsigned int size)
{
struct nwb *nbuff;
nbuff = (struct nwb *)k_calloc(sizeof(struct nwb), sizeof(char));
nbuff = (struct nwb *)zep_shim_data_mem_zalloc(sizeof(struct nwb));
if (!nbuff) {
return NULL;
}
nbuff->priv = k_calloc(size, sizeof(char));
nbuff->priv = zep_shim_data_mem_zalloc(size);
if (!nbuff->priv) {
k_free(nbuff);
zep_shim_data_mem_free(nbuff);
return NULL;
}
@ -241,8 +302,8 @@ static void zep_shim_nbuf_free(void *nbuf)
return;
}
k_free(((struct nwb *)nbuf)->priv);
k_free(nbuf);
zep_shim_data_mem_free(((struct nwb *)nbuf)->priv);
zep_shim_data_mem_free(nbuf);
}
static void zep_shim_nbuf_headroom_res(void *nbuf, unsigned int size)
@ -406,7 +467,7 @@ void *net_raw_pkt_from_nbuf(void *iface, void *frm,
nwb_data = zep_shim_nbuf_data_get(nwb);
total_len = raw_hdr_len + nwb_len;
data = (unsigned char *)k_malloc(total_len);
data = (unsigned char *)zep_shim_data_mem_zalloc(total_len);
if (!data) {
LOG_ERR("%s: Unable to allocate memory for sniffer data packet", __func__);
goto out;
@ -428,7 +489,7 @@ void *net_raw_pkt_from_nbuf(void *iface, void *frm,
}
out:
if (data != NULL) {
k_free(data);
zep_shim_data_mem_free(data);
}
if (pkt_free) {
@ -443,7 +504,7 @@ static void *zep_shim_llist_node_alloc(void)
{
struct zep_shim_llist_node *llist_node = NULL;
llist_node = k_calloc(sizeof(*llist_node), sizeof(char));
llist_node = zep_shim_data_mem_zalloc(sizeof(*llist_node));
if (!llist_node) {
LOG_ERR("%s: Unable to allocate memory for linked list node", __func__);
@ -457,7 +518,7 @@ static void *zep_shim_llist_node_alloc(void)
static void zep_shim_llist_node_free(void *llist_node)
{
k_free(llist_node);
zep_shim_data_mem_free(llist_node);
}
static void *zep_shim_llist_node_data_get(void *llist_node)
@ -482,7 +543,20 @@ static void *zep_shim_llist_alloc(void)
{
struct zep_shim_llist *llist = NULL;
llist = k_calloc(sizeof(*llist), sizeof(char));
llist = zep_shim_data_mem_zalloc(sizeof(*llist));
if (!llist) {
LOG_ERR("%s: Unable to allocate memory for linked list", __func__);
}
return llist;
}
static void *zep_shim_ctrl_llist_alloc(void)
{
struct zep_shim_llist *llist = NULL;
llist = zep_shim_mem_zalloc(sizeof(*llist));
if (!llist) {
LOG_ERR("%s: Unable to allocate memory for linked list", __func__);
@ -493,7 +567,12 @@ static void *zep_shim_llist_alloc(void)
static void zep_shim_llist_free(void *llist)
{
k_free(llist);
zep_shim_data_mem_free(llist);
}
static void zep_shim_ctrl_llist_free(void *llist)
{
zep_shim_mem_free(llist);
}
static void zep_shim_llist_init(void *llist)
@ -698,7 +777,7 @@ static void *zep_shim_bus_qspi_init(void)
{
struct zep_shim_bus_qspi_priv *qspi_priv = NULL;
qspi_priv = k_calloc(sizeof(*qspi_priv), sizeof(char));
qspi_priv = zep_shim_mem_zalloc(sizeof(*qspi_priv));
if (!qspi_priv) {
LOG_ERR("%s: Unable to allocate memory for qspi_priv", __func__);
@ -714,7 +793,7 @@ static void zep_shim_bus_qspi_deinit(void *os_qspi_priv)
qspi_priv = os_qspi_priv;
k_free(qspi_priv);
zep_shim_mem_free(qspi_priv);
}
#ifdef CONFIG_NRF_WIFI_LOW_POWER
@ -789,7 +868,7 @@ static enum nrf_wifi_status zep_shim_bus_qspi_intr_reg(void *os_dev_ctx, void *c
ARG_UNUSED(os_dev_ctx);
intr_priv = k_calloc(sizeof(*intr_priv), sizeof(char));
intr_priv = zep_shim_mem_zalloc(sizeof(*intr_priv));
if (!intr_priv) {
LOG_ERR("%s: Unable to allocate memory for intr_priv", __func__);
@ -805,7 +884,7 @@ static enum nrf_wifi_status zep_shim_bus_qspi_intr_reg(void *os_dev_ctx, void *c
if (ret) {
LOG_ERR("%s: request_irq failed", __func__);
k_free(intr_priv);
zep_shim_mem_free(intr_priv);
intr_priv = NULL;
goto out;
}
@ -831,7 +910,7 @@ static void zep_shim_bus_qspi_intr_unreg(void *os_qspi_dev_ctx)
k_work_cancel_delayable_sync(&intr_priv->work, &sync);
k_free(intr_priv);
zep_shim_mem_free(intr_priv);
intr_priv = NULL;
}
@ -840,7 +919,7 @@ static void *zep_shim_timer_alloc(void)
{
struct timer_list *timer = NULL;
timer = k_malloc(sizeof(*timer));
timer = zep_shim_mem_zalloc(sizeof(*timer));
if (!timer) {
LOG_ERR("%s: Unable to allocate memory for work", __func__);
@ -859,7 +938,7 @@ static void zep_shim_timer_init(void *timer, void (*callback)(unsigned long), un
static void zep_shim_timer_free(void *timer)
{
k_free(timer);
zep_shim_mem_free(timer);
}
static void zep_shim_timer_schedule(void *timer, unsigned long duration)
@ -907,7 +986,9 @@ static unsigned int zep_shim_strlen(const void *str)
const struct nrf_wifi_osal_ops nrf_wifi_os_zep_ops = {
.mem_alloc = zep_shim_mem_alloc,
.mem_zalloc = zep_shim_mem_zalloc,
.mem_free = k_free,
.data_mem_zalloc = zep_shim_data_mem_zalloc,
.mem_free = zep_shim_mem_free,
.data_mem_free = zep_shim_data_mem_free,
.mem_cpy = zep_shim_mem_cpy,
.mem_set = zep_shim_mem_set,
.mem_cmp = zep_shim_mem_cmp,
@ -936,7 +1017,9 @@ const struct nrf_wifi_osal_ops nrf_wifi_os_zep_ops = {
.llist_node_data_set = zep_shim_llist_node_data_set,
.llist_alloc = zep_shim_llist_alloc,
.ctrl_llist_alloc = zep_shim_ctrl_llist_alloc,
.llist_free = zep_shim_llist_free,
.ctrl_llist_free = zep_shim_ctrl_llist_free,
.llist_init = zep_shim_llist_init,
.llist_add_node_tail = zep_shim_llist_add_node_tail,
.llist_add_node_head = zep_shim_llist_add_node_head,