From f9b5466cb6ce2e12689f6764a16a1e87712ed0de Mon Sep 17 00:00:00 2001 From: Pankaj Singh Date: Wed, 8 Jul 2020 18:47:16 +0530 Subject: [PATCH] qcacld-3.0: TDLS not releasing the vdev ref taken with WLAN_TDLS_NB_ID During NAN+TDLS case, when NAN is present dut is trying to add TDLS peer and the ref is not released which results in assert due to obj delete timeout. Fix is to release the ref taken properly in default handing of tdls serialization cmd and error handling. Change-ID: Ia1ff16fdde7f70e45b712d260c1eca372ceb947e CRs-Fixed: 2727206 --- .../tdls/core/src/wlan_tdls_cmds_process.c | 57 ++++--------------- .../tdls/dispatcher/src/wlan_tdls_ucfg_api.c | 4 +- 2 files changed, 15 insertions(+), 46 deletions(-) diff --git a/components/tdls/core/src/wlan_tdls_cmds_process.c b/components/tdls/core/src/wlan_tdls_cmds_process.c index d12014dfea6c..9437f27ea30b 100644 --- a/components/tdls/core/src/wlan_tdls_cmds_process.c +++ b/components/tdls/core/src/wlan_tdls_cmds_process.c @@ -813,7 +813,7 @@ QDF_STATUS tdls_process_add_peer(struct tdls_add_peer_request *req) if (!req || !req->vdev) { tdls_err("req: %pK", req); - goto error; + goto free_req; } vdev = req->vdev; psoc = wlan_vdev_get_psoc(vdev); @@ -848,26 +848,16 @@ QDF_STATUS tdls_process_add_peer(struct tdls_add_peer_request *req) case WLAN_SER_CMD_ACTIVE: /* command moved to active list. Do nothing */ break; - case WLAN_SER_CMD_DENIED_LIST_FULL: - case WLAN_SER_CMD_DENIED_RULES_FAILED: - case WLAN_SER_CMD_DENIED_UNSPECIFIED: - /* notify os interface about internal error*/ - status = tdls_internal_add_peer_rsp(req, QDF_STATUS_E_FAILURE); - wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); - /* cmd can't be serviced. - * release tdls_add_peer_request memory - */ - qdf_mem_free(req); - break; default: - QDF_ASSERT(0); - status = QDF_STATUS_E_INVAL; goto error; } return status; error: + /* notify os interface about internal error*/ status = tdls_internal_add_peer_rsp(req, QDF_STATUS_E_FAILURE); + wlan_objmgr_vdev_release_ref(req->vdev, WLAN_TDLS_NB_ID); +free_req: qdf_mem_free(req); return status; } @@ -1038,7 +1028,7 @@ QDF_STATUS tdls_process_update_peer(struct tdls_update_peer_request *req) if (!req || !req->vdev) { tdls_err("req: %pK", req); status = QDF_STATUS_E_FAILURE; - goto error; + goto free_req; } vdev = req->vdev; @@ -1063,27 +1053,16 @@ QDF_STATUS tdls_process_update_peer(struct tdls_update_peer_request *req) case WLAN_SER_CMD_ACTIVE: /* command moved to active list. Do nothing */ break; - case WLAN_SER_CMD_DENIED_LIST_FULL: - case WLAN_SER_CMD_DENIED_RULES_FAILED: - case WLAN_SER_CMD_DENIED_UNSPECIFIED: - /* notify os interface about internal error*/ - status = tdls_internal_update_peer_rsp(req, - QDF_STATUS_E_FAILURE); - wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); - /* cmd can't be serviced. - * release tdls_add_peer_request memory - */ - qdf_mem_free(req); - break; default: - QDF_ASSERT(0); - status = QDF_STATUS_E_INVAL; - break; + goto error; } return status; error: + /* notify os interface about internal error*/ status = tdls_internal_update_peer_rsp(req, QDF_STATUS_E_FAILURE); + wlan_objmgr_vdev_release_ref(req->vdev, WLAN_TDLS_NB_ID); +free_req: qdf_mem_free(req); return status; } @@ -1222,27 +1201,15 @@ QDF_STATUS tdls_process_del_peer(struct tdls_oper_request *req) case WLAN_SER_CMD_ACTIVE: /* command moved to active list. Do nothing */ break; - case WLAN_SER_CMD_DENIED_LIST_FULL: - case WLAN_SER_CMD_DENIED_RULES_FAILED: - case WLAN_SER_CMD_DENIED_UNSPECIFIED: - /* notify os interface about internal error*/ - status = tdls_internal_del_peer_rsp(req); - wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); - /* cmd can't be serviced. - * release tdls_add_peer_request memory - */ - qdf_mem_free(req); - break; default: - QDF_ASSERT(0); - status = QDF_STATUS_E_INVAL; - break; + goto error; } return status; error: + /* notify os interface about internal error*/ status = tdls_internal_del_peer_rsp(req); - wlan_objmgr_vdev_release_ref(vdev, WLAN_TDLS_NB_ID); + wlan_objmgr_vdev_release_ref(req->vdev, WLAN_TDLS_NB_ID); free_req: qdf_mem_free(req); return status; diff --git a/components/tdls/dispatcher/src/wlan_tdls_ucfg_api.c b/components/tdls/dispatcher/src/wlan_tdls_ucfg_api.c index 57f9df5ff212..9a1a5527f3b8 100644 --- a/components/tdls/dispatcher/src/wlan_tdls_ucfg_api.c +++ b/components/tdls/dispatcher/src/wlan_tdls_ucfg_api.c @@ -857,8 +857,10 @@ QDF_STATUS ucfg_tdls_notify_sta_disconnect( tdls_debug("Enter "); notify = qdf_mem_malloc(sizeof(*notify)); - if (!notify) + if (!notify) { + wlan_objmgr_vdev_release_ref(notify->vdev, WLAN_TDLS_NB_ID); return QDF_STATUS_E_NULL_VALUE; + } *notify = *notify_info;