From 3e59ce0fde3735d6e35be08b3d766031913bfb68 Mon Sep 17 00:00:00 2001 From: Dmitry Shmidt Date: Fri, 23 Sep 2011 13:52:01 -0700 Subject: [PATCH] net: wireless: bcmdhd: Remove unnecessary rtnl_lock() calls Signed-off-by: Dmitry Shmidt --- drivers/net/wireless/bcmdhd/wl_cfg80211.c | 84 +++++++++++++---------- 1 file changed, 49 insertions(+), 35 deletions(-) diff --git a/drivers/net/wireless/bcmdhd/wl_cfg80211.c b/drivers/net/wireless/bcmdhd/wl_cfg80211.c index 4fd9893970f3..65c48063879d 100644 --- a/drivers/net/wireless/bcmdhd/wl_cfg80211.c +++ b/drivers/net/wireless/bcmdhd/wl_cfg80211.c @@ -809,6 +809,8 @@ wl_cfg80211_add_virtual_iface(struct wiphy *wiphy, char *name, struct net_device *_ndev; dhd_pub_t *dhd = (dhd_pub_t *)(wl->pub); int (*net_attach)(dhd_pub_t *dhdp, int ifidx); + bool rollback_lock = false; + WL_DBG(("if name: %s, type: %d\n", name, type)); switch (type) { case NL80211_IFTYPE_ADHOC: @@ -845,7 +847,11 @@ wl_cfg80211_add_virtual_iface(struct wiphy *wiphy, char *name, /* wait till IF_DEL is complete * release the lock for the unregister to proceed */ - rtnl_unlock(); + /* put back the rtnl_lock again */ + if (rtnl_is_locked()) { + rtnl_unlock(); + rollback_lock = true; + } WL_INFO(("%s: Released the lock and wait till IF_DEL is complete\n", __func__)); timeout = wait_event_interruptible_timeout(wl->dongle_event_wait, @@ -853,7 +859,10 @@ wl_cfg80211_add_virtual_iface(struct wiphy *wiphy, char *name, msecs_to_jiffies(MAX_WAIT_TIME)); /* put back the rtnl_lock again */ - rtnl_lock(); + if (rollback_lock) { + rtnl_lock(); + rollback_lock = false; + } if (timeout > 0) { WL_ERR(("IF DEL is Success\n")); @@ -911,15 +920,23 @@ wl_cfg80211_add_virtual_iface(struct wiphy *wiphy, char *name, wl->p2p->vif_created = true; set_mode_by_netdev(wl, _ndev, mode); net_attach = wl_to_p2p_bss_private(wl, P2PAPI_BSSCFG_CONNECTION); - rtnl_unlock(); + /* put back the rtnl_lock again */ + if (rtnl_is_locked()) { + rtnl_unlock(); + rollback_lock = true; + } if (net_attach && !net_attach(dhd, _ndev->ifindex)) WL_DBG((" virtual interface(%s) is " "created net attach done\n", wl->p2p->vir_ifname)); else { - rtnl_lock(); + /* put back the rtnl_lock again */ + if (rollback_lock) + rtnl_lock(); goto fail; } - rtnl_lock(); + /* put back the rtnl_lock again */ + if (rollback_lock) + rtnl_lock(); return _ndev; } else { @@ -1811,6 +1828,7 @@ wl_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev, struct cfg80211_ssid ssid; s32 scan_retry = 0; s32 err = 0; + bool rollback_lock = false; WL_TRACE(("In\n")); CHECK_SYS_UP(wl); @@ -1832,11 +1850,15 @@ wl_cfg80211_join_ibss(struct wiphy *wiphy, struct net_device *dev, } } while (++scan_retry < WL_SCAN_RETRY_MAX); /* to allow scan_inform to propagate to cfg80211 plane */ - rtnl_unlock(); + if (rtnl_is_locked()) { + rtnl_unlock(); + rollback_lock = true; + } /* wait 4 secons till scan done.... */ schedule_timeout_interruptible(4 * HZ); - rtnl_lock(); + if (rollback_lock) + rtnl_lock(); bss = cfg80211_get_ibss(wiphy, NULL, params->ssid, params->ssid_len); } @@ -4573,7 +4595,7 @@ static s32 wl_update_bss_info(struct wl_priv *wl, struct net_device *ndev) ssid->SSID, ssid->SSID_len, WLAN_CAPABILITY_ESS, WLAN_CAPABILITY_ESS); - rtnl_lock(); + mutex_lock(&wl->usr_sync); if (unlikely(!bss)) { WL_DBG(("Could not find the AP\n")); *(u32 *) wl->extra_buf = htod32(WL_EXTRA_BUF_MAX); @@ -4624,7 +4646,7 @@ static s32 wl_update_bss_info(struct wl_priv *wl, struct net_device *ndev) wl_update_prof(wl, NULL, &dtim_period, WL_PROF_DTIMPERIOD); update_bss_info_out: - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); return err; } @@ -4696,7 +4718,7 @@ wl_notify_mic_status(struct wl_priv *wl, struct net_device *ndev, u16 flags = ntoh16(e->flags); enum nl80211_key_type key_type; - rtnl_lock(); + mutex_lock(&wl->usr_sync); if (flags & WLC_EVENT_MSG_GROUP) key_type = NL80211_KEYTYPE_GROUP; else @@ -4704,7 +4726,7 @@ wl_notify_mic_status(struct wl_priv *wl, struct net_device *ndev, cfg80211_michael_mic_failure(ndev, (u8 *)&e->addr, key_type, -1, NULL, GFP_KERNEL); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); return 0; } @@ -4723,8 +4745,8 @@ wl_notify_scan_status(struct wl_priv *wl, struct net_device *ndev, if (wl->iscan_on && wl->iscan_kickstart) return wl_wakeup_iscan(wl_to_iscan(wl)); + mutex_lock(&wl->usr_sync); wl_clr_drv_status(wl, SCANNING); - rtnl_lock(); err = wldev_ioctl(ndev, WLC_GET_CHANNEL, &channel_inform, sizeof(channel_inform), false); if (unlikely(err)) { @@ -4762,7 +4784,7 @@ scan_done_out: wl->scan_request = NULL; } dhd_os_spin_unlock((dhd_pub_t *)(wl->pub), flags); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); return err; } static s32 @@ -5132,10 +5154,10 @@ static s32 wl_iscan_done(struct wl_priv *wl) s32 err = 0; iscan->state = WL_ISCAN_STATE_IDLE; - rtnl_lock(); + mutex_lock(&wl->usr_sync); wl_inform_bss(wl); wl_notify_iscan_complete(iscan, false); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); return err; } @@ -5157,10 +5179,10 @@ static s32 wl_iscan_inprogress(struct wl_priv *wl) struct wl_iscan_ctrl *iscan = wl->iscan; s32 err = 0; - rtnl_lock(); + mutex_lock(&wl->usr_sync); wl_inform_bss(wl); wl_run_iscan(iscan, NULL, WL_SCAN_ACTION_CONTINUE); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); /* Reschedule the timer */ mod_timer(&iscan->timer, jiffies + iscan->timer_ms * HZ / 1000); iscan->timer_on = 1; @@ -5174,9 +5196,9 @@ static s32 wl_iscan_aborted(struct wl_priv *wl) s32 err = 0; iscan->state = WL_ISCAN_STATE_IDLE; - rtnl_lock(); + mutex_lock(&wl->usr_sync); wl_notify_iscan_complete(iscan, true); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); return err; } @@ -5199,13 +5221,13 @@ static s32 wl_iscan_thread(void *data) del_timer_sync(&iscan->timer); iscan->timer_on = 0; } - rtnl_lock(); + mutex_lock(&wl->usr_sync); err = wl_get_iscan_results(iscan, &status, &wl->bss_list); if (unlikely(err)) { status = WL_SCAN_RESULTS_ABORTED; WL_ERR(("Abort iscan\n")); } - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); iscan->iscan_handler[status] (wl); } if (iscan->timer_on) { @@ -5366,37 +5388,37 @@ static s32 wl_escan_handler(struct wl_priv *wl, else if (status == WLC_E_STATUS_SUCCESS) { wl->escan_info.escan_state = WL_ESCAN_STATE_IDLE; if (likely(wl->scan_request)) { - rtnl_lock(); + mutex_lock(&wl->usr_sync); del_timer_sync(&wl->scan_timeout); WL_INFO(("ESCAN COMPLETED\n")); wl->bss_list = (wl_scan_results_t *)wl->escan_info.escan_buf; wl_inform_bss(wl); wl_notify_escan_complete(wl, false); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); } } else if (status == WLC_E_STATUS_ABORT) { wl->escan_info.escan_state = WL_ESCAN_STATE_IDLE; if (likely(wl->scan_request)) { - rtnl_lock(); + mutex_lock(&wl->usr_sync); del_timer_sync(&wl->scan_timeout); WL_INFO(("ESCAN ABORTED\n")); wl->bss_list = (wl_scan_results_t *)wl->escan_info.escan_buf; wl_inform_bss(wl); wl_notify_escan_complete(wl, true); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); } } else { WL_ERR(("unexpected Escan Event %d : abort\n", status)); wl->escan_info.escan_state = WL_ESCAN_STATE_IDLE; if (likely(wl->scan_request)) { - rtnl_lock(); + mutex_lock(&wl->usr_sync); del_timer_sync(&wl->scan_timeout); wl->bss_list = (wl_scan_results_t *)wl->escan_info.escan_buf; wl_inform_bss(wl); wl_notify_escan_complete(wl, true); - rtnl_unlock(); + mutex_unlock(&wl->usr_sync); } } exit: @@ -6988,10 +7010,6 @@ wl_cfg80211_bt_setflag(struct net_device *dev, bool set) char buf_flag7_default[8] = { 7, 00, 00, 00, 0x0, 0x00, 0x00, 0x00}; #endif -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 27)) - rtnl_lock(); -#endif - #if defined(BT_DHCP_eSCO_FIX) /* set = 1, save & turn on 0 - off & restore prev settings */ set_btc_esco_params(dev, set); @@ -7010,10 +7028,6 @@ wl_cfg80211_bt_setflag(struct net_device *dev, bool set) (char *)&buf_flag7_default[0], sizeof(buf_flag7_default)); #endif - -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2, 6, 27)) - rtnl_unlock(); -#endif } static void wl_cfg80211_bt_timerfunc(ulong data) -- 2.34.1