From 44be80232aa49737c035ee4656d20a22f573d33e Mon Sep 17 00:00:00 2001 From: Ping-Ke Shih Date: Tue, 6 Apr 2021 19:55:59 +0800 Subject: [PATCH] rtlwifi: implement set_tim by update beacon content Once beacon content is changed, we update the content to wifi card by send_beacon_frame(). Signed-off-by: Ping-Ke Shih --- drivers/net/wireless/realtek/rtlwifi/core.c | 30 +++++++++++++++++++++ drivers/net/wireless/realtek/rtlwifi/core.h | 1 + drivers/net/wireless/realtek/rtlwifi/pci.c | 3 +++ drivers/net/wireless/realtek/rtlwifi/usb.c | 3 +++ drivers/net/wireless/realtek/rtlwifi/wifi.h | 1 + 5 files changed, 38 insertions(+) diff --git a/drivers/net/wireless/realtek/rtlwifi/core.c b/drivers/net/wireless/realtek/rtlwifi/core.c index 965bd9589045..ca47a70d9a86 100644 --- a/drivers/net/wireless/realtek/rtlwifi/core.c +++ b/drivers/net/wireless/realtek/rtlwifi/core.c @@ -1018,6 +1018,25 @@ static void send_beacon_frame(struct ieee80211_hw *hw, } } +void rtl_update_beacon_work_callback(struct work_struct *work) +{ + struct rtl_works *rtlworks = + container_of(work, struct rtl_works, update_beacon_work); + struct ieee80211_hw *hw = rtlworks->hw; + struct rtl_priv *rtlpriv = rtl_priv(hw); + struct ieee80211_vif *vif = rtlpriv->mac80211.vif; + + if (!vif) { + WARN_ONCE(true, "no vif to update beacon\n"); + return; + } + + mutex_lock(&rtlpriv->locks.conf_mutex); + send_beacon_frame(hw, vif); + mutex_unlock(&rtlpriv->locks.conf_mutex); +} +EXPORT_SYMBOL_GPL(rtl_update_beacon_work_callback); + static void rtl_op_bss_info_changed(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_bss_conf *bss_conf, @@ -1747,6 +1766,16 @@ static void rtl_op_flush(struct ieee80211_hw *hw, rtlpriv->intf_ops->flush(hw, queues, drop); } +static int rtl_op_set_tim(struct ieee80211_hw *hw, struct ieee80211_sta *sta, + bool set) +{ + struct rtl_priv *rtlpriv = rtl_priv(hw); + + schedule_work(&rtlpriv->works.update_beacon_work); + + return 0; +} + /* Description: * This routine deals with the Power Configuration CMD * parsing for RTL8723/RTL8188E Series IC. @@ -1903,6 +1932,7 @@ const struct ieee80211_ops rtl_ops = { .sta_add = rtl_op_sta_add, .sta_remove = rtl_op_sta_remove, .flush = rtl_op_flush, + .set_tim = rtl_op_set_tim, }; EXPORT_SYMBOL_GPL(rtl_ops); diff --git a/drivers/net/wireless/realtek/rtlwifi/core.h b/drivers/net/wireless/realtek/rtlwifi/core.h index 7447ff456710..345161b47442 100644 --- a/drivers/net/wireless/realtek/rtlwifi/core.h +++ b/drivers/net/wireless/realtek/rtlwifi/core.h @@ -60,5 +60,6 @@ void rtl_bb_delay(struct ieee80211_hw *hw, u32 addr, u32 data); bool rtl_cmd_send_packet(struct ieee80211_hw *hw, struct sk_buff *skb); bool rtl_btc_status_false(void); void rtl_dm_diginit(struct ieee80211_hw *hw, u32 cur_igval); +void rtl_update_beacon_work_callback(struct work_struct *work); #endif diff --git a/drivers/net/wireless/realtek/rtlwifi/pci.c b/drivers/net/wireless/realtek/rtlwifi/pci.c index 3776495fd9d0..c7365354737e 100644 --- a/drivers/net/wireless/realtek/rtlwifi/pci.c +++ b/drivers/net/wireless/realtek/rtlwifi/pci.c @@ -1200,6 +1200,8 @@ static void _rtl_pci_init_struct(struct ieee80211_hw *hw, _rtl_pci_prepare_bcn_tasklet); INIT_WORK(&rtlpriv->works.lps_change_work, rtl_lps_change_work_callback); + INIT_WORK(&rtlpriv->works.update_beacon_work, + rtl_update_beacon_work_callback); } static int _rtl_pci_init_tx_ring(struct ieee80211_hw *hw, @@ -1742,6 +1744,7 @@ static void rtl_pci_deinit(struct ieee80211_hw *hw) synchronize_irq(rtlpci->pdev->irq); tasklet_kill(&rtlpriv->works.irq_tasklet); cancel_work_sync(&rtlpriv->works.lps_change_work); + cancel_work_sync(&rtlpriv->works.update_beacon_work); flush_workqueue(rtlpriv->works.rtl_wq); destroy_workqueue(rtlpriv->works.rtl_wq); diff --git a/drivers/net/wireless/realtek/rtlwifi/usb.c b/drivers/net/wireless/realtek/rtlwifi/usb.c index 6c5e242b1bc5..b5e1f9403949 100644 --- a/drivers/net/wireless/realtek/rtlwifi/usb.c +++ b/drivers/net/wireless/realtek/rtlwifi/usb.c @@ -805,6 +805,7 @@ static void rtl_usb_stop(struct ieee80211_hw *hw) tasklet_kill(&rtlusb->rx_work_tasklet); cancel_work_sync(&rtlpriv->works.lps_change_work); + cancel_work_sync(&rtlpriv->works.update_beacon_work); flush_workqueue(rtlpriv->works.rtl_wq); @@ -1031,6 +1032,8 @@ int rtl_usb_probe(struct usb_interface *intf, rtl_fill_h2c_cmd_work_callback); INIT_WORK(&rtlpriv->works.lps_change_work, rtl_lps_change_work_callback); + INIT_WORK(&rtlpriv->works.update_beacon_work, + rtl_update_beacon_work_callback); rtlpriv->usb_data_index = 0; init_completion(&rtlpriv->firmware_loading_complete); diff --git a/drivers/net/wireless/realtek/rtlwifi/wifi.h b/drivers/net/wireless/realtek/rtlwifi/wifi.h index fdccfd29fd61..8152117c03ee 100644 --- a/drivers/net/wireless/realtek/rtlwifi/wifi.h +++ b/drivers/net/wireless/realtek/rtlwifi/wifi.h @@ -2487,6 +2487,7 @@ struct rtl_works { struct work_struct lps_change_work; struct work_struct fill_h2c_cmd; + struct work_struct update_beacon_work; }; struct rtl_debug { -- 2.21.0