提交 6a5e1e00 编写于 作者: F Franky Lin 提交者: Greg Kroah-Hartman

staging: brcm80211: remove event handler thread from fullmac

Use work queue to defer cfg80211 event handle jobs
Reviewed-by: NRoland Vossen <rvossen@broadcom.com>
Reviewed-by: NPieter-Paul Giesberts <pieterpg@broadcom.com>
Reviewed-by: NArend van Spriel <arend@broadcom.com>
Signed-off-by: NFranky Lin <frankyl@broadcom.com>
Signed-off-by: NGreg Kroah-Hartman <gregkh@suse.de>
上级 6fc1fbc0
......@@ -3248,69 +3248,30 @@ static void brcmf_put_event(struct brcmf_cfg80211_event_q *e)
kfree(e);
}
static s32 brcmf_event_handler(void *data)
static void brcmf_cfg80211_event_handler(struct work_struct *work)
{
struct brcmf_cfg80211_priv *cfg_priv =
(struct brcmf_cfg80211_priv *)data;
struct sched_param param = {.sched_priority = MAX_RT_PRIO - 1 };
container_of(work, struct brcmf_cfg80211_priv,
event_work);
struct brcmf_cfg80211_event_q *e;
DECLARE_WAITQUEUE(wait, current);
sched_setscheduler(current, SCHED_FIFO, &param);
allow_signal(SIGTERM);
add_wait_queue(&cfg_priv->event_waitq, &wait);
while (1) {
prepare_to_wait(&cfg_priv->event_waitq, &wait,
TASK_INTERRUPTIBLE);
schedule();
if (kthread_should_stop())
break;
e = brcmf_deq_event(cfg_priv);
if (unlikely(!e)) {
WL_ERR("event queue empty...\n");
continue;
}
do {
WL_INFO("event type (%d)\n", e->etype);
if (cfg_priv->el.handler[e->etype])
cfg_priv->el.handler[e->etype](cfg_priv,
cfg_to_ndev(cfg_priv),
&e->emsg, e->edata);
else
WL_INFO("Unknown Event (%d): ignoring\n",
e->etype);
brcmf_put_event(e);
} while ((e = brcmf_deq_event(cfg_priv)));
e = brcmf_deq_event(cfg_priv);
if (unlikely(!e)) {
WL_ERR("event queue empty...\n");
return;
}
finish_wait(&cfg_priv->event_waitq, &wait);
WL_INFO("was terminated\n");
return 0;
}
static s32 brcmf_create_event_handler(struct brcmf_cfg80211_priv *cfg_priv)
{
init_waitqueue_head(&cfg_priv->event_waitq);
cfg_priv->event_tsk = kthread_run(brcmf_event_handler, cfg_priv,
"wl_event_handler");
if (IS_ERR(cfg_priv->event_tsk)) {
cfg_priv->event_tsk = NULL;
WL_ERR("failed to create event thread\n");
return -ENOMEM;
}
return 0;
}
do {
WL_INFO("event type (%d)\n", e->etype);
if (cfg_priv->el.handler[e->etype])
cfg_priv->el.handler[e->etype](cfg_priv,
cfg_to_ndev(cfg_priv),
&e->emsg, e->edata);
else
WL_INFO("Unknown Event (%d): ignoring\n", e->etype);
brcmf_put_event(e);
} while ((e = brcmf_deq_event(cfg_priv)));
static void brcmf_destroy_event_handler(struct brcmf_cfg80211_priv *cfg_priv)
{
if (cfg_priv->event_tsk) {
send_sig(SIGTERM, cfg_priv->event_tsk, 1);
kthread_stop(cfg_priv->event_tsk);
cfg_priv->event_tsk = NULL;
}
}
static void brcmf_init_eq(struct brcmf_cfg80211_priv *cfg_priv)
......@@ -3352,8 +3313,7 @@ static s32 wl_init_priv(struct brcmf_cfg80211_priv *cfg_priv)
err = brcmf_init_priv_mem(cfg_priv);
if (unlikely(err))
return err;
if (unlikely(brcmf_create_event_handler(cfg_priv)))
return -ENOMEM;
INIT_WORK(&cfg_priv->event_work, brcmf_cfg80211_event_handler);
brcmf_init_eloop_handler(&cfg_priv->el);
mutex_init(&cfg_priv->usr_sync);
err = brcmf_init_iscan(cfg_priv);
......@@ -3368,7 +3328,7 @@ static s32 wl_init_priv(struct brcmf_cfg80211_priv *cfg_priv)
static void wl_deinit_priv(struct brcmf_cfg80211_priv *cfg_priv)
{
brcmf_destroy_event_handler(cfg_priv);
cancel_work_sync(&cfg_priv->event_work);
cfg_priv->dongle_up = false; /* dongle down */
brcmf_flush_eq(cfg_priv);
brcmf_link_down(cfg_priv);
......@@ -3438,11 +3398,6 @@ void brcmf_cfg80211_detach(struct brcmf_cfg80211_dev *cfg_dev)
kfree(cfg_dev);
}
static void brcmf_wakeup_event(struct brcmf_cfg80211_priv *cfg_priv)
{
wake_up(&cfg_priv->event_waitq);
}
void
brcmf_cfg80211_event(struct net_device *ndev,
const struct brcmf_event_msg *e, void *data)
......@@ -3451,7 +3406,7 @@ brcmf_cfg80211_event(struct net_device *ndev,
struct brcmf_cfg80211_priv *cfg_priv = ndev_to_cfg(ndev);
if (likely(!brcmf_enq_event(cfg_priv, event_type, e)))
brcmf_wakeup_event(cfg_priv);
schedule_work(&cfg_priv->event_work);
}
static s32 brcmf_dongle_mode(struct net_device *ndev, s32 iftype)
......
......@@ -298,8 +298,7 @@ struct brcmf_cfg80211_priv {
struct brcmf_cfg80211_iscan_ctrl *iscan; /* iscan controller */
struct brcmf_cfg80211_connect_info conn_info; /* association info */
struct brcmf_cfg80211_pmk_list *pmk_list; /* wpa2 pmk list */
struct task_struct *event_tsk; /* task of main event handler thread */
wait_queue_head_t event_waitq; /* wait queue for main event handling */
struct work_struct event_work; /* event handler work struct */
unsigned long status; /* current dongle status */
void *pub;
u32 channel; /* current channel */
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册