aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/uwb/lc-rc.c
diff options
context:
space:
mode:
authorDavid Vrabel <david.vrabel@csr.com>2008-11-07 13:19:19 -0500
committerDavid Vrabel <david.vrabel@csr.com>2008-11-07 13:19:19 -0500
commit58be81ed301d96045bca2b85f3b838910efcfde4 (patch)
treed65d13f757652cd2126b43449727c2a1f40ab551 /drivers/uwb/lc-rc.c
parent307ba6dd73254fe7d2ce27db64ffd90e1bb3c6c0 (diff)
uwb: fix races between events and neh timers
Always use del_timer_sync() before freeing nehs. Destroy all nehs after stopping the radio controller and before cleaning up the reservation manager. Handle the timer running after an event has removed the neh. This fixes various oopses that may occur if a radio controller is removed while a neh timer is still active. Signed-off-by: David Vrabel <david.vrabel@csr.com>
Diffstat (limited to 'drivers/uwb/lc-rc.c')
-rw-r--r--drivers/uwb/lc-rc.c5
1 files changed, 3 insertions, 2 deletions
diff --git a/drivers/uwb/lc-rc.c b/drivers/uwb/lc-rc.c
index 38e3d57ec8f7..f00633d334dd 100644
--- a/drivers/uwb/lc-rc.c
+++ b/drivers/uwb/lc-rc.c
@@ -79,7 +79,6 @@ static void uwb_rc_sys_release(struct device *dev)
79 struct uwb_dev *uwb_dev = container_of(dev, struct uwb_dev, dev); 79 struct uwb_dev *uwb_dev = container_of(dev, struct uwb_dev, dev);
80 struct uwb_rc *rc = container_of(uwb_dev, struct uwb_rc, uwb_dev); 80 struct uwb_rc *rc = container_of(uwb_dev, struct uwb_rc, uwb_dev);
81 81
82 uwb_rc_neh_destroy(rc);
83 uwb_rc_ie_release(rc); 82 uwb_rc_ie_release(rc);
84 kfree(rc); 83 kfree(rc);
85} 84}
@@ -311,7 +310,7 @@ void uwb_rc_rm(struct uwb_rc *rc)
311 rc->ready = 0; 310 rc->ready = 0;
312 311
313 uwb_dbg_del_rc(rc); 312 uwb_dbg_del_rc(rc);
314 uwb_rsv_cleanup(rc); 313 uwb_rsv_remove_all(rc);
315 uwb_rc_ie_rm(rc, UWB_IDENTIFICATION_IE); 314 uwb_rc_ie_rm(rc, UWB_IDENTIFICATION_IE);
316 if (rc->beaconing >= 0) 315 if (rc->beaconing >= 0)
317 uwb_rc_beacon(rc, -1, 0); 316 uwb_rc_beacon(rc, -1, 0);
@@ -322,6 +321,7 @@ void uwb_rc_rm(struct uwb_rc *rc)
322 rc->stop(rc); 321 rc->stop(rc);
323 322
324 uwbd_stop(rc); 323 uwbd_stop(rc);
324 uwb_rc_neh_destroy(rc);
325 325
326 uwb_dev_lock(&rc->uwb_dev); 326 uwb_dev_lock(&rc->uwb_dev);
327 rc->priv = NULL; 327 rc->priv = NULL;
@@ -331,6 +331,7 @@ void uwb_rc_rm(struct uwb_rc *rc)
331 uwb_dev_for_each(rc, uwb_dev_offair_helper, NULL); 331 uwb_dev_for_each(rc, uwb_dev_offair_helper, NULL);
332 __uwb_rc_sys_rm(rc); 332 __uwb_rc_sys_rm(rc);
333 mutex_unlock(&rc->uwb_beca.mutex); 333 mutex_unlock(&rc->uwb_beca.mutex);
334 uwb_rsv_cleanup(rc);
334 uwb_beca_release(rc); 335 uwb_beca_release(rc);
335 uwb_dev_rm(&rc->uwb_dev); 336 uwb_dev_rm(&rc->uwb_dev);
336} 337}