• Emil Goode's avatar
    brcmsmac: fix deadlock on missing firmware · 8fc1e8c2
    Emil Goode authored
    When brcm80211 firmware is not installed networking hangs.
    A deadlock happens because we call ieee80211_unregister_hw()
    from the .start callback of struct ieee80211_ops. When .start
    is called we are under rtnl lock and ieee80211_unregister_hw()
    tries to take it again.
    
    Function call stack:
    
    dev_change_flags()
    	__dev_change_flags()
    		__dev_open()
    			ASSERT_RTNL() <-- Assert rtnl lock
    			ops->ndo_open()
    
    .ndo_open = ieee80211_open,
    
    ieee80211_open()
    	ieee80211_do_open()
    		drv_start()
    			local->ops->start()
    
    .start = brcms_ops_start,
    
    brcms_ops_start()
    	brcms_remove()
    		ieee80211_unregister_hw()
    			rtnl_lock() <-- Here we deadlock
    
    Introduced by:
    commit 25b5632f
    ("brcmsmac: request firmware in .start() callback")
    
    This patch fixes the bug by removing the call to brcms_remove()
    and moves the brcms_request_fw() call to the top of the .start
    callback to not initiate anything unless firmware is installed.
    Signed-off-by: default avatarEmil Goode <emilgoode@gmail.com>
    Signed-off-by: default avatarJohn W. Linville <linville@tuxdriver.com>
    8fc1e8c2
mac80211_if.c 42.6 KB