diff options
| author | Himanshu Agarwal <himanaga@qti.qualcomm.com> | 2015-12-10 12:52:38 +0530 |
|---|---|---|
| committer | Anjaneedevi Kapparapu <akappa@codeaurora.org> | 2015-12-16 12:38:42 +0530 |
| commit | 8ecaa7bd0d402652a896c02e516e2db8d866ffdd (patch) | |
| tree | 37bd58a125074cdbb91960da84d3456e8e8960d0 | |
| parent | bb00dc469d0c76eeb50925b6674597950a1cd6ef (diff) | |
qcacld-2.0: Avoid double free of vdev
Due to a race condition, vdev is getting deleted in
ol_txrx_vdev_detach and after that in
ol_txrx_peer_unref_delete, as vdev->delete.pending
is not equal to 0 as it is some garbage value, vdev
is getting deleted again causing crash.
This fix release the lock after checking
vdev->delete.pending so that before vdev gets deleted
in ol_txrx_vdev_detach, this check has been made and as
vdev->delete.pending is 0, it will not delete the
vdev in ol_txrx_peer_unref_delete and so vdev will be
deleted only once.
Change-Id: I4a7362b0e226c66ccb7c72243276d77e8df60b20
CRs-Fixed: 949397
| -rw-r--r-- | CORE/CLD_TXRX/TXRX/ol_txrx.c | 15 |
1 files changed, 9 insertions, 6 deletions
diff --git a/CORE/CLD_TXRX/TXRX/ol_txrx.c b/CORE/CLD_TXRX/TXRX/ol_txrx.c index 74369051e810..48c328ff111d 100644 --- a/CORE/CLD_TXRX/TXRX/ol_txrx.c +++ b/CORE/CLD_TXRX/TXRX/ol_txrx.c @@ -1693,18 +1693,19 @@ ol_txrx_peer_unref_delete(ol_txrx_peer_handle peer) /* check whether the parent vdev has no peers left */ if (TAILQ_EMPTY(&vdev->peer_list)) { /* - * Now that there are no references to the peer, we can - * release the peer reference lock. - */ - adf_os_spin_unlock_bh(&pdev->peer_ref_mutex); - /* * Check if the parent vdev was waiting for its peers to be * deleted, in order for it to be deleted too. */ - if (vdev->delete.pending) { + if (vdev->delete.pending == 1) { ol_txrx_vdev_delete_cb vdev_delete_cb = vdev->delete.callback; void *vdev_delete_context = vdev->delete.context; + /* + * Now that there are no references to the peer, we can + * release the peer reference lock. + */ + adf_os_spin_unlock_bh(&pdev->peer_ref_mutex); + TXRX_PRINT(TXRX_PRINT_LEVEL_INFO1, "%s: deleting vdev object %p " "(%02x:%02x:%02x:%02x:%02x:%02x)" @@ -1718,6 +1719,8 @@ ol_txrx_peer_unref_delete(ol_txrx_peer_handle peer) if (vdev_delete_cb) { vdev_delete_cb(vdev_delete_context); } + } else { + adf_os_spin_unlock_bh(&pdev->peer_ref_mutex); } } else { adf_os_spin_unlock_bh(&pdev->peer_ref_mutex); |
