1 /* 2 * Copyright (c) 2017-2021 The Linux Foundation. All rights reserved. 3 * Copyright (c) 2021,2023-2024 Qualcomm Innovation Center, Inc. All rights reserved. 4 * 5 * Permission to use, copy, modify, and/or distribute this software for 6 * any purpose with or without fee is hereby granted, provided that the 7 * above copyright notice and this permission notice appear in all 8 * copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL 11 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED 12 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE 13 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL 14 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 15 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER 16 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 17 * PERFORMANCE OF THIS SOFTWARE. 18 */ 19 /** 20 * DOC: Implement various api / helper function which shall be used 21 * PMO user and target interface. 22 */ 23 24 #include "wlan_pmo_main.h" 25 #include "wlan_pmo_obj_mgmt_public_struct.h" 26 #include "wlan_pmo_cfg.h" 27 #include "cfg_ucfg_api.h" 28 #include "wlan_fwol_ucfg_api.h" 29 #include "wlan_ipa_obj_mgmt_api.h" 30 #include "wlan_pmo_icmp.h" 31 32 static struct wlan_pmo_ctx *gp_pmo_ctx; 33 pmo_allocate_ctx(void)34 QDF_STATUS pmo_allocate_ctx(void) 35 { 36 /* If it is already created, ignore */ 37 if (gp_pmo_ctx) { 38 pmo_debug("already allocated pmo_ctx"); 39 return QDF_STATUS_SUCCESS; 40 } 41 42 /* allocate offload mgr ctx */ 43 gp_pmo_ctx = (struct wlan_pmo_ctx *)qdf_mem_malloc( 44 sizeof(*gp_pmo_ctx)); 45 if (!gp_pmo_ctx) 46 return QDF_STATUS_E_NOMEM; 47 48 qdf_spinlock_create(&gp_pmo_ctx->lock); 49 50 return QDF_STATUS_SUCCESS; 51 } 52 pmo_free_ctx(void)53 void pmo_free_ctx(void) 54 { 55 if (!gp_pmo_ctx) { 56 pmo_err("pmo ctx is already freed"); 57 QDF_ASSERT(0); 58 return; 59 } 60 qdf_spinlock_destroy(&gp_pmo_ctx->lock); 61 qdf_mem_free(gp_pmo_ctx); 62 gp_pmo_ctx = NULL; 63 } 64 pmo_get_context(void)65 struct wlan_pmo_ctx *pmo_get_context(void) 66 { 67 return gp_pmo_ctx; 68 } 69 70 #ifdef WLAN_FEATURE_EXTWOW_SUPPORT wlan_extwow_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)71 static void wlan_extwow_init_cfg(struct wlan_objmgr_psoc *psoc, 72 struct pmo_psoc_cfg *psoc_cfg) 73 { 74 psoc_cfg->extwow_goto_suspend = 75 cfg_get(psoc, CFG_EXTWOW_GOTO_SUSPEND); 76 psoc_cfg->extwow_app1_wakeup_pin_num = 77 cfg_get(psoc, CFG_EXTWOW_APP1_WAKE_PIN_NUMBER); 78 psoc_cfg->extwow_app2_wakeup_pin_num = 79 cfg_get(psoc, CFG_EXTWOW_APP2_WAKE_PIN_NUMBER); 80 psoc_cfg->extwow_app2_init_ping_interval = 81 cfg_get(psoc, CFG_EXTWOW_KA_INIT_PING_INTERVAL); 82 psoc_cfg->extwow_app2_min_ping_interval = 83 cfg_get(psoc, CFG_EXTWOW_KA_MIN_PING_INTERVAL); 84 psoc_cfg->extwow_app2_max_ping_interval = 85 cfg_get(psoc, CFG_EXTWOW_KA_MAX_PING_INTERVAL); 86 psoc_cfg->extwow_app2_inc_ping_interval = 87 cfg_get(psoc, CFG_EXTWOW_KA_INC_PING_INTERVAL); 88 psoc_cfg->extwow_app2_tcp_src_port = 89 cfg_get(psoc, CFG_EXTWOW_TCP_SRC_PORT); 90 psoc_cfg->extwow_app2_tcp_dst_port = 91 cfg_get(psoc, CFG_EXTWOW_TCP_DST_PORT); 92 psoc_cfg->extwow_app2_tcp_tx_timeout = 93 cfg_get(psoc, CFG_EXTWOW_TCP_TX_TIMEOUT); 94 psoc_cfg->extwow_app2_tcp_rx_timeout = 95 cfg_get(psoc, CFG_EXTWOW_TCP_RX_TIMEOUT); 96 } 97 #else wlan_extwow_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)98 static void wlan_extwow_init_cfg(struct wlan_objmgr_psoc *psoc, 99 struct pmo_psoc_cfg *psoc_cfg) 100 { 101 } 102 #endif 103 104 #ifdef WLAN_FEATURE_WOW_PULSE wlan_pmo_wow_pulse_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)105 static void wlan_pmo_wow_pulse_init_cfg(struct wlan_objmgr_psoc *psoc, 106 struct pmo_psoc_cfg *psoc_cfg) 107 { 108 psoc_cfg->is_wow_pulse_supported = 109 cfg_get(psoc, CFG_PMO_WOW_PULSE_ENABLE); 110 psoc_cfg->wow_pulse_pin = cfg_get(psoc, CFG_PMO_WOW_PULSE_PIN); 111 psoc_cfg->wow_pulse_interval_high = 112 cfg_get(psoc, CFG_PMO_WOW_PULSE_HIGH); 113 psoc_cfg->wow_pulse_interval_low = 114 cfg_get(psoc, CFG_PMO_WOW_PULSE_LOW); 115 psoc_cfg->wow_pulse_repeat_count = 116 cfg_get(psoc, CFG_PMO_WOW_PULSE_REPEAT); 117 psoc_cfg->wow_pulse_init_state = 118 cfg_get(psoc, CFG_PMO_WOW_PULSE_INIT); 119 } 120 #else wlan_pmo_wow_pulse_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)121 static void wlan_pmo_wow_pulse_init_cfg(struct wlan_objmgr_psoc *psoc, 122 struct pmo_psoc_cfg *psoc_cfg) 123 { 124 } 125 #endif 126 127 #ifdef WLAN_FEATURE_PACKET_FILTERING wlan_pmo_pkt_filter_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)128 static void wlan_pmo_pkt_filter_init_cfg(struct wlan_objmgr_psoc *psoc, 129 struct pmo_psoc_cfg *psoc_cfg) 130 { 131 psoc_cfg->packet_filters_bitmap = cfg_get(psoc, CFG_PMO_PKT_FILTER); 132 psoc_cfg->packet_filter_enabled = 133 !cfg_get(psoc, CFG_PMO_DISABLE_PKT_FILTER); 134 } 135 #else wlan_pmo_pkt_filter_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)136 static void wlan_pmo_pkt_filter_init_cfg(struct wlan_objmgr_psoc *psoc, 137 struct pmo_psoc_cfg *psoc_cfg) 138 { 139 psoc_cfg->packet_filter_enabled = 140 !cfg_get(psoc, CFG_PMO_DISABLE_PKT_FILTER); 141 } 142 #endif 143 144 #ifdef FEATURE_RUNTIME_PM wlan_pmo_runtime_pm_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)145 static void wlan_pmo_runtime_pm_init_cfg(struct wlan_objmgr_psoc *psoc, 146 struct pmo_psoc_cfg *psoc_cfg) 147 { 148 psoc_cfg->runtime_pm_delay = cfg_get(psoc, CFG_PMO_RUNTIME_PM_DELAY); 149 } 150 #else wlan_pmo_runtime_pm_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)151 static void wlan_pmo_runtime_pm_init_cfg(struct wlan_objmgr_psoc *psoc, 152 struct pmo_psoc_cfg *psoc_cfg) 153 { 154 } 155 #endif 156 157 #ifdef FEATURE_WLAN_RA_FILTERING wlan_pmo_ra_filtering_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)158 static void wlan_pmo_ra_filtering_init_cfg(struct wlan_objmgr_psoc *psoc, 159 struct pmo_psoc_cfg *psoc_cfg) 160 { 161 bool ra_enable; 162 163 if (QDF_IS_STATUS_SUCCESS(ucfg_fwol_get_is_rate_limit_enabled(psoc, 164 &ra_enable))) 165 psoc_cfg->ra_ratelimit_enable = ra_enable; 166 167 psoc_cfg->ra_ratelimit_interval = 168 cfg_get(psoc, CFG_RA_RATE_LIMIT_INTERVAL); 169 } 170 #else wlan_pmo_ra_filtering_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)171 static void wlan_pmo_ra_filtering_init_cfg(struct wlan_objmgr_psoc *psoc, 172 struct pmo_psoc_cfg *psoc_cfg) 173 { 174 } 175 #endif 176 177 #ifdef WLAN_ENABLE_GPIO_WAKEUP wlan_pmo_gpio_wakeup_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)178 static void wlan_pmo_gpio_wakeup_init_cfg(struct wlan_objmgr_psoc *psoc, 179 struct pmo_psoc_cfg *psoc_cfg) 180 { 181 psoc_cfg->enable_gpio_wakeup = 182 cfg_get(psoc, CFG_PMO_ENABLE_GPIO_WAKEUP); 183 psoc_cfg->gpio_wakeup_pin = 184 cfg_get(psoc, CFG_PMO_GPIO_WAKEUP_PIN); 185 psoc_cfg->gpio_wakeup_mode = 186 cfg_get(psoc, CFG_PMO_GPIO_WAKEUP_MODE); 187 } 188 #else wlan_pmo_gpio_wakeup_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)189 static void wlan_pmo_gpio_wakeup_init_cfg(struct wlan_objmgr_psoc *psoc, 190 struct pmo_psoc_cfg *psoc_cfg) 191 { 192 } 193 #endif 194 195 #ifdef WLAN_FEATURE_IGMP_OFFLOAD 196 static void wlan_pmo_get_igmp_version_support_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)197 wlan_pmo_get_igmp_version_support_cfg(struct wlan_objmgr_psoc *psoc, 198 struct pmo_psoc_cfg *psoc_cfg) 199 { 200 psoc_cfg->igmp_version_support = 201 cfg_get(psoc, CFG_IGMP_VERSION_SUPPORT); 202 } 203 204 static void wlan_pmo_get_igmp_offload_enable_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)205 wlan_pmo_get_igmp_offload_enable_cfg(struct wlan_objmgr_psoc *psoc, 206 struct pmo_psoc_cfg *psoc_cfg) 207 { 208 psoc_cfg->igmp_offload_enable = cfg_get(psoc, 209 CFG_PMO_ENABLE_IGMP_OFFLOAD); 210 } 211 #else 212 static void wlan_pmo_get_igmp_version_support_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)213 wlan_pmo_get_igmp_version_support_cfg(struct wlan_objmgr_psoc *psoc, 214 struct pmo_psoc_cfg *psoc_cfg) 215 {} 216 217 static void wlan_pmo_get_igmp_offload_enable_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)218 wlan_pmo_get_igmp_offload_enable_cfg(struct wlan_objmgr_psoc *psoc, 219 struct pmo_psoc_cfg *psoc_cfg) 220 {} 221 #endif 222 223 #ifdef WLAN_FEATURE_ICMP_OFFLOAD 224 static void wlan_pmo_get_icmp_offload_enable_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)225 wlan_pmo_get_icmp_offload_enable_cfg(struct wlan_objmgr_psoc *psoc, 226 struct pmo_psoc_cfg *psoc_cfg) 227 { 228 psoc_cfg->is_icmp_offload_enable = 229 cfg_get(psoc, CFG_ENABLE_ICMP_OFFLOAD); 230 } 231 #else 232 static inline void wlan_pmo_get_icmp_offload_enable_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)233 wlan_pmo_get_icmp_offload_enable_cfg(struct wlan_objmgr_psoc *psoc, 234 struct pmo_psoc_cfg *psoc_cfg) 235 {} 236 #endif 237 wlan_pmo_init_cfg(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)238 static void wlan_pmo_init_cfg(struct wlan_objmgr_psoc *psoc, 239 struct pmo_psoc_cfg *psoc_cfg) 240 { 241 psoc_cfg->arp_offload_enable = 242 cfg_get(psoc, CFG_PMO_ENABLE_HOST_ARPOFFLOAD); 243 psoc_cfg->hw_filter_mode_bitmap = cfg_get(psoc, CFG_PMO_HW_FILTER_MODE); 244 psoc_cfg->ssdp = cfg_get(psoc, CFG_PMO_ENABLE_HOST_SSDP); 245 psoc_cfg->ns_offload_enable_static = 246 cfg_get(psoc, CFG_PMO_ENABLE_HOST_NSOFFLOAD); 247 psoc_cfg->ns_offload_enable_dynamic = 248 cfg_get(psoc, CFG_PMO_ENABLE_HOST_NSOFFLOAD); 249 psoc_cfg->sta_dynamic_dtim = cfg_get(psoc, CFG_PMO_ENABLE_DYNAMIC_DTIM); 250 wlan_pmo_get_igmp_version_support_cfg(psoc, psoc_cfg); 251 psoc_cfg->sta_mod_dtim = cfg_get(psoc, CFG_PMO_ENABLE_MODULATED_DTIM); 252 psoc_cfg->enable_mc_list = cfg_get(psoc, CFG_PMO_MC_ADDR_LIST_ENABLE); 253 psoc_cfg->power_save_mode = cfg_get(psoc, CFG_PMO_POWERSAVE_MODE); 254 psoc_cfg->sta_forced_dtim = cfg_get(psoc, CFG_PMO_ENABLE_FORCED_DTIM); 255 psoc_cfg->is_mod_dtim_on_sys_suspend_enabled = 256 cfg_get(psoc, CFG_PMO_MOD_DTIM_ON_SYS_SUSPEND); 257 psoc_cfg->is_bus_suspend_enabled_in_sap_mode = 258 cfg_get(psoc, CFG_ENABLE_BUS_SUSPEND_IN_SAP_MODE); 259 psoc_cfg->is_bus_suspend_enabled_in_go_mode = 260 cfg_get(psoc, CFG_ENABLE_BUS_SUSPEND_IN_GO_MODE); 261 if (wlan_ipa_config_is_enabled() && 262 !ipa_config_is_opt_wifi_dp_enabled()) { 263 pmo_info("ipa is enabled and hence disable sap/go d3 wow"); 264 psoc_cfg->is_bus_suspend_enabled_in_sap_mode = 0; 265 psoc_cfg->is_bus_suspend_enabled_in_go_mode = 0; 266 } 267 psoc_cfg->default_power_save_mode = psoc_cfg->power_save_mode; 268 psoc_cfg->max_ps_poll = cfg_get(psoc, CFG_PMO_MAX_PS_POLL); 269 270 psoc_cfg->wow_enable = cfg_get(psoc, CFG_PMO_WOW_ENABLE); 271 psoc_cfg->suspend_mode = cfg_get(psoc, CFG_PMO_SUSPEND_MODE); 272 273 wlan_extwow_init_cfg(psoc, psoc_cfg); 274 psoc_cfg->apf_enable = cfg_get(psoc, CFG_PMO_APF_ENABLE); 275 psoc_cfg->active_mode_offload = cfg_get(psoc, CFG_PMO_ACTIVE_MODE); 276 wlan_pmo_wow_pulse_init_cfg(psoc, psoc_cfg); 277 wlan_pmo_pkt_filter_init_cfg(psoc, psoc_cfg); 278 wlan_pmo_runtime_pm_init_cfg(psoc, psoc_cfg); 279 psoc_cfg->auto_power_save_fail_mode = 280 cfg_get(psoc, CFG_PMO_PWR_FAILURE); 281 psoc_cfg->enable_sap_suspend = cfg_get(psoc, CFG_ENABLE_SAP_SUSPEND); 282 psoc_cfg->wow_data_inactivity_timeout = 283 cfg_get(psoc, CFG_PMO_WOW_DATA_INACTIVITY_TIMEOUT); 284 psoc_cfg->wow_spec_wake_interval = 285 cfg_get(psoc, CFG_PMO_WOW_SPEC_WAKE_INTERVAL); 286 psoc_cfg->active_uc_apf_mode = 287 cfg_get(psoc, CFG_ACTIVE_UC_APF_MODE); 288 psoc_cfg->active_mc_bc_apf_mode = 289 cfg_get(psoc, CFG_ACTIVE_MC_BC_APF_MODE); 290 psoc_cfg->ito_repeat_count = cfg_get(psoc, CFG_ITO_REPEAT_COUNT); 291 wlan_pmo_ra_filtering_init_cfg(psoc, psoc_cfg); 292 wlan_pmo_gpio_wakeup_init_cfg(psoc, psoc_cfg); 293 wlan_pmo_get_igmp_offload_enable_cfg(psoc, psoc_cfg); 294 psoc_cfg->disconnect_sap_tdls_in_wow = 295 cfg_get(psoc, CFG_DISCONNECT_SAP_TDLS_IN_WOW); 296 wlan_pmo_get_icmp_offload_enable_cfg(psoc, psoc_cfg); 297 298 psoc_cfg->host_pf_action = cfg_get(psoc, CFG_HOST_ACTION_ON_PAGEFAULT); 299 psoc_cfg->min_pagefault_wakeups_for_action = 300 cfg_get(psoc, 301 CFG_MIN_PAGEFAULT_WAKEUPS_FOR_ACTION); 302 psoc_cfg->interval_for_pagefault_wakeup_counts = 303 cfg_get(psoc, 304 CFG_INTERVAL_FOR_PAGEFAULT_WAKEUP_COUNT); 305 psoc_cfg->ssr_frequency_on_pagefault = 306 cfg_get(psoc, CFG_SSR_FREQUENCY_ON_PAGEFAULT); 307 } 308 pmo_psoc_open(struct wlan_objmgr_psoc * psoc)309 QDF_STATUS pmo_psoc_open(struct wlan_objmgr_psoc *psoc) 310 { 311 struct pmo_psoc_priv_obj *pmo_psoc_ctx; 312 313 if (!psoc) { 314 pmo_err("null psoc"); 315 return QDF_STATUS_E_INVAL; 316 } 317 318 pmo_psoc_ctx = pmo_psoc_get_priv(psoc); 319 wlan_pmo_init_cfg(psoc, &pmo_psoc_ctx->psoc_cfg); 320 321 return QDF_STATUS_SUCCESS; 322 } 323 pmo_psoc_close(struct wlan_objmgr_psoc * psoc)324 QDF_STATUS pmo_psoc_close(struct wlan_objmgr_psoc *psoc) 325 { 326 return QDF_STATUS_SUCCESS; 327 } 328 pmo_is_vdev_in_beaconning_mode(enum QDF_OPMODE vdev_opmode)329 bool pmo_is_vdev_in_beaconning_mode(enum QDF_OPMODE vdev_opmode) 330 { 331 switch (vdev_opmode) { 332 case QDF_SAP_MODE: 333 case QDF_P2P_GO_MODE: 334 case QDF_IBSS_MODE: 335 return true; 336 default: 337 return false; 338 } 339 } 340 pmo_get_vdev_bss_peer_mac_addr(struct wlan_objmgr_vdev * vdev,struct qdf_mac_addr * bss_peer_mac_address)341 QDF_STATUS pmo_get_vdev_bss_peer_mac_addr(struct wlan_objmgr_vdev *vdev, 342 struct qdf_mac_addr *bss_peer_mac_address) 343 { 344 struct wlan_objmgr_peer *peer; 345 346 if (!vdev) { 347 pmo_err("vdev is null"); 348 return QDF_STATUS_E_INVAL; 349 } 350 351 peer = wlan_objmgr_vdev_try_get_bsspeer(vdev, WLAN_PMO_ID); 352 if (!peer) { 353 pmo_err("peer is null"); 354 return QDF_STATUS_E_INVAL; 355 } 356 wlan_peer_obj_lock(peer); 357 qdf_mem_copy(bss_peer_mac_address->bytes, wlan_peer_get_macaddr(peer), 358 QDF_MAC_ADDR_SIZE); 359 wlan_peer_obj_unlock(peer); 360 361 wlan_objmgr_peer_release_ref(peer, WLAN_PMO_ID); 362 363 return QDF_STATUS_SUCCESS; 364 } 365 pmo_core_is_ap_mode_supports_arp_ns(struct wlan_objmgr_psoc * psoc,enum QDF_OPMODE vdev_opmode)366 bool pmo_core_is_ap_mode_supports_arp_ns(struct wlan_objmgr_psoc *psoc, 367 enum QDF_OPMODE vdev_opmode) 368 { 369 struct pmo_psoc_priv_obj *psoc_ctx; 370 371 psoc_ctx = pmo_psoc_get_priv(psoc); 372 373 if ((vdev_opmode == QDF_SAP_MODE || 374 vdev_opmode == QDF_P2P_GO_MODE) && 375 !psoc_ctx->psoc_cfg.ap_arpns_support) { 376 pmo_debug("ARP/NS Offload is not supported in SAP/P2PGO mode"); 377 return false; 378 } 379 380 return true; 381 } 382 pmo_core_is_vdev_supports_offload(struct wlan_objmgr_vdev * vdev)383 bool pmo_core_is_vdev_supports_offload(struct wlan_objmgr_vdev *vdev) 384 { 385 enum QDF_OPMODE opmode; 386 bool val; 387 388 opmode = pmo_get_vdev_opmode(vdev); 389 pmo_debug("vdev opmode: %d", opmode); 390 switch (opmode) { 391 case QDF_STA_MODE: 392 case QDF_P2P_CLIENT_MODE: 393 case QDF_NDI_MODE: 394 val = true; 395 break; 396 default: 397 val = false; 398 break; 399 } 400 401 return val; 402 } 403 pmo_core_get_psoc_config(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)404 QDF_STATUS pmo_core_get_psoc_config(struct wlan_objmgr_psoc *psoc, 405 struct pmo_psoc_cfg *psoc_cfg) 406 { 407 struct pmo_psoc_priv_obj *psoc_ctx; 408 QDF_STATUS status = QDF_STATUS_SUCCESS; 409 410 pmo_enter(); 411 if (!psoc || !psoc_cfg) { 412 pmo_err("%s is null", !psoc ? "psoc":"psoc_cfg"); 413 status = QDF_STATUS_E_NULL_VALUE; 414 goto out; 415 } 416 417 pmo_psoc_with_ctx(psoc, psoc_ctx) { 418 qdf_mem_copy(psoc_cfg, &psoc_ctx->psoc_cfg, sizeof(*psoc_cfg)); 419 } 420 421 out: 422 pmo_exit(); 423 424 return status; 425 } 426 pmo_core_update_psoc_config(struct wlan_objmgr_psoc * psoc,struct pmo_psoc_cfg * psoc_cfg)427 QDF_STATUS pmo_core_update_psoc_config(struct wlan_objmgr_psoc *psoc, 428 struct pmo_psoc_cfg *psoc_cfg) 429 { 430 struct pmo_psoc_priv_obj *psoc_ctx; 431 QDF_STATUS status = QDF_STATUS_SUCCESS; 432 433 pmo_enter(); 434 if (!psoc || !psoc_cfg) { 435 pmo_err("%s is null", !psoc ? "psoc":"psoc_cfg"); 436 status = QDF_STATUS_E_NULL_VALUE; 437 goto out; 438 } 439 440 pmo_psoc_with_ctx(psoc, psoc_ctx) { 441 qdf_mem_copy(&psoc_ctx->psoc_cfg, psoc_cfg, sizeof(*psoc_cfg)); 442 } 443 444 out: 445 pmo_exit(); 446 447 return status; 448 } 449 pmo_psoc_set_caps(struct wlan_objmgr_psoc * psoc,struct pmo_device_caps * caps)450 void pmo_psoc_set_caps(struct wlan_objmgr_psoc *psoc, 451 struct pmo_device_caps *caps) 452 { 453 struct pmo_psoc_priv_obj *psoc_ctx; 454 455 pmo_psoc_with_ctx(psoc, psoc_ctx) { 456 qdf_mem_copy(&psoc_ctx->caps, caps, sizeof(psoc_ctx->caps)); 457 } 458 } 459 pmo_core_psoc_set_hif_handle(struct wlan_objmgr_psoc * psoc,void * hif_hdl)460 void pmo_core_psoc_set_hif_handle(struct wlan_objmgr_psoc *psoc, 461 void *hif_hdl) 462 { 463 struct pmo_psoc_priv_obj *psoc_ctx; 464 465 pmo_psoc_with_ctx(psoc, psoc_ctx) { 466 psoc_ctx->hif_hdl = hif_hdl; 467 } 468 } 469 pmo_core_psoc_get_hif_handle(struct wlan_objmgr_psoc * psoc)470 void *pmo_core_psoc_get_hif_handle(struct wlan_objmgr_psoc *psoc) 471 { 472 void *hif_hdl = NULL; 473 struct pmo_psoc_priv_obj *psoc_ctx; 474 475 pmo_psoc_with_ctx(psoc, psoc_ctx) { 476 hif_hdl = psoc_ctx->hif_hdl; 477 } 478 479 return hif_hdl; 480 } 481 pmo_core_psoc_set_txrx_pdev_id(struct wlan_objmgr_psoc * psoc,uint8_t txrx_pdev_id)482 void pmo_core_psoc_set_txrx_pdev_id(struct wlan_objmgr_psoc *psoc, 483 uint8_t txrx_pdev_id) 484 { 485 struct pmo_psoc_priv_obj *psoc_ctx; 486 487 pmo_psoc_with_ctx(psoc, psoc_ctx) { 488 psoc_ctx->txrx_pdev_id = txrx_pdev_id; 489 } 490 } 491 pmo_core_psoc_get_txrx_handle(struct wlan_objmgr_psoc * psoc)492 uint8_t pmo_core_psoc_get_txrx_handle(struct wlan_objmgr_psoc *psoc) 493 { 494 uint8_t txrx_pdev_id = OL_TXRX_INVALID_PDEV_ID; 495 struct pmo_psoc_priv_obj *psoc_ctx; 496 497 pmo_psoc_with_ctx(psoc, psoc_ctx) { 498 txrx_pdev_id = psoc_ctx->txrx_pdev_id; 499 } 500 501 return txrx_pdev_id; 502 } 503 504 enum pmo_page_fault_action pmo_host_action_on_page_fault(struct wlan_objmgr_psoc * psoc)505 pmo_host_action_on_page_fault(struct wlan_objmgr_psoc *psoc) 506 { 507 struct pmo_psoc_priv_obj *pmo_psoc_ctx = pmo_psoc_get_priv(psoc); 508 509 if (!pmo_psoc_ctx) 510 return PMO_PF_HOST_ACTION_NO_OP; 511 512 return pmo_psoc_ctx->psoc_cfg.host_pf_action; 513 } 514 pmo_get_min_pagefault_wakeups_for_action(struct wlan_objmgr_psoc * psoc)515 uint8_t pmo_get_min_pagefault_wakeups_for_action(struct wlan_objmgr_psoc *psoc) 516 { 517 struct pmo_psoc_priv_obj *pmo_psoc_ctx = pmo_psoc_get_priv(psoc); 518 519 if (!pmo_psoc_ctx) 520 return 0; 521 522 return pmo_psoc_ctx->psoc_cfg.min_pagefault_wakeups_for_action; 523 } 524 525 uint32_t pmo_get_interval_for_pagefault_wakeup_counts(struct wlan_objmgr_psoc * psoc)526 pmo_get_interval_for_pagefault_wakeup_counts(struct wlan_objmgr_psoc *psoc) 527 { 528 struct pmo_psoc_priv_obj *pmo_psoc_ctx = pmo_psoc_get_priv(psoc); 529 530 if (!pmo_psoc_ctx) 531 return 0; 532 533 return pmo_psoc_ctx->psoc_cfg.interval_for_pagefault_wakeup_counts; 534 } 535 pmo_get_ssr_frequency_on_pagefault(struct wlan_objmgr_psoc * psoc)536 uint32_t pmo_get_ssr_frequency_on_pagefault(struct wlan_objmgr_psoc *psoc) 537 { 538 struct pmo_psoc_priv_obj *pmo_psoc_ctx = pmo_psoc_get_priv(psoc); 539 540 if (!pmo_psoc_ctx) 541 return 0; 542 543 return pmo_psoc_ctx->psoc_cfg.ssr_frequency_on_pagefault; 544 } 545 pmo_get_vdev_bridge_addr(struct wlan_objmgr_vdev * vdev,struct qdf_mac_addr * bridgeaddr)546 QDF_STATUS pmo_get_vdev_bridge_addr(struct wlan_objmgr_vdev *vdev, 547 struct qdf_mac_addr *bridgeaddr) 548 { 549 struct pmo_vdev_priv_obj *vdev_ctx; 550 551 if (!vdev) { 552 pmo_err("vdev is null"); 553 return QDF_STATUS_E_INVAL; 554 } 555 556 vdev_ctx = pmo_vdev_get_priv(vdev); 557 qdf_mem_copy(bridgeaddr->bytes, vdev_ctx->bridgeaddr, 558 QDF_MAC_ADDR_SIZE); 559 560 return QDF_STATUS_SUCCESS; 561 } 562 pmo_set_vdev_bridge_addr(struct wlan_objmgr_vdev * vdev,struct qdf_mac_addr * bridgeaddr)563 QDF_STATUS pmo_set_vdev_bridge_addr(struct wlan_objmgr_vdev *vdev, 564 struct qdf_mac_addr *bridgeaddr) 565 { 566 struct pmo_vdev_priv_obj *vdev_ctx; 567 568 if (!vdev) { 569 pmo_err("vdev is null"); 570 return QDF_STATUS_E_INVAL; 571 } 572 573 vdev_ctx = pmo_vdev_get_priv(vdev); 574 qdf_mem_copy(vdev_ctx->bridgeaddr, bridgeaddr->bytes, QDF_MAC_ADDR_SIZE); 575 576 return QDF_STATUS_SUCCESS; 577 } 578 pmo_core_get_listen_interval(struct wlan_objmgr_vdev * vdev,uint32_t * listen_interval)579 QDF_STATUS pmo_core_get_listen_interval(struct wlan_objmgr_vdev *vdev, 580 uint32_t *listen_interval) 581 { 582 struct pmo_vdev_priv_obj *vdev_ctx; 583 584 if (!vdev || !listen_interval) { 585 pmo_err("vdev NULL or NULL ptr"); 586 return QDF_STATUS_E_NULL_VALUE; 587 } 588 589 vdev_ctx = pmo_vdev_get_priv(vdev); 590 qdf_spin_lock_bh(&vdev_ctx->pmo_vdev_lock); 591 *listen_interval = vdev_ctx->dyn_listen_interval; 592 qdf_spin_unlock_bh(&vdev_ctx->pmo_vdev_lock); 593 594 return QDF_STATUS_SUCCESS; 595 } 596