Commit f96f8ae0 authored by Davidlohr Bueso's avatar Davidlohr Bueso Committed by Greg Kroah-Hartman

staging/rtl8192e,ieee80211: replace ps tasklet with work

Tasklets have long been deprecated as being too heavy on the system
by running in irq context - and this is not a performance critical
path. If a higher priority process wants to run, it must wait for
the tasklet to finish before doing so.

rtllib_sta_ps() and ieee80211_sta_ps() will now run in process context
and have further concurrency (tasklets being serialized among themselves),
but this is done holding the ieee->lock, so it should be fine.
Signed-off-by: default avatarDavidlohr Bueso <dave@stgolabs.net>
Link: https://lore.kernel.org/r/20220411151620.129178-7-dave@stgolabs.netSigned-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent 2a2849a8
...@@ -1585,7 +1585,7 @@ struct rtllib_device { ...@@ -1585,7 +1585,7 @@ struct rtllib_device {
short sta_sleep; short sta_sleep;
int ps_timeout; int ps_timeout;
int ps_period; int ps_period;
struct tasklet_struct ps_task; struct work_struct ps_task;
u64 ps_time; u64 ps_time;
bool polling; bool polling;
......
...@@ -2721,7 +2721,7 @@ static void rtllib_rx_mgt(struct rtllib_device *ieee, ...@@ -2721,7 +2721,7 @@ static void rtllib_rx_mgt(struct rtllib_device *ieee,
if (ieee->sta_sleep || (ieee->ps != RTLLIB_PS_DISABLED && if (ieee->sta_sleep || (ieee->ps != RTLLIB_PS_DISABLED &&
ieee->iw_mode == IW_MODE_INFRA && ieee->iw_mode == IW_MODE_INFRA &&
ieee->state == RTLLIB_LINKED)) ieee->state == RTLLIB_LINKED))
tasklet_schedule(&ieee->ps_task); schedule_work(&ieee->ps_task);
break; break;
......
...@@ -2042,13 +2042,17 @@ static short rtllib_sta_ps_sleep(struct rtllib_device *ieee, u64 *time) ...@@ -2042,13 +2042,17 @@ static short rtllib_sta_ps_sleep(struct rtllib_device *ieee, u64 *time)
} }
static inline void rtllib_sta_ps(struct tasklet_struct *t) static inline void rtllib_sta_ps(struct work_struct *work)
{ {
struct rtllib_device *ieee = from_tasklet(ieee, t, ps_task); struct rtllib_device *ieee;
u64 time; u64 time;
short sleep; short sleep;
unsigned long flags, flags2; unsigned long flags, flags2;
ieee = container_of(work, struct rtllib_device, ps_task);
if (!ieee)
return;
spin_lock_irqsave(&ieee->lock, flags); spin_lock_irqsave(&ieee->lock, flags);
if ((ieee->ps == RTLLIB_PS_DISABLED || if ((ieee->ps == RTLLIB_PS_DISABLED ||
...@@ -3028,7 +3032,7 @@ int rtllib_softmac_init(struct rtllib_device *ieee) ...@@ -3028,7 +3032,7 @@ int rtllib_softmac_init(struct rtllib_device *ieee)
spin_lock_init(&ieee->mgmt_tx_lock); spin_lock_init(&ieee->mgmt_tx_lock);
spin_lock_init(&ieee->beacon_lock); spin_lock_init(&ieee->beacon_lock);
tasklet_setup(&ieee->ps_task, rtllib_sta_ps); INIT_WORK(&ieee->ps_task, rtllib_sta_ps);
return 0; return 0;
} }
...@@ -3050,8 +3054,8 @@ void rtllib_softmac_free(struct rtllib_device *ieee) ...@@ -3050,8 +3054,8 @@ void rtllib_softmac_free(struct rtllib_device *ieee)
cancel_work_sync(&ieee->associate_complete_wq); cancel_work_sync(&ieee->associate_complete_wq);
cancel_work_sync(&ieee->ips_leave_wq); cancel_work_sync(&ieee->ips_leave_wq);
cancel_work_sync(&ieee->wx_sync_scan_wq); cancel_work_sync(&ieee->wx_sync_scan_wq);
cancel_work_sync(&ieee->ps_task);
mutex_unlock(&ieee->wx_mutex); mutex_unlock(&ieee->wx_mutex);
tasklet_kill(&ieee->ps_task);
} }
static inline struct sk_buff * static inline struct sk_buff *
......
...@@ -1790,7 +1790,7 @@ struct ieee80211_device { ...@@ -1790,7 +1790,7 @@ struct ieee80211_device {
short sta_sleep; short sta_sleep;
int ps_timeout; int ps_timeout;
int ps_period; int ps_period;
struct tasklet_struct ps_task; struct work_struct ps_task;
u32 ps_th; u32 ps_th;
u32 ps_tl; u32 ps_tl;
......
...@@ -1687,14 +1687,17 @@ static short ieee80211_sta_ps_sleep(struct ieee80211_device *ieee, u32 *time_h, ...@@ -1687,14 +1687,17 @@ static short ieee80211_sta_ps_sleep(struct ieee80211_device *ieee, u32 *time_h,
return 1; return 1;
} }
static inline void ieee80211_sta_ps(struct tasklet_struct *t) static inline void ieee80211_sta_ps(struct work_struct *work)
{ {
struct ieee80211_device *ieee = from_tasklet(ieee, t, ps_task); struct ieee80211_device *ieee;
u32 th, tl; u32 th, tl;
short sleep; short sleep;
unsigned long flags, flags2; unsigned long flags, flags2;
ieee = container_of(work, struct ieee80211_device, ps_task);
if (!ieee)
return;
spin_lock_irqsave(&ieee->lock, flags); spin_lock_irqsave(&ieee->lock, flags);
if ((ieee->ps == IEEE80211_PS_DISABLED || if ((ieee->ps == IEEE80211_PS_DISABLED ||
...@@ -1897,7 +1900,7 @@ ieee80211_rx_frame_softmac(struct ieee80211_device *ieee, struct sk_buff *skb, ...@@ -1897,7 +1900,7 @@ ieee80211_rx_frame_softmac(struct ieee80211_device *ieee, struct sk_buff *skb,
if (ieee->sta_sleep || (ieee->ps != IEEE80211_PS_DISABLED && if (ieee->sta_sleep || (ieee->ps != IEEE80211_PS_DISABLED &&
ieee->iw_mode == IW_MODE_INFRA && ieee->iw_mode == IW_MODE_INFRA &&
ieee->state == IEEE80211_LINKED)) ieee->state == IEEE80211_LINKED))
tasklet_schedule(&ieee->ps_task); schedule_work(&ieee->ps_task);
if (WLAN_FC_GET_STYPE(header->frame_ctl) != IEEE80211_STYPE_PROBE_RESP && if (WLAN_FC_GET_STYPE(header->frame_ctl) != IEEE80211_STYPE_PROBE_RESP &&
WLAN_FC_GET_STYPE(header->frame_ctl) != IEEE80211_STYPE_BEACON) WLAN_FC_GET_STYPE(header->frame_ctl) != IEEE80211_STYPE_BEACON)
...@@ -2602,7 +2605,7 @@ void ieee80211_softmac_init(struct ieee80211_device *ieee) ...@@ -2602,7 +2605,7 @@ void ieee80211_softmac_init(struct ieee80211_device *ieee)
spin_lock_init(&ieee->mgmt_tx_lock); spin_lock_init(&ieee->mgmt_tx_lock);
spin_lock_init(&ieee->beacon_lock); spin_lock_init(&ieee->beacon_lock);
tasklet_setup(&ieee->ps_task, ieee80211_sta_ps); INIT_WORK(&ieee->ps_task, ieee80211_sta_ps);
} }
void ieee80211_softmac_free(struct ieee80211_device *ieee) void ieee80211_softmac_free(struct ieee80211_device *ieee)
...@@ -2613,7 +2616,7 @@ void ieee80211_softmac_free(struct ieee80211_device *ieee) ...@@ -2613,7 +2616,7 @@ void ieee80211_softmac_free(struct ieee80211_device *ieee)
del_timer_sync(&ieee->associate_timer); del_timer_sync(&ieee->associate_timer);
cancel_delayed_work(&ieee->associate_retry_wq); cancel_delayed_work(&ieee->associate_retry_wq);
cancel_work_sync(&ieee->ps_task);
mutex_unlock(&ieee->wx_mutex); mutex_unlock(&ieee->wx_mutex);
} }
......
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