Commit d5367334 authored by Hante Meuleman's avatar Hante Meuleman Committed by Kalle Valo

brcmfmac: Limit memory allocs to <64K

Some systems have problems with allocating memory allocation larger
then 64K. Often on unload/load or suspend/resume a failure is
reported: Could not allocate wiphy device. This patch makes the
escan intermediate storage buf dynamically allocated, and smaller
than 64K.
Reviewed-by: default avatarArend Van Spriel <arend@broadcom.com>
Reviewed-by: default avatarFranky (Zhenhui) Lin <frankyl@broadcom.com>
Reviewed-by: default avatarPieter-Paul Giesberts <pieterpg@broadcom.com>
Signed-off-by: default avatarHante Meuleman <meuleman@broadcom.com>
Signed-off-by: default avatarArend van Spriel <arend@broadcom.com>
Signed-off-by: default avatarKalle Valo <kvalo@codeaurora.org>
parent a9eb0c4b
...@@ -1125,7 +1125,7 @@ brcmf_cfg80211_escan(struct wiphy *wiphy, struct brcmf_cfg80211_vif *vif, ...@@ -1125,7 +1125,7 @@ brcmf_cfg80211_escan(struct wiphy *wiphy, struct brcmf_cfg80211_vif *vif,
/* Arm scan timeout timer */ /* Arm scan timeout timer */
mod_timer(&cfg->escan_timeout, jiffies + mod_timer(&cfg->escan_timeout, jiffies +
WL_ESCAN_TIMER_INTERVAL_MS * HZ / 1000); BRCMF_ESCAN_TIMER_INTERVAL_MS * HZ / 1000);
return 0; return 0;
...@@ -3020,7 +3020,7 @@ brcmf_cfg80211_escan_handler(struct brcmf_if *ifp, ...@@ -3020,7 +3020,7 @@ brcmf_cfg80211_escan_handler(struct brcmf_if *ifp,
list = (struct brcmf_scan_results *) list = (struct brcmf_scan_results *)
cfg->escan_info.escan_buf; cfg->escan_info.escan_buf;
if (bi_length > WL_ESCAN_BUF_SIZE - list->buflen) { if (bi_length > BRCMF_ESCAN_BUF_SIZE - list->buflen) {
brcmf_err("Buffer is too small: ignoring\n"); brcmf_err("Buffer is too small: ignoring\n");
goto exit; goto exit;
} }
...@@ -3033,8 +3033,8 @@ brcmf_cfg80211_escan_handler(struct brcmf_if *ifp, ...@@ -3033,8 +3033,8 @@ brcmf_cfg80211_escan_handler(struct brcmf_if *ifp,
bss_info_le)) bss_info_le))
goto exit; goto exit;
} }
memcpy(&(cfg->escan_info.escan_buf[list->buflen]), memcpy(&cfg->escan_info.escan_buf[list->buflen], bss_info_le,
bss_info_le, bi_length); bi_length);
list->version = le32_to_cpu(bss_info_le->version); list->version = le32_to_cpu(bss_info_le->version);
list->buflen += bi_length; list->buflen += bi_length;
list->count++; list->count++;
...@@ -5402,14 +5402,14 @@ static void brcmf_deinit_priv_mem(struct brcmf_cfg80211_info *cfg) ...@@ -5402,14 +5402,14 @@ static void brcmf_deinit_priv_mem(struct brcmf_cfg80211_info *cfg)
{ {
kfree(cfg->conf); kfree(cfg->conf);
cfg->conf = NULL; cfg->conf = NULL;
kfree(cfg->escan_ioctl_buf);
cfg->escan_ioctl_buf = NULL;
kfree(cfg->extra_buf); kfree(cfg->extra_buf);
cfg->extra_buf = NULL; cfg->extra_buf = NULL;
kfree(cfg->wowl.nd); kfree(cfg->wowl.nd);
cfg->wowl.nd = NULL; cfg->wowl.nd = NULL;
kfree(cfg->wowl.nd_info); kfree(cfg->wowl.nd_info);
cfg->wowl.nd_info = NULL; cfg->wowl.nd_info = NULL;
kfree(cfg->escan_info.escan_buf);
cfg->escan_info.escan_buf = NULL;
} }
static s32 brcmf_init_priv_mem(struct brcmf_cfg80211_info *cfg) static s32 brcmf_init_priv_mem(struct brcmf_cfg80211_info *cfg)
...@@ -5417,9 +5417,6 @@ static s32 brcmf_init_priv_mem(struct brcmf_cfg80211_info *cfg) ...@@ -5417,9 +5417,6 @@ static s32 brcmf_init_priv_mem(struct brcmf_cfg80211_info *cfg)
cfg->conf = kzalloc(sizeof(*cfg->conf), GFP_KERNEL); cfg->conf = kzalloc(sizeof(*cfg->conf), GFP_KERNEL);
if (!cfg->conf) if (!cfg->conf)
goto init_priv_mem_out; goto init_priv_mem_out;
cfg->escan_ioctl_buf = kzalloc(BRCMF_DCMD_MEDLEN, GFP_KERNEL);
if (!cfg->escan_ioctl_buf)
goto init_priv_mem_out;
cfg->extra_buf = kzalloc(WL_EXTRA_BUF_MAX, GFP_KERNEL); cfg->extra_buf = kzalloc(WL_EXTRA_BUF_MAX, GFP_KERNEL);
if (!cfg->extra_buf) if (!cfg->extra_buf)
goto init_priv_mem_out; goto init_priv_mem_out;
...@@ -5431,6 +5428,9 @@ static s32 brcmf_init_priv_mem(struct brcmf_cfg80211_info *cfg) ...@@ -5431,6 +5428,9 @@ static s32 brcmf_init_priv_mem(struct brcmf_cfg80211_info *cfg)
GFP_KERNEL); GFP_KERNEL);
if (!cfg->wowl.nd_info) if (!cfg->wowl.nd_info)
goto init_priv_mem_out; goto init_priv_mem_out;
cfg->escan_info.escan_buf = kzalloc(BRCMF_ESCAN_BUF_SIZE, GFP_KERNEL);
if (!cfg->escan_info.escan_buf)
goto init_priv_mem_out;
return 0; return 0;
......
...@@ -28,8 +28,11 @@ ...@@ -28,8 +28,11 @@
#define WL_ROAM_TRIGGER_LEVEL -75 #define WL_ROAM_TRIGGER_LEVEL -75
#define WL_ROAM_DELTA 20 #define WL_ROAM_DELTA 20
#define WL_ESCAN_BUF_SIZE (1024 * 64) /* Keep BRCMF_ESCAN_BUF_SIZE below 64K (65536). Allocing over 64K can be
#define WL_ESCAN_TIMER_INTERVAL_MS 10000 /* E-Scan timeout */ * problematic on some systems and should be avoided.
*/
#define BRCMF_ESCAN_BUF_SIZE 65000
#define BRCMF_ESCAN_TIMER_INTERVAL_MS 10000 /* E-Scan timeout */
#define WL_ESCAN_ACTION_START 1 #define WL_ESCAN_ACTION_START 1
#define WL_ESCAN_ACTION_CONTINUE 2 #define WL_ESCAN_ACTION_CONTINUE 2
...@@ -205,7 +208,7 @@ enum wl_escan_state { ...@@ -205,7 +208,7 @@ enum wl_escan_state {
struct escan_info { struct escan_info {
u32 escan_state; u32 escan_state;
u8 escan_buf[WL_ESCAN_BUF_SIZE]; u8 *escan_buf;
struct wiphy *wiphy; struct wiphy *wiphy;
struct brcmf_if *ifp; struct brcmf_if *ifp;
s32 (*run)(struct brcmf_cfg80211_info *cfg, struct brcmf_if *ifp, s32 (*run)(struct brcmf_cfg80211_info *cfg, struct brcmf_if *ifp,
...@@ -278,7 +281,6 @@ struct brcmf_cfg80211_wowl { ...@@ -278,7 +281,6 @@ struct brcmf_cfg80211_wowl {
* @escan_info: escan information. * @escan_info: escan information.
* @escan_timeout: Timer for catch scan timeout. * @escan_timeout: Timer for catch scan timeout.
* @escan_timeout_work: scan timeout worker. * @escan_timeout_work: scan timeout worker.
* @escan_ioctl_buf: dongle command buffer for escan commands.
* @vif_list: linked list of vif instances. * @vif_list: linked list of vif instances.
* @vif_cnt: number of vif instances. * @vif_cnt: number of vif instances.
* @vif_event: vif event signalling. * @vif_event: vif event signalling.
...@@ -309,7 +311,6 @@ struct brcmf_cfg80211_info { ...@@ -309,7 +311,6 @@ struct brcmf_cfg80211_info {
struct escan_info escan_info; struct escan_info escan_info;
struct timer_list escan_timeout; struct timer_list escan_timeout;
struct work_struct escan_timeout_work; struct work_struct escan_timeout_work;
u8 *escan_ioctl_buf;
struct list_head vif_list; struct list_head vif_list;
struct brcmf_cfg80211_vif_event vif_event; struct brcmf_cfg80211_vif_event vif_event;
struct completion vif_disabled; struct completion vif_disabled;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment