NFC: llcp: Clean local timers and works when removing a device
Whenever an adapter is removed we must clean all the local structures, especially the timers and scheduled work. Otherwise those asynchronous threads will eventually try to access the freed nfc_dev pointer if an LLCP link is up. Signed-off-by: Samuel Ortiz <sameo@linux.intel.com>
This commit is contained in:
Родитель
b141e811a0
Коммит
3536da06db
|
@ -142,6 +142,17 @@ struct nfc_llcp_local *nfc_llcp_local_get(struct nfc_llcp_local *local)
|
|||
return local;
|
||||
}
|
||||
|
||||
static void local_cleanup(struct nfc_llcp_local *local, bool listen)
|
||||
{
|
||||
nfc_llcp_socket_release(local, listen);
|
||||
del_timer_sync(&local->link_timer);
|
||||
skb_queue_purge(&local->tx_queue);
|
||||
cancel_work_sync(&local->tx_work);
|
||||
cancel_work_sync(&local->rx_work);
|
||||
cancel_work_sync(&local->timeout_work);
|
||||
kfree_skb(local->rx_pending);
|
||||
}
|
||||
|
||||
static void local_release(struct kref *ref)
|
||||
{
|
||||
struct nfc_llcp_local *local;
|
||||
|
@ -149,13 +160,7 @@ static void local_release(struct kref *ref)
|
|||
local = container_of(ref, struct nfc_llcp_local, ref);
|
||||
|
||||
list_del(&local->list);
|
||||
nfc_llcp_socket_release(local, false);
|
||||
del_timer_sync(&local->link_timer);
|
||||
skb_queue_purge(&local->tx_queue);
|
||||
cancel_work_sync(&local->tx_work);
|
||||
cancel_work_sync(&local->rx_work);
|
||||
cancel_work_sync(&local->timeout_work);
|
||||
kfree_skb(local->rx_pending);
|
||||
local_cleanup(local, false);
|
||||
kfree(local);
|
||||
}
|
||||
|
||||
|
@ -1427,6 +1432,8 @@ void nfc_llcp_unregister_device(struct nfc_dev *dev)
|
|||
return;
|
||||
}
|
||||
|
||||
local_cleanup(local, false);
|
||||
|
||||
nfc_llcp_local_put(local);
|
||||
}
|
||||
|
||||
|
|
Загрузка…
Ссылка в новой задаче