diff --git a/Kbuild b/Kbuild index 784a381ff2..881f82d5ce 100644 --- a/Kbuild +++ b/Kbuild @@ -745,6 +745,20 @@ CDS_OBJS := $(CDS_SRC_DIR)/cds_api.o \ $(CDS_SRC_DIR)/cds_utils.o +###### UMAC OBJMGR ######## +UMAC_OBJMGR_DIR := $(WLAN_COMMON_ROOT)/umac/cmn_services/obj_mgr + +UMAC_OBJMGR_INC := -I$(WLAN_COMMON_INC)/umac/cmn_services/obj_mgr/inc \ + -I$(WLAN_COMMON_INC)/umac/cmn_services/obj_mgr/src \ + -I$(WLAN_COMMON_INC)/umac/cmn_services/inc \ + -I$(WLAN_COMMON_INC)/umac/global_umac_dispatcher/lmac_if/inc + +UMAC_OBJMGR_OBJS := $(UMAC_OBJMGR_DIR)/src/wlan_objmgr_global_obj.o \ + $(UMAC_OBJMGR_DIR)/src/wlan_objmgr_pdev_obj.o \ + $(UMAC_OBJMGR_DIR)/src/wlan_objmgr_peer_obj.o \ + $(UMAC_OBJMGR_DIR)/src/wlan_objmgr_psoc_obj.o \ + $(UMAC_OBJMGR_DIR)/src/wlan_objmgr_vdev_obj.o + ########### BMI ########### BMI_DIR := core/bmi @@ -1090,6 +1104,7 @@ INCS += $(HIF_INC) \ $(BMI_INC) \ $(HAL_INC) +INCS += $(UMAC_OBJMGR_INC) INCS += $(TARGET_INC) INCS += $(NLINK_INC) \ @@ -1134,6 +1149,7 @@ OBJS += $(HIF_OBJS) \ $(HTT_OBJS) \ $(HAL_OBJS) +OBJS += $(UMAC_OBJMGR_OBJS) OBJS += $(WLAN_LOGGING_OBJS) OBJS += $(NLINK_OBJS) OBJS += $(PTT_OBJS) diff --git a/core/cds/inc/cds_api.h b/core/cds/inc/cds_api.h index 0f2456bb68..52532a2a15 100644 --- a/core/cds/inc/cds_api.h +++ b/core/cds/inc/cds_api.h @@ -48,6 +48,7 @@ #include #include #include +#include /* Amount of time to wait for WMA to perform an asynchronous activity. * This value should be larger than the timeout used by WMI to wait for @@ -200,11 +201,11 @@ void cds_deinit(void); QDF_STATUS cds_pre_enable(v_CONTEXT_t cds_context); -QDF_STATUS cds_open(void); +QDF_STATUS cds_open(struct wlan_objmgr_psoc *psoc); -QDF_STATUS cds_enable(v_CONTEXT_t cds_context); +QDF_STATUS cds_enable(struct wlan_objmgr_psoc *psoc, v_CONTEXT_t cds_context); -QDF_STATUS cds_disable(v_CONTEXT_t cds_context); +QDF_STATUS cds_disable(struct wlan_objmgr_psoc *psoc, v_CONTEXT_t cds_context); /** * cds_flush_cache_rx_queue() - flush cache rx queue frame @@ -215,7 +216,7 @@ void cds_flush_cache_rx_queue(void); QDF_STATUS cds_post_disable(v_CONTEXT_t cds_context); -QDF_STATUS cds_close(v_CONTEXT_t cds_context); +QDF_STATUS cds_close(struct wlan_objmgr_psoc *psoc, v_CONTEXT_t cds_context); void *cds_get_context(QDF_MODULE_ID moduleId); diff --git a/core/cds/src/cds_api.c b/core/cds/src/cds_api.c index 75560a8bdd..d5ed6c4175 100644 --- a/core/cds/src/cds_api.c +++ b/core/cds/src/cds_api.c @@ -263,7 +263,7 @@ static QDF_STATUS cds_deregister_all_modules(void) * * Return: QDF status */ -QDF_STATUS cds_open(void) +QDF_STATUS cds_open(struct wlan_objmgr_psoc *psoc) { QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; tSirRetStatus sirStatus = eSIR_SUCCESS; @@ -386,7 +386,7 @@ QDF_STATUS cds_open(void) } /*Open the WMA module */ - qdf_status = wma_open(gp_cds_context, + qdf_status = wma_open(psoc, gp_cds_context, hdd_update_tgt_cfg, hdd_dfs_indicate_radar, cds_cfg); @@ -443,7 +443,7 @@ QDF_STATUS cds_open(void) /* Now proceed to open the MAC */ sirStatus = - mac_open(&(gp_cds_context->pMACContext), + mac_open(psoc, &(gp_cds_context->pMACContext), gp_cds_context->pHDDContext, cds_cfg); if (eSIR_SUCCESS != sirStatus) { @@ -481,8 +481,7 @@ QDF_STATUS cds_open(void) "%s: CDS successfully Opened", __func__); cds_register_all_modules(); - dispatcher_psoc_open(); - + dispatcher_psoc_open(psoc); return QDF_STATUS_SUCCESS; err_sme_close: @@ -639,11 +638,12 @@ QDF_STATUS cds_pre_enable(v_CONTEXT_t cds_context) /** * cds_enable() - start/enable cds module + * @psoc: Psoc pointer * @cds_context: CDS context * * Return: QDF status */ -QDF_STATUS cds_enable(v_CONTEXT_t cds_context) +QDF_STATUS cds_enable(struct wlan_objmgr_psoc *psoc, v_CONTEXT_t cds_context) { QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; tSirRetStatus sirStatus = eSIR_SUCCESS; @@ -729,7 +729,7 @@ QDF_STATUS cds_enable(v_CONTEXT_t cds_context) QDF_TRACE(QDF_MODULE_ID_QDF, QDF_TRACE_LEVEL_INFO, "%s: CDS Start is successful!!", __func__); - dispatcher_psoc_enable(); + dispatcher_psoc_enable(psoc); return QDF_STATUS_SUCCESS; @@ -776,11 +776,12 @@ err_wma_stop: /** * cds_disable() - stop/disable cds module + * @psoc: Psoc pointer * @cds_context: CDS context * * Return: QDF status */ -QDF_STATUS cds_disable(v_CONTEXT_t cds_context) +QDF_STATUS cds_disable(struct wlan_objmgr_psoc *psoc, v_CONTEXT_t cds_context) { QDF_STATUS qdf_status; void *handle; @@ -790,8 +791,8 @@ QDF_STATUS cds_disable(v_CONTEXT_t cds_context) * ongoing transaction with FW. Always keep it before wma_stop() as * wma_stop() does target PDEV suspend. */ - dispatcher_psoc_disable(); + dispatcher_psoc_disable(psoc); qdf_status = wma_stop(cds_context, HAL_STOP_TYPE_RF_KILL); @@ -883,6 +884,7 @@ QDF_STATUS cds_post_disable(v_CONTEXT_t cds_context) /** * cds_close() - close cds module + * @psoc: Psoc pointer * @cds_context: CDS context * * This API allows user to close modules registered @@ -890,7 +892,7 @@ QDF_STATUS cds_post_disable(v_CONTEXT_t cds_context) * * Return: QDF status */ -QDF_STATUS cds_close(v_CONTEXT_t cds_context) +QDF_STATUS cds_close(struct wlan_objmgr_psoc *psoc, v_CONTEXT_t cds_context) { QDF_STATUS qdf_status; @@ -977,7 +979,7 @@ QDF_STATUS cds_close(v_CONTEXT_t cds_context) cds_deregister_all_modules(); - dispatcher_psoc_close(); + dispatcher_psoc_close(psoc); return QDF_STATUS_SUCCESS; } diff --git a/core/hdd/inc/wlan_hdd_main.h b/core/hdd/inc/wlan_hdd_main.h index 8d4898bc75..7782766d6c 100644 --- a/core/hdd/inc/wlan_hdd_main.h +++ b/core/hdd/inc/wlan_hdd_main.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2012-2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2012-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -64,6 +64,12 @@ #include #include "wlan_hdd_nan_datapath.h" #include "wlan_tgt_def_config.h" +#include +#include +#include +#include +#include +#include /*--------------------------------------------------------------------------- Preprocessor definitions and constants @@ -267,6 +273,9 @@ /* session ID invalid */ #define HDD_SESSION_ID_INVALID 0xFF +/* Default Psoc id */ +#define DEFAULT_PSOC_ID 1 + /* * Generic asynchronous request/response support * @@ -903,6 +912,7 @@ struct hdd_adapter_s { uint32_t magic; void *pHddCtx; + struct wlan_objmgr_vdev *hdd_vdev; void *txrx_vdev; @@ -1299,6 +1309,9 @@ struct hdd_context_s { /** Global CDS context */ v_CONTEXT_t pcds_context; + struct wlan_objmgr_psoc *hdd_psoc; + struct wlan_objmgr_pdev *hdd_pdev; + /** HAL handle...*/ tHalHandle hHal; @@ -1994,4 +2007,98 @@ static inline int wlan_hdd_validate_session_id(u8 session_id) bool hdd_is_roaming_in_progress(void); void hdd_set_roaming_in_progress(bool value); +/** + * hdd_create_and_store_psoc() - Create psoc object and store in hdd context + * @hdd_ctx: Hdd context + * @psoc_id: Psoc Id + * + * This API creates Psoc object with given @psoc_id and store the psoc reference + * to hdd context + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_create_and_store_psoc(hdd_context_t *hdd_ctx, uint8_t psoc_id); + +/** + * hdd_destroy_and_release_psoc() - Deletes the psoc object + * @hdd_ctx: Hdd context + * + * This API deletes psoc object and release its reference from hdd context + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_destroy_and_release_psoc(hdd_context_t *hdd_ctx); + +/** + * hdd_create_and_store_pdev() - Create pdev object and store in hdd context + * @hdd_ctx: Hdd context + * + * This API creates the pdev object and store the pdev reference to hdd context + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_create_and_store_pdev(hdd_context_t *hdd_ctx); + +/** + * hdd_destroy_and_release_pdev() - Deletes the pdev object + * @hdd_ctx: Hdd context + * + * This API deletes pdev object and release its reference from hdd context + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_destroy_and_release_pdev(hdd_context_t *hdd_ctx); + +/** + * hdd_create_and_store_vdev() - Create vdev object and store in hdd adapter + * @pdev: pdev pointer + * @adapter: hdd adapter + * + * This API creates the vdev object and store the vdev reference to the + * given @adapter. Also, creates a self peer for the vdev. If the adapter + * session id and vdev id of the new vdev object doesnot match, destroys the + * created vdev object and returns failure + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_create_and_store_vdev(struct wlan_objmgr_pdev *pdev, + hdd_adapter_t *adapter); + +/** + * hdd_destroy_and_release_vdev() - Delete the vdev object + * @hdd_ctx: Hdd context + * + * This API deletes vdev object and release its reference from hdd adapter + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_destroy_and_release_vdev(hdd_adapter_t *adapter); + +/** + * hdd_add_peer_object() - Create and add the peer object to the vdev + * @vdev: vdev pointer + * @adapter_mode: adapter mode + * @mac_addr: Peer mac address + * + * This API creates and adds the peer object to the given @vdev. The peer type + * (STA, AP or IBSS) is assigned based on adapter mode. For example, if adapter + * mode is STA, peer is AP. + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_add_peer_object(struct wlan_objmgr_vdev *vdev, + enum tQDF_ADAPTER_MODE adapter_mode, + uint8_t *mac_addr); + +/** + * hdd_remove_peer_object() - Delete and remove the peer from vdev + * @vdev: vdev pointer + * @mac_addr: Peer Mac address + * + * This API finds the peer object from given @mac_addr and deletes the same. + * + * Return: QDF_STATUS + */ +QDF_STATUS hdd_remove_peer_object(struct wlan_objmgr_vdev *vdev, + uint8_t *mac_addr); #endif /* end #if !defined(WLAN_HDD_MAIN_H) */ diff --git a/core/hdd/src/wlan_hdd_assoc.c b/core/hdd/src/wlan_hdd_assoc.c index 8619629a1e..3220136d38 100644 --- a/core/hdd/src/wlan_hdd_assoc.c +++ b/core/hdd/src/wlan_hdd_assoc.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2012-2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2012-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -1190,6 +1190,7 @@ static void hdd_send_association_event(struct net_device *dev, int we_event; char *msg; struct qdf_mac_addr peerMacAddr; + QDF_STATUS qdf_status; /* Added to find the auth type on the fly at run time */ /* rather than with cfg to see if FT is enabled */ @@ -1272,6 +1273,14 @@ static void hdd_send_association_event(struct net_device *dev, pCsrRoamInfo->chan_info.reg_info_1; chan_info.reg_info_2 = pCsrRoamInfo->chan_info.reg_info_2; + + qdf_status = hdd_add_peer_object(pAdapter->hdd_vdev, + pAdapter->device_mode, + peerMacAddr.bytes); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Peer object "MAC_ADDRESS_STR" add fails!", + MAC_ADDR_ARRAY(peerMacAddr.bytes)); + /* send peer status indication to oem app */ hdd_send_peer_status_ind_to_oem_app(&peerMacAddr, ePeerConnected, @@ -1304,6 +1313,13 @@ static void hdd_send_association_event(struct net_device *dev, ETH_ALEN); hdd_err("wlan: new IBSS connection to " MAC_ADDRESS_STR, MAC_ADDR_ARRAY(pHddStaCtx->conn_info.bssId.bytes)); + + qdf_status = hdd_add_peer_object(pAdapter->hdd_vdev, + QDF_IBSS_MODE, + pCsrRoamInfo->bssid.bytes); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Peer object "MAC_ADDRESS_STR" add fails!", + MAC_ADDR_ARRAY(pCsrRoamInfo->bssid.bytes)); } else { /* Not Associated */ hdd_err("wlan: disconnected"); memset(wrqu.ap_addr.sa_data, '\0', ETH_ALEN); @@ -1327,6 +1343,13 @@ static void hdd_send_association_event(struct net_device *dev, NULL, pAdapter->device_mode); } + + qdf_status = hdd_remove_peer_object(pAdapter->hdd_vdev, + peerMacAddr.bytes); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Peer obj "MAC_ADDRESS_STR" delete fails", + MAC_ADDR_ARRAY(peerMacAddr.bytes)); + hdd_lpass_notify_disconnect(pAdapter); /* Update tdls module about the disconnection event */ wlan_hdd_tdls_notify_disconnect(pAdapter); @@ -3310,8 +3333,8 @@ roam_roam_connect_status_update_handler(hdd_adapter_t *pAdapter, eCsrRoamResult roamResult) { QDF_STATUS qdf_status; - hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter); + switch (roamResult) { case eCSR_ROAM_RESULT_IBSS_NEW_PEER: { @@ -3423,6 +3446,12 @@ roam_roam_connect_status_update_handler(hdd_adapter_t *pAdapter, pHddCtx->sta_to_adapter[pRoamInfo->staId] = NULL; pHddStaCtx->ibss_sta_generation++; + qdf_status = hdd_remove_peer_object(pAdapter->hdd_vdev, + pRoamInfo->peerMac.bytes); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Peer obj "MAC_ADDRESS_STR" delete fails", + MAC_ADDR_ARRAY(pRoamInfo->peerMac.bytes)); + cfg80211_del_sta(pAdapter->dev, (const u8 *)&pRoamInfo->peerMac.bytes, GFP_KERNEL); diff --git a/core/hdd/src/wlan_hdd_hostapd.c b/core/hdd/src/wlan_hdd_hostapd.c index 76a062cf03..e962cd6059 100644 --- a/core/hdd/src/wlan_hdd_hostapd.c +++ b/core/hdd/src/wlan_hdd_hostapd.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2012-2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2012-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -1671,6 +1671,18 @@ QDF_STATUS hdd_hostapd_sap_event_cb(tpSap_Event pSapEvent, chan_info, pHostapdAdapter->device_mode); } + + qdf_status = hdd_add_peer_object(pHostapdAdapter->hdd_vdev, + pHostapdAdapter->device_mode, + pSapEvent->sapevt. + sapStationAssocReassocCompleteEvent. + staMac.bytes); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Peer object "MAC_ADDRESS_STR" add fails!", + MAC_ADDR_ARRAY(pSapEvent->sapevt. + sapStationAssocReassocCompleteEvent. + staMac.bytes)); + hdd_green_ap_add_sta(pHddCtx); break; @@ -1783,6 +1795,15 @@ QDF_STATUS hdd_hostapd_sap_event_cb(tpSap_Event pSapEvent, NULL, pHostapdAdapter->device_mode); } + qdf_status = hdd_remove_peer_object(pHostapdAdapter->hdd_vdev, + pSapEvent->sapevt. + sapStationDisassocCompleteEvent. + staMac.bytes); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Peer obj "MAC_ADDRESS_STR" delete fails", + MAC_ADDR_ARRAY(pSapEvent->sapevt. + sapStationDisassocCompleteEvent. + staMac.bytes)); #ifdef MSM_PLATFORM /*stop timer in sap/p2p_go */ if (pHddApCtx->bApActive == false) { @@ -5751,7 +5772,6 @@ QDF_STATUS hdd_init_ap_mode(hdd_adapter_t *pAdapter) struct net_device *dev = pAdapter->dev; hdd_context_t *pHddCtx = WLAN_HDD_GET_CTX(pAdapter); QDF_STATUS status; - QDF_STATUS qdf_status; v_CONTEXT_t p_cds_context = (WLAN_HDD_GET_CTX(pAdapter))->pcds_context; v_CONTEXT_t sapContext = NULL; int ret; @@ -5788,12 +5808,15 @@ QDF_STATUS hdd_init_ap_mode(hdd_adapter_t *pAdapter) &session_id); if (!QDF_IS_STATUS_SUCCESS(status)) { hdd_err("ERROR: wlansap_start failed!!"); - wlansap_close(sapContext); pAdapter->sessionCtx.ap.sapContext = NULL; return status; } pAdapter->sessionId = session_id; + status = hdd_create_and_store_vdev(pHddCtx->hdd_pdev, pAdapter); + if (QDF_IS_STATUS_ERROR(status)) + goto error_vdev_create; + /* Allocate the Wireless Extensions state structure */ phostapdBuf = WLAN_HDD_GET_HOSTAP_STATE_PTR(pAdapter); @@ -5807,25 +5830,19 @@ QDF_STATUS hdd_init_ap_mode(hdd_adapter_t *pAdapter) status = hdd_set_hostapd(pAdapter); if (!QDF_IS_STATUS_SUCCESS(status)) { hdd_err("ERROR: hdd_set_hostapd failed!!"); - wlansap_close(sapContext); - pAdapter->sessionCtx.ap.sapContext = NULL; - return status; + goto error_init_ap_mode; } - qdf_status = qdf_event_create(&phostapdBuf->qdf_event); - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { + status = qdf_event_create(&phostapdBuf->qdf_event); + if (!QDF_IS_STATUS_SUCCESS(status)) { hdd_err("ERROR: Hostapd HDD qdf event init failed!!"); - wlansap_close(sapContext); - pAdapter->sessionCtx.ap.sapContext = NULL; - return qdf_status; + goto error_init_ap_mode; } - qdf_status = qdf_event_create(&phostapdBuf->qdf_stop_bss_event); - if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { + status = qdf_event_create(&phostapdBuf->qdf_stop_bss_event); + if (!QDF_IS_STATUS_SUCCESS(status)) { hdd_err("ERROR: Hostapd HDD stop bss event init failed!!"); - wlansap_close(sapContext); - pAdapter->sessionCtx.ap.sapContext = NULL; - return qdf_status; + goto error_init_ap_mode; } init_completion(&pAdapter->session_close_comp_var); @@ -5867,6 +5884,11 @@ QDF_STATUS hdd_init_ap_mode(hdd_adapter_t *pAdapter) error_wmm_init: hdd_softap_deinit_tx_rx(pAdapter); +error_init_ap_mode: + status = hdd_destroy_and_release_vdev(pAdapter); + if (QDF_IS_STATUS_ERROR(status)) + hdd_err("vdev delete failed"); +error_vdev_create: wlansap_close(sapContext); pAdapter->sessionCtx.ap.sapContext = NULL; EXIT(); @@ -6040,6 +6062,10 @@ QDF_STATUS hdd_unregister_hostapd(hdd_adapter_t *pAdapter, bool rtnl_held) hdd_err("Failed:WLANSAP_close"); pAdapter->sessionCtx.ap.sapContext = NULL; + status = hdd_destroy_and_release_vdev(pAdapter); + if (QDF_IS_STATUS_ERROR(status)) + hdd_err("vdev delete failed"); + EXIT(); return 0; } diff --git a/core/hdd/src/wlan_hdd_main.c b/core/hdd/src/wlan_hdd_main.c index 91b7e1e194..0072e96286 100644 --- a/core/hdd/src/wlan_hdd_main.c +++ b/core/hdd/src/wlan_hdd_main.c @@ -109,6 +109,12 @@ #include #include "wlan_hdd_disa.h" #include +#include +#include +#include +#include +#include +#include #ifdef MODULE #define WLAN_MODULE_NAME module_name(THIS_MODULE) @@ -1322,6 +1328,13 @@ void hdd_update_tgt_cfg(void *context, void *param) struct wma_tgt_cfg *cfg = param; uint8_t temp_band_cap; struct cds_config_info *cds_cfg = cds_get_ini_config(); + QDF_STATUS qdf_status; + + qdf_status = hdd_create_and_store_pdev(hdd_ctx); + if (QDF_IS_STATUS_ERROR(qdf_status)) { + hdd_err("Pdev creation fails!"); + QDF_BUG(0); + } if (cds_cfg) { if (hdd_ctx->config->enable_sub_20_channel_width != @@ -1775,7 +1788,13 @@ int hdd_wlan_start_modules(hdd_context_t *hdd_ctx, hdd_adapter_t *adapter, goto ol_cds_free; } - status = cds_open(); + status = hdd_create_and_store_psoc(hdd_ctx, DEFAULT_PSOC_ID); + if (QDF_IS_STATUS_ERROR(status)) { + hdd_err("Psoc creation fails!"); + goto ol_cds_free; + } + + status = cds_open(hdd_ctx->hdd_psoc); if (!QDF_IS_STATUS_SUCCESS(status)) { hdd_err("Failed to Open CDS: %d", status); goto ol_cds_free; @@ -1832,7 +1851,7 @@ int hdd_wlan_start_modules(hdd_context_t *hdd_ctx, hdd_adapter_t *adapter, return 0; close: - cds_close(p_cds_context); + cds_close(hdd_ctx->hdd_psoc, p_cds_context); ol_cds_free: ol_cds_free(); @@ -2670,10 +2689,13 @@ QDF_STATUS hdd_init_station_mode(hdd_adapter_t *adapter) hdd_alert("Session is not opened within timeout period code %ld", rc); adapter->sessionId = HDD_SESSION_ID_INVALID; - status = QDF_STATUS_E_FAILURE; - goto error_sme_open; + return QDF_STATUS_E_FAILURE; } + status = hdd_create_and_store_vdev(hdd_ctx->hdd_pdev, adapter); + if (QDF_IS_STATUS_ERROR(status)) + goto error_vdev_create; + sme_set_vdev_ies_per_band(hdd_ctx->hHal, adapter->sessionId); /* Register wireless extensions */ qdf_ret_status = hdd_register_wext(pWlanDev); @@ -2742,6 +2764,10 @@ error_wmm_init: error_init_txrx: hdd_unregister_wext(pWlanDev); error_register_wext: + status = hdd_destroy_and_release_vdev(adapter); + if (QDF_IS_STATUS_ERROR(status)) + hdd_err("vdev delete failed"); +error_vdev_create: if (test_bit(SME_SESSION_OPENED, &adapter->event_flags)) { INIT_COMPLETION(adapter->session_close_comp_var); if (QDF_STATUS_SUCCESS == sme_close_session(hdd_ctx->hHal, @@ -2894,6 +2920,7 @@ static void hdd_cleanup_adapter(hdd_context_t *hdd_ctx, hdd_adapter_t *adapter, bool rtnl_held) { struct net_device *pWlanDev = NULL; + QDF_STATUS qdf_status; if (adapter) pWlanDev = adapter->dev; @@ -2902,6 +2929,10 @@ static void hdd_cleanup_adapter(hdd_context_t *hdd_ctx, hdd_adapter_t *adapter, return; } + qdf_status = hdd_destroy_and_release_vdev(adapter); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("vdev delete failed"); + hdd_debugfs_exit(adapter); if (adapter->scan_info.default_scan_ies) { @@ -3506,6 +3537,7 @@ static void hdd_wait_for_sme_close_sesion(hdd_context_t *hdd_ctx, hdd_adapter_t *adapter) { unsigned long rc; + QDF_STATUS qdf_status; if (!test_bit(SME_SESSION_OPENED, &adapter->event_flags)) { hdd_err("session is not opened:%d", adapter->sessionId); @@ -3532,6 +3564,10 @@ static void hdd_wait_for_sme_close_sesion(hdd_context_t *hdd_ctx, clear_bit(SME_SESSION_OPENED, &adapter->event_flags); return; } + qdf_status = hdd_destroy_and_release_vdev(adapter); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("vdev delete failed"); + adapter->sessionId = HDD_SESSION_ID_INVALID; } } @@ -7716,7 +7752,7 @@ int hdd_configure_cds(hdd_context_t *hdd_ctx, hdd_adapter_t *adapter) * Start CDS which starts up the SME/MAC/HAL modules and everything * else */ - status = cds_enable(hdd_ctx->pcds_context); + status = cds_enable(hdd_ctx->hdd_psoc, hdd_ctx->pcds_context); if (!QDF_IS_STATUS_SUCCESS(status)) { hdd_alert("cds_enable failed"); @@ -7747,7 +7783,7 @@ hdd_features_deinit: hdd_deregister_cb(hdd_ctx); wlan_hdd_cfg80211_deregister_frames(adapter); cds_disable: - cds_disable(hdd_ctx->pcds_context); + cds_disable(hdd_ctx->hdd_psoc, hdd_ctx->pcds_context); out: return -EINVAL; @@ -7778,7 +7814,7 @@ static int hdd_deconfigure_cds(hdd_context_t *hdd_ctx) ret = -EINVAL; } - qdf_status = cds_disable(hdd_ctx->pcds_context); + qdf_status = cds_disable(hdd_ctx->hdd_psoc, hdd_ctx->pcds_context); if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { hdd_err("Failed to Disable the CDS Modules! :%d", qdf_status); @@ -7810,7 +7846,6 @@ int hdd_wlan_stop_modules(hdd_context_t *hdd_ctx) ENTER(); - qdf_ctx = cds_get_context(QDF_MODULE_ID_QDF_DEVICE); if (!qdf_ctx) { hdd_err("QDF device context NULL"); @@ -7862,13 +7897,21 @@ int hdd_wlan_stop_modules(hdd_context_t *hdd_ctx) ret = -EINVAL; QDF_ASSERT(0); } - qdf_status = cds_close(hdd_ctx->pcds_context); + qdf_status = cds_close(hdd_ctx->hdd_psoc, hdd_ctx->pcds_context); if (!QDF_IS_STATUS_SUCCESS(qdf_status)) { hdd_warn("Failed to stop CDS:%d", qdf_status); ret = -EINVAL; QDF_ASSERT(0); } + qdf_status = hdd_destroy_and_release_pdev(hdd_ctx); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Pdev delete failed"); + + qdf_status = hdd_destroy_and_release_psoc(hdd_ctx); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("Psoc delete failed"); + hif_ctx = cds_get_context(QDF_MODULE_ID_HIF); if (!hif_ctx) { hdd_err("Hif context is Null"); @@ -9870,6 +9913,191 @@ bool hdd_is_roaming_in_progress(void) return hdd_ctx->roaming_in_progress; } +QDF_STATUS hdd_create_and_store_psoc(hdd_context_t *hdd_ctx, uint8_t psoc_id) +{ + struct wlan_objmgr_psoc *psoc; + + psoc = wlan_objmgr_psoc_obj_create(psoc_id, WLAN_DEV_OL); + if (!psoc) + return QDF_STATUS_E_FAILURE; + + hdd_ctx->hdd_psoc = psoc; + + return QDF_STATUS_SUCCESS; +} + +QDF_STATUS hdd_destroy_and_release_psoc(hdd_context_t *hdd_ctx) +{ + struct wlan_objmgr_psoc *psoc = hdd_ctx->hdd_psoc; + + hdd_ctx->hdd_psoc = NULL; + if (psoc) { + wlan_objmgr_psoc_obj_delete(psoc); + return QDF_STATUS_SUCCESS; + } else + return QDF_STATUS_E_FAILURE; +} + +QDF_STATUS hdd_create_and_store_pdev(hdd_context_t *hdd_ctx) +{ + struct wlan_objmgr_psoc *psoc = hdd_ctx->hdd_psoc; + struct wlan_objmgr_pdev *pdev; + + if (!psoc) { + hdd_err("Psoc NULL"); + return QDF_STATUS_E_FAILURE; + } + + pdev = wlan_objmgr_pdev_obj_create(psoc, NULL); + if (!pdev) { + hdd_err("pdev obj create failed"); + return QDF_STATUS_E_FAILURE; + } + hdd_ctx->hdd_pdev = pdev; + + return QDF_STATUS_SUCCESS; +} + +QDF_STATUS hdd_destroy_and_release_pdev(hdd_context_t *hdd_ctx) +{ + struct wlan_objmgr_pdev *pdev = hdd_ctx->hdd_pdev; + + hdd_ctx->hdd_pdev = NULL; + if (pdev) { + wlan_objmgr_pdev_obj_delete(pdev); + return QDF_STATUS_SUCCESS; + } else + return QDF_STATUS_E_FAILURE; +} + +QDF_STATUS hdd_create_and_store_vdev(struct wlan_objmgr_pdev *pdev, + hdd_adapter_t *adapter) +{ + struct wlan_objmgr_vdev *vdev; + struct wlan_objmgr_peer *peer; + struct wlan_vdev_create_params vdev_params; + + vdev_params.opmode = adapter->device_mode; + qdf_mem_copy(vdev_params.macaddr, adapter->macAddressCurrent.bytes, + QDF_NET_MAC_ADDR_MAX_LEN); + if (!pdev) { + hdd_err("pdev NULL"); + return QDF_STATUS_E_FAILURE; + } + + vdev = wlan_objmgr_vdev_obj_create(pdev, &vdev_params); + if (!vdev) { + hdd_err("vdev obj create fails"); + return QDF_STATUS_E_FAILURE; + } + + if (adapter->sessionId != wlan_vdev_get_id(vdev)) { + hdd_err("session id and vdev id mismatch"); + wlan_objmgr_vdev_obj_delete(vdev); + QDF_ASSERT(0); + return QDF_STATUS_E_FAILURE; + } + + peer = wlan_objmgr_peer_obj_create(vdev, WLAN_PEER_SELF, + vdev_params.macaddr); + if (!peer) { + hdd_err("obj manager self peer create fails for adapter %d", + adapter->device_mode); + wlan_objmgr_vdev_obj_delete(vdev); + return QDF_STATUS_E_FAILURE; + } + adapter->hdd_vdev = vdev; + + return QDF_STATUS_SUCCESS; +} + +QDF_STATUS hdd_destroy_and_release_vdev(hdd_adapter_t *adapter) +{ + struct wlan_objmgr_vdev *vdev = adapter->hdd_vdev; + + adapter->hdd_vdev = NULL; + if (vdev) { + if (hdd_remove_peer_object(vdev, + wlan_vdev_mlme_get_macaddr(vdev))) { + hdd_err("Self peer delete fails"); + return QDF_STATUS_E_FAILURE; + } + + wlan_objmgr_vdev_obj_delete(vdev); + return QDF_STATUS_SUCCESS; + } else + return QDF_STATUS_E_FAILURE; +} + +QDF_STATUS hdd_add_peer_object(struct wlan_objmgr_vdev *vdev, + enum tQDF_ADAPTER_MODE adapter_mode, + uint8_t *mac_addr) +{ + enum wlan_peer_type peer_type; + + if ((adapter_mode == QDF_STA_MODE) || + (adapter_mode == QDF_P2P_CLIENT_MODE)) + peer_type = WLAN_PEER_AP; + else if ((adapter_mode == QDF_SAP_MODE) || + (adapter_mode == QDF_P2P_GO_MODE)) + peer_type = WLAN_PEER_STA; + else if (adapter_mode == QDF_IBSS_MODE) + peer_type = WLAN_PEER_IBSS; + else { + hdd_err("Unsupported device mode %d", adapter_mode); + return QDF_STATUS_E_FAILURE; + } + + if (!vdev) { + hdd_err("vdev NULL"); + QDF_ASSERT(0); + return QDF_STATUS_E_FAILURE; + } + + if (!wlan_objmgr_peer_obj_create(vdev, peer_type, mac_addr)) + return QDF_STATUS_E_FAILURE; + + hdd_info("Peer object "MAC_ADDRESS_STR" add success!", + MAC_ADDR_ARRAY(mac_addr)); + + return QDF_STATUS_SUCCESS; +} + +QDF_STATUS hdd_remove_peer_object(struct wlan_objmgr_vdev *vdev, + uint8_t *mac_addr) +{ + struct wlan_objmgr_psoc *psoc; + struct wlan_objmgr_peer *peer; + + if (!vdev) { + hdd_err("vdev NULL"); + QDF_ASSERT(0); + return QDF_STATUS_E_FAILURE; + } + + psoc = wlan_vdev_get_psoc(vdev); + if (!psoc) { + hdd_err("Psoc NUll"); + QDF_ASSERT(0); + return QDF_STATUS_E_FAILURE; + } + + peer = wlan_objmgr_find_peer(psoc, mac_addr); + if (peer) { + if (wlan_objmgr_peer_obj_delete(peer)) + return QDF_STATUS_E_FAILURE; + + hdd_info("Peer obj "MAC_ADDRESS_STR" deleted", + MAC_ADDR_ARRAY(mac_addr)); + return QDF_STATUS_SUCCESS; + } + + hdd_err("Peer obj "MAC_ADDRESS_STR" not found", + MAC_ADDR_ARRAY(mac_addr)); + + return QDF_STATUS_E_FAILURE; +} + /* Register the module init/exit functions */ module_init(hdd_module_init); module_exit(hdd_module_exit); diff --git a/core/hdd/src/wlan_hdd_nan_datapath.c b/core/hdd/src/wlan_hdd_nan_datapath.c index 64ee8f085d..0a4b5503be 100644 --- a/core/hdd/src/wlan_hdd_nan_datapath.c +++ b/core/hdd/src/wlan_hdd_nan_datapath.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2016-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -105,6 +105,7 @@ static int hdd_close_ndi(hdd_adapter_t *adapter) int rc; hdd_context_t *hdd_ctx = WLAN_HDD_GET_CTX(adapter); uint32_t timeout = WLAN_WAIT_TIME_SESSIONOPENCLOSE; + QDF_STATUS qdf_status; ENTER(); @@ -139,6 +140,10 @@ static int hdd_close_ndi(hdd_adapter_t *adapter) msecs_to_jiffies(timeout)); if (!rc) hdd_err("session close timeout"); + + qdf_status = hdd_destroy_and_release_vdev(adapter); + if (QDF_IS_STATUS_ERROR(qdf_status)) + hdd_err("vdev delete failed"); } } @@ -1885,6 +1890,12 @@ int hdd_init_nan_data_mode(struct hdd_adapter_s *adapter) goto error_sme_open; } + status = hdd_create_and_store_vdev(hdd_ctx->hdd_pdev, adapter); + if (QDF_IS_STATUS_ERROR(status)) { + ret_val = -EAGAIN; + goto error_vdev_create; + } + /* Register wireless extensions */ ret_val = hdd_register_wext(wlan_dev); if (0 > ret_val) { @@ -1931,6 +1942,10 @@ error_init_txrx: hdd_unregister_wext(wlan_dev); error_register_wext: + status = hdd_destroy_and_release_vdev(adapter); + if (QDF_IS_STATUS_ERROR(status)) + hdd_err("vdev delete failed"); +error_vdev_create: if (test_bit(SME_SESSION_OPENED, &adapter->event_flags)) { INIT_COMPLETION(adapter->session_close_comp_var); if (QDF_STATUS_SUCCESS == diff --git a/core/mac/inc/ani_global.h b/core/mac/inc/ani_global.h index 7c3397dc7d..9a65c0ec11 100644 --- a/core/mac/inc/ani_global.h +++ b/core/mac/inc/ani_global.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2012-2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2012-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -52,6 +52,7 @@ #include "p2p_api.h" #include +#include "wlan_objmgr_psoc_obj.h" /* Check if this definition can actually move here from halInternal.h even for Volans. In that case */ /* this featurization can be removed. */ @@ -973,6 +974,7 @@ typedef struct sAniSirGlobal { uint8_t user_configured_nss; bool sta_prefer_80MHz_over_160MHz; bool is_11d_hint; + struct wlan_objmgr_psoc *psoc; } tAniSirGlobal; typedef enum { diff --git a/core/mac/inc/mac_init_api.h b/core/mac/inc/mac_init_api.h index 1a231d43f4..a439d19f58 100644 --- a/core/mac/inc/mac_init_api.h +++ b/core/mac/inc/mac_init_api.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011-2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2011-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -43,8 +43,8 @@ tSirRetStatus mac_start(tHalHandle hHal, void *pHalMacStartParams); tSirRetStatus mac_stop(tHalHandle hHal, tHalStopType stopType); -tSirRetStatus mac_open(tHalHandle *pHalHandle, tHddHandle hHdd, - struct cds_config_info *cds_cfg); +tSirRetStatus mac_open(struct wlan_objmgr_psoc *psoc, tHalHandle *pHalHandle, + tHddHandle hHdd, struct cds_config_info *cds_cfg); tSirRetStatus mac_close(tHalHandle hHal); #endif /* __MAC_INIT_API_H */ diff --git a/core/mac/src/sys/legacy/src/system/src/mac_init_api.c b/core/mac/src/sys/legacy/src/system/src/mac_init_api.c index 8c0c432dae..aaca627c2c 100644 --- a/core/mac/src/sys/legacy/src/system/src/mac_init_api.c +++ b/core/mac/src/sys/legacy/src/system/src/mac_init_api.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2011-2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2011-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -103,8 +103,8 @@ tSirRetStatus mac_stop(tHalHandle hHal, tHalStopType stopType) \return tSirRetStatus -------------------------------------------------------------*/ -tSirRetStatus mac_open(tHalHandle *pHalHandle, tHddHandle hHdd, - struct cds_config_info *cds_cfg) +tSirRetStatus mac_open(struct wlan_objmgr_psoc *psoc, tHalHandle *pHalHandle, + tHddHandle hHdd, struct cds_config_info *cds_cfg) { tpAniSirGlobal p_mac = NULL; tSirRetStatus status = eSIR_SUCCESS; @@ -130,6 +130,9 @@ tSirRetStatus mac_open(tHalHandle *pHalHandle, tHddHandle hHdd, * dependant) */ p_mac->hHdd = hHdd; + + /* Increase psoc ref count once APIs are available in object manager */ + p_mac->psoc = psoc; *pHalHandle = (tHalHandle) p_mac; { @@ -184,6 +187,8 @@ tSirRetStatus mac_close(tHalHandle hHal) log_deinit(pMac); + /* Decrease psoc ref count once APIs are available in object manager */ + pMac->psoc = NULL; /* Finally, de-allocate the global MAC datastructure: */ qdf_mem_free(pMac); diff --git a/core/wma/inc/wma.h b/core/wma/inc/wma.h index 86f9f6aef5..31f930054b 100644 --- a/core/wma/inc/wma.h +++ b/core/wma/inc/wma.h @@ -49,6 +49,7 @@ #include "cdp_txrx_cmn.h" #include "dbglog.h" #include "cds_ieee80211_common.h" +#include "wlan_objmgr_psoc_obj.h" /* Platform specific configuration for max. no. of fragments */ #define QCA_OL_11AC_TX_MAX_FRAGS 2 @@ -1279,6 +1280,7 @@ struct extended_caps { * @htc_handle: htc handle * @cds_context: cds handle * @mac_context: mac context + * @psoc: psoc context * @wma_ready_event: wma rx ready event * @wma_resume_event: wma resume event * @target_suspend: target suspend event @@ -1411,6 +1413,7 @@ typedef struct { void *htc_handle; void *cds_context; void *mac_context; + struct wlan_objmgr_psoc *psoc; qdf_event_t wma_ready_event; qdf_event_t wma_resume_event; qdf_event_t target_suspend; diff --git a/core/wma/inc/wma_types.h b/core/wma/inc/wma_types.h index cfd4d2ffb5..ab7e09fb3e 100644 --- a/core/wma/inc/wma_types.h +++ b/core/wma/inc/wma_types.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2012-2016 The Linux Foundation. All rights reserved. + * Copyright (c) 2012-2017 The Linux Foundation. All rights reserved. * * Previously licensed under the ISC license by Qualcomm Atheros, Inc. * @@ -698,7 +698,7 @@ QDF_STATUS wma_tx_packet(void *pWMA, uint8_t txFlag, uint8_t sessionId, bool tdlsflag, uint16_t channel_freq); -QDF_STATUS wma_open(void *p_cds_context, +QDF_STATUS wma_open(struct wlan_objmgr_psoc *psoc, void *p_cds_context, wma_tgt_cfg_cb pTgtUpdCB, wma_dfs_radar_indication_cb radar_ind_cb, struct cds_config_info *cds_cfg); diff --git a/core/wma/src/wma_main.c b/core/wma/src/wma_main.c index 5bf81fdc15..b106d387fa 100644 --- a/core/wma/src/wma_main.c +++ b/core/wma/src/wma_main.c @@ -1841,7 +1841,7 @@ wma_register_tx_ops_handler(struct wlan_lmac_if_tx_ops *tx_ops) */ static void wma_target_if_open(tp_wma_handle wma_handle) { - struct wlan_objmgr_psoc *psoc = cds_get_psoc_by_id(0); + struct wlan_objmgr_psoc *psoc = wma_handle->psoc; if (!psoc) return; @@ -1862,7 +1862,7 @@ static void wma_target_if_open(tp_wma_handle wma_handle) */ static void wma_target_if_close(tp_wma_handle wma_handle) { - struct wlan_objmgr_psoc *psoc = cds_get_psoc_by_id(0); + struct wlan_objmgr_psoc *psoc = wma_handle->psoc; if (!psoc) return; @@ -1876,6 +1876,7 @@ static void wma_target_if_close(tp_wma_handle wma_handle) {}; /** * wma_open() - Allocate wma context and initialize it. + * @psoc: Psoc pointer * @cds_context: cds context * @wma_tgt_cfg_cb: tgt config callback fun * @radar_ind_cb: dfs radar indication callback @@ -1883,7 +1884,7 @@ static void wma_target_if_close(tp_wma_handle wma_handle) {}; * * Return: 0 on success, errno on failure */ -QDF_STATUS wma_open(void *cds_context, +QDF_STATUS wma_open(struct wlan_objmgr_psoc *psoc, void *cds_context, wma_tgt_cfg_cb tgt_cfg_cb, wma_dfs_radar_indication_cb radar_ind_cb, struct cds_config_info *cds_cfg) @@ -1935,6 +1936,9 @@ QDF_STATUS wma_open(void *cds_context, qdf_wake_lock_create(&wma_handle->wow_wake_lock, "wlan_wow_wl"); } + /* Increase psoc ref count once APIs are available in object manager */ + wma_handle->psoc = psoc; + /* Attach mc_thread context processing function */ ops.wma_process_fw_event_handler_cbk = wma_process_fw_event_handler; /* attach the wmi */ @@ -3528,6 +3532,8 @@ QDF_STATUS wma_close(void *cds_ctx) wmi_desc_pool_deinit(wma_handle); } + /* Decrease psoc ref count once APIs are available in object manager */ + wma_handle->psoc = NULL; wma_target_if_close(wma_handle); WMA_LOGD("%s: Exit", __func__);