1 /* 2 * Copyright (c) 2013-2021 The Linux Foundation. All rights reserved. 3 * Copyright (c) 2021-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 /* Include Files */ 21 #include "wlan_ipa_core.h" 22 #include "wlan_ipa_main.h" 23 #include "cdp_txrx_ipa.h" 24 #include "cdp_txrx_ctrl.h" 25 #include "wal_rx_desc.h" 26 #include "qdf_str.h" 27 #include "host_diag_core_event.h" 28 #include "wlan_objmgr_vdev_obj.h" 29 #include "qdf_platform.h" 30 #include <wmi_unified_param.h> 31 #include <wlan_osif_priv.h> 32 #include <net/cfg80211.h> 33 #ifdef IPA_OPT_WIFI_DP 34 #include "init_deinit_lmac.h" 35 #endif 36 #if defined(QCA_LL_TX_FLOW_CONTROL_V2) || !defined(QCA_IPA_LL_TX_FLOW_CONTROL) 37 #include <cdp_txrx_flow_ctrl_v2.h> 38 #include <cdp_txrx_peer_ops.h> 39 #endif 40 #include <qal_vbus_dev.h> 41 42 #define IPA_SPS_DESC_SIZE 8 43 #define IPA_DEFAULT_HDL 0 44 #ifdef IPA_WDS_EASYMESH_FEATURE 45 #define IPA_TA_PEER_ID_ATTRI 2 46 #endif 47 #ifdef IPA_OPT_WIFI_DP 48 #define IPA_WDI_MAX_FILTER 2 49 #define IPV6BYTES 16 /* IPV6 addr: 128bits/8 = 16bytes */ 50 #define IPV4BYTES 4 /* IPV4 addr: 32bits/8 = 4bytes */ 51 #define DP_MAX_SLEEP_TIME 100 52 #define IPV4 0x0008 53 #define IPV6 0xdd86 54 #define IPV6ARRAY 4 55 #define OPT_DP_TARGET_RESUME_WAIT_TIMEOUT_MS 50 56 #define OPT_DP_TARGET_RESUME_WAIT_COUNT 10 57 #endif 58 59 static struct wlan_ipa_priv *gp_ipa; 60 static void wlan_ipa_set_pending_tx_timer(struct wlan_ipa_priv *ipa_ctx); 61 static void wlan_ipa_reset_pending_tx_timer(struct wlan_ipa_priv *ipa_ctx); 62 63 static inline wlan_ipa_is_driver_unloading(struct wlan_ipa_priv * ipa_ctx)64 bool wlan_ipa_is_driver_unloading(struct wlan_ipa_priv *ipa_ctx) 65 { 66 if (ipa_ctx->driver_is_unloading) 67 return ipa_ctx->driver_is_unloading(); 68 return false; 69 } 70 71 static struct wlan_ipa_iface_2_client { 72 qdf_ipa_client_type_t cons_client; 73 qdf_ipa_client_type_t prod_client; 74 } wlan_ipa_iface_2_client[WLAN_IPA_CLIENT_MAX_IFACE] = { 75 { 76 QDF_IPA_CLIENT_WLAN2_CONS, QDF_IPA_CLIENT_WLAN1_PROD 77 }, 78 { 79 QDF_IPA_CLIENT_MCC2_CONS, QDF_IPA_CLIENT_WLAN1_PROD 80 }, 81 #if WLAN_IPA_CLIENT_MAX_IFACE >= 3 82 { 83 QDF_IPA_CLIENT_WLAN4_CONS, QDF_IPA_CLIENT_WLAN1_PROD 84 }, 85 #if WLAN_IPA_CLIENT_MAX_IFACE == 4 86 { 87 QDF_IPA_CLIENT_WLAN4_CONS, QDF_IPA_CLIENT_WLAN1_PROD 88 }, 89 #endif 90 #endif 91 }; 92 93 /* Local Function Prototypes */ 94 static void wlan_ipa_i2w_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 95 unsigned long data); 96 static void wlan_ipa_w2i_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 97 unsigned long data); 98 static void wlan_ipa_update_wds_params(struct wlan_ipa_priv *ipa_ctx, 99 qdf_ipa_wdi_init_in_params_t *in); 100 static void wlan_ipa_msg_wds_update(bool ipa_wds, qdf_ipa_wlan_msg_t *msg); 101 102 /** 103 * wlan_ipa_uc_sta_is_enabled() - Is STA mode IPA uC offload enabled? 104 * @ipa_cfg: IPA config 105 * 106 * Return: true if STA mode IPA uC offload is enabled, false otherwise 107 */ wlan_ipa_uc_sta_is_enabled(struct wlan_ipa_config * ipa_cfg)108 static inline bool wlan_ipa_uc_sta_is_enabled(struct wlan_ipa_config *ipa_cfg) 109 { 110 return WLAN_IPA_IS_CONFIG_ENABLED(ipa_cfg, WLAN_IPA_UC_STA_ENABLE_MASK); 111 } 112 113 /** 114 * wlan_ipa_is_pre_filter_enabled() - Is IPA pre-filter enabled? 115 * @ipa_cfg: IPA config 116 * 117 * Return: true if pre-filter is enabled, otherwise false 118 */ 119 static inline wlan_ipa_is_pre_filter_enabled(struct wlan_ipa_config * ipa_cfg)120 bool wlan_ipa_is_pre_filter_enabled(struct wlan_ipa_config *ipa_cfg) 121 { 122 return WLAN_IPA_IS_CONFIG_ENABLED(ipa_cfg, 123 WLAN_IPA_PRE_FILTER_ENABLE_MASK); 124 } 125 126 /** 127 * wlan_ipa_is_ipv6_enabled() - Is IPA IPv6 enabled? 128 * @ipa_cfg: IPA config 129 * 130 * Return: true if IPv6 is enabled, otherwise false 131 */ wlan_ipa_is_ipv6_enabled(struct wlan_ipa_config * ipa_cfg)132 static inline bool wlan_ipa_is_ipv6_enabled(struct wlan_ipa_config *ipa_cfg) 133 { 134 return WLAN_IPA_IS_CONFIG_ENABLED(ipa_cfg, WLAN_IPA_IPV6_ENABLE_MASK); 135 } 136 137 /** 138 * wlan_ipa_is_sta_only_offload_enabled() - Is IPA STA only offload enabled 139 * 140 * STA only IPA offload is needed on MDM platforms to support 141 * tethering scenarios in STA-SAP configurations when SAP is idle. 142 * 143 * Currently in STA-SAP configurations, IPA pipes are enabled only 144 * when a wifi client is connected to SAP. 145 * 146 * Impact of this API is only limited to when IPA pipes are enabled 147 * and disabled. To take effect, WLAN_IPA_UC_STA_ENABLE_MASK needs to 148 * set to 1. 149 * 150 * Return: true if MDM_PLATFORM is defined, false otherwise 151 */ 152 #ifdef MDM_PLATFORM wlan_ipa_is_sta_only_offload_enabled(void)153 static inline bool wlan_ipa_is_sta_only_offload_enabled(void) 154 { 155 return true; 156 } 157 #else 158 #ifdef IPA_OPT_WIFI_DP wlan_ipa_is_sta_only_offload_enabled(void)159 static inline bool wlan_ipa_is_sta_only_offload_enabled(void) 160 { 161 return true; 162 } 163 #else wlan_ipa_is_sta_only_offload_enabled(void)164 static inline bool wlan_ipa_is_sta_only_offload_enabled(void) 165 { 166 return false; 167 } 168 #endif /* IPA_OPT_WIFI_DP */ 169 #endif /* MDM_PLATFORM */ 170 171 /** 172 * wlan_ipa_msg_free_fn() - Free an IPA message 173 * @buff: pointer to the IPA message 174 * @len: length of the IPA message 175 * @type: type of IPA message 176 * 177 * Return: None 178 */ wlan_ipa_msg_free_fn(void * buff,uint32_t len,uint32_t type)179 static void wlan_ipa_msg_free_fn(void *buff, uint32_t len, uint32_t type) 180 { 181 ipa_debug("msg type:%d, len:%d", type, len); 182 qdf_mem_free(buff); 183 } 184 185 /** 186 * wlan_ipa_uc_loaded_uc_cb() - IPA UC loaded event callback 187 * @priv_ctxt: IPA context 188 * 189 * Will be called by IPA context. 190 * It's atomic context, then should be scheduled to kworker thread 191 * 192 * Return: None 193 */ wlan_ipa_uc_loaded_uc_cb(void * priv_ctxt)194 static void wlan_ipa_uc_loaded_uc_cb(void *priv_ctxt) 195 { 196 struct wlan_ipa_priv *ipa_ctx; 197 struct op_msg_type *msg; 198 struct uc_op_work_struct *uc_op_work; 199 200 if (!ipa_cb_is_ready()) { 201 ipa_info("IPA is not READY"); 202 return; 203 } 204 205 if (!priv_ctxt) { 206 ipa_err("Invalid IPA context"); 207 return; 208 } 209 210 ipa_ctx = priv_ctxt; 211 212 uc_op_work = &ipa_ctx->uc_op_work[WLAN_IPA_UC_OPCODE_UC_READY]; 213 if (!list_empty(&uc_op_work->work.work.entry)) { 214 /* uc_op_work is not initialized yet */ 215 ipa_ctx->uc_loaded = true; 216 return; 217 } 218 219 msg = qdf_mem_malloc(sizeof(*msg)); 220 if (!msg) 221 return; 222 223 msg->op_code = WLAN_IPA_UC_OPCODE_UC_READY; 224 225 /* When the same uC OPCODE is already pended, just return */ 226 if (uc_op_work->msg) 227 goto done; 228 229 uc_op_work->msg = msg; 230 231 if (!qdf_atomic_read(&ipa_ctx->deinit_in_prog)) { 232 qdf_sched_work(0, &uc_op_work->work); 233 } else { 234 uc_op_work->msg = NULL; 235 goto done; 236 } 237 238 /* work handler will free the msg buffer */ 239 return; 240 241 done: 242 qdf_mem_free(msg); 243 } 244 wlan_ipa_get_obj_context(void)245 struct wlan_ipa_priv *wlan_ipa_get_obj_context(void) 246 { 247 return gp_ipa; 248 } 249 250 /** 251 * wlan_ipa_send_pkt_to_tl() - Send an IPA packet to TL 252 * @iface_context: interface-specific IPA context 253 * @ipa_tx_desc: packet data descriptor 254 * 255 * Return: None 256 */ wlan_ipa_send_pkt_to_tl(struct wlan_ipa_iface_context * iface_context,qdf_ipa_rx_data_t * ipa_tx_desc)257 static void wlan_ipa_send_pkt_to_tl( 258 struct wlan_ipa_iface_context *iface_context, 259 qdf_ipa_rx_data_t *ipa_tx_desc) 260 { 261 struct wlan_ipa_priv *ipa_ctx = iface_context->ipa_ctx; 262 struct wlan_objmgr_pdev *pdev; 263 struct wlan_objmgr_psoc *psoc; 264 qdf_device_t osdev; 265 qdf_nbuf_t skb; 266 struct wlan_ipa_tx_desc *tx_desc; 267 qdf_dma_addr_t paddr; 268 QDF_STATUS status; 269 270 if (!ipa_ctx) 271 return; 272 pdev = ipa_ctx->pdev; 273 psoc = wlan_pdev_get_psoc(pdev); 274 osdev = wlan_psoc_get_qdf_dev(psoc); 275 276 qdf_spin_lock_bh(&iface_context->interface_lock); 277 /* 278 * During CAC period, data packets shouldn't be sent over the air so 279 * drop all the packets here 280 */ 281 if (iface_context->device_mode == QDF_SAP_MODE || 282 iface_context->device_mode == QDF_P2P_GO_MODE) { 283 if (ipa_ctx->dfs_cac_block_tx) { 284 ipa_free_skb(ipa_tx_desc); 285 qdf_spin_unlock_bh(&iface_context->interface_lock); 286 iface_context->stats.num_tx_cac_drop++; 287 wlan_ipa_wdi_rm_try_release(ipa_ctx); 288 return; 289 } 290 } 291 292 if (!osdev) { 293 ipa_free_skb(ipa_tx_desc); 294 iface_context->stats.num_tx_drop++; 295 qdf_spin_unlock_bh(&iface_context->interface_lock); 296 wlan_ipa_wdi_rm_try_release(ipa_ctx); 297 return; 298 } 299 qdf_spin_unlock_bh(&iface_context->interface_lock); 300 301 skb = QDF_IPA_RX_DATA_SKB(ipa_tx_desc); 302 303 qdf_mem_zero(skb->cb, sizeof(skb->cb)); 304 305 /* Store IPA Tx buffer ownership into SKB CB */ 306 qdf_nbuf_ipa_owned_set(skb); 307 308 if (qdf_mem_smmu_s1_enabled(osdev)) { 309 status = qdf_nbuf_map(osdev, skb, QDF_DMA_TO_DEVICE); 310 if (QDF_IS_STATUS_SUCCESS(status)) { 311 paddr = qdf_nbuf_get_frag_paddr(skb, 0); 312 } else { 313 ipa_free_skb(ipa_tx_desc); 314 qdf_spin_lock_bh(&iface_context->interface_lock); 315 iface_context->stats.num_tx_drop++; 316 qdf_spin_unlock_bh(&iface_context->interface_lock); 317 wlan_ipa_wdi_rm_try_release(ipa_ctx); 318 return; 319 } 320 } else { 321 paddr = QDF_IPA_RX_DATA_DMA_ADDR(ipa_tx_desc); 322 } 323 324 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 325 qdf_nbuf_mapped_paddr_set(skb, 326 paddr + 327 WLAN_IPA_WLAN_FRAG_HEADER + 328 WLAN_IPA_WLAN_IPA_HEADER); 329 QDF_IPA_RX_DATA_SKB_LEN(ipa_tx_desc) -= 330 WLAN_IPA_WLAN_FRAG_HEADER + WLAN_IPA_WLAN_IPA_HEADER; 331 } else { 332 qdf_nbuf_mapped_paddr_set(skb, paddr); 333 } 334 335 qdf_spin_lock_bh(&ipa_ctx->q_lock); 336 /* get free Tx desc and assign ipa_tx_desc pointer */ 337 if (ipa_ctx->tx_desc_free_list.count && 338 qdf_list_remove_front(&ipa_ctx->tx_desc_free_list, 339 (qdf_list_node_t **)&tx_desc) == 340 QDF_STATUS_SUCCESS) { 341 tx_desc->ipa_tx_desc_ptr = ipa_tx_desc; 342 ipa_ctx->stats.num_tx_desc_q_cnt++; 343 qdf_spin_unlock_bh(&ipa_ctx->q_lock); 344 /* Store Tx Desc index into SKB CB */ 345 qdf_nbuf_ipa_priv_set(skb, tx_desc->id); 346 } else { 347 ipa_ctx->stats.num_tx_desc_error++; 348 qdf_spin_unlock_bh(&ipa_ctx->q_lock); 349 350 if (qdf_mem_smmu_s1_enabled(osdev)) { 351 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) 352 qdf_nbuf_mapped_paddr_set(skb, paddr); 353 354 qdf_nbuf_unmap(osdev, skb, QDF_DMA_TO_DEVICE); 355 } 356 357 qdf_ipa_free_skb(ipa_tx_desc); 358 wlan_ipa_wdi_rm_try_release(ipa_ctx); 359 return; 360 } 361 362 skb = cdp_ipa_tx_send_data_frame(ipa_ctx->dp_soc, 363 iface_context->session_id, 364 QDF_IPA_RX_DATA_SKB(ipa_tx_desc)); 365 if (skb) { 366 qdf_nbuf_free(skb); 367 iface_context->stats.num_tx_err++; 368 return; 369 } 370 371 atomic_inc(&ipa_ctx->tx_ref_cnt); 372 373 iface_context->stats.num_tx++; 374 } 375 376 /** 377 * wlan_ipa_forward() - handle packet forwarding to wlan tx 378 * @ipa_ctx: pointer to ipa ipa context 379 * @iface_ctx: interface context 380 * @skb: data pointer 381 * 382 * if exception packet has set forward bit, copied new packet should be 383 * forwarded to wlan tx. if wlan subsystem is in suspend state, packet should 384 * put into pm queue and tx procedure will be differed 385 * 386 * Return: None 387 */ wlan_ipa_forward(struct wlan_ipa_priv * ipa_ctx,struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t skb)388 static void wlan_ipa_forward(struct wlan_ipa_priv *ipa_ctx, 389 struct wlan_ipa_iface_context *iface_ctx, 390 qdf_nbuf_t skb) 391 { 392 struct wlan_ipa_pm_tx_cb *pm_tx_cb; 393 394 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 395 396 /* Set IPA ownership for intra-BSS Tx packets to avoid skb_orphan */ 397 qdf_nbuf_ipa_owned_set(skb); 398 399 /* WLAN subsystem is in suspend, put in queue */ 400 if (ipa_ctx->suspended) { 401 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 402 ipa_info_rl("Tx in suspend, put in queue"); 403 qdf_mem_zero(skb->cb, sizeof(skb->cb)); 404 pm_tx_cb = (struct wlan_ipa_pm_tx_cb *)skb->cb; 405 pm_tx_cb->exception = true; 406 pm_tx_cb->iface_context = iface_ctx; 407 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 408 qdf_nbuf_queue_add(&ipa_ctx->pm_queue_head, skb); 409 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 410 ipa_ctx->stats.num_tx_queued++; 411 } else { 412 /* Resume, put packet into WLAN TX */ 413 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 414 415 if (ipa_ctx->softap_xmit) { 416 if (ipa_ctx->softap_xmit(skb, iface_ctx->dev)) { 417 ipa_err_rl("packet Tx fail"); 418 ipa_ctx->stats.num_tx_fwd_err++; 419 } else { 420 ipa_ctx->stats.num_tx_fwd_ok++; 421 } 422 } else { 423 dev_kfree_skb_any(skb); 424 } 425 } 426 } 427 428 #ifndef QCA_IPA_LL_TX_FLOW_CONTROL 429 static inline wlan_ipa_tx_desc_thresh_reached(struct cdp_soc_t * soc,uint8_t vdev_id)430 bool wlan_ipa_tx_desc_thresh_reached(struct cdp_soc_t *soc, uint8_t vdev_id) 431 { 432 return cdp_tx_desc_thresh_reached(soc, vdev_id); 433 } 434 435 static inline wlan_ipa_get_peer_state(struct cdp_soc_t * soc,uint8_t vdev_id,uint8_t * peer_mac)436 bool wlan_ipa_get_peer_state(struct cdp_soc_t *soc, uint8_t vdev_id, 437 uint8_t *peer_mac) 438 { 439 if (cdp_peer_state_get(soc, vdev_id, peer_mac, false) == 440 OL_TXRX_PEER_STATE_AUTH) 441 return true; 442 443 return false; 444 } 445 #else 446 static inline wlan_ipa_tx_desc_thresh_reached(struct cdp_soc_t * soc,uint8_t vdev_id)447 bool wlan_ipa_tx_desc_thresh_reached(struct cdp_soc_t *soc, uint8_t vdev_id) 448 { 449 return false; 450 } 451 452 static inline wlan_ipa_get_peer_state(struct cdp_soc_t * soc,uint8_t vdev_id,uint8_t * peer_mac)453 bool wlan_ipa_get_peer_state(struct cdp_soc_t *soc, uint8_t vdev_id, 454 uint8_t *peer_mac) 455 { 456 return cdp_peer_get_authorize(soc, vdev_id, peer_mac); 457 } 458 #endif 459 460 /** 461 * wlan_ipa_intrabss_forward() - Forward intra bss packets. 462 * @ipa_ctx: pointer to IPA IPA struct 463 * @iface_ctx: ipa interface context 464 * @desc: Firmware descriptor 465 * @skb: Data buffer 466 * 467 * Return: 468 * WLAN_IPA_FORWARD_PKT_NONE 469 * WLAN_IPA_FORWARD_PKT_DISCARD 470 * WLAN_IPA_FORWARD_PKT_LOCAL_STACK 471 * 472 */ wlan_ipa_intrabss_forward(struct wlan_ipa_priv * ipa_ctx,struct wlan_ipa_iface_context * iface_ctx,uint8_t desc,qdf_nbuf_t skb)473 static enum wlan_ipa_forward_type wlan_ipa_intrabss_forward( 474 struct wlan_ipa_priv *ipa_ctx, 475 struct wlan_ipa_iface_context *iface_ctx, 476 uint8_t desc, 477 qdf_nbuf_t skb) 478 { 479 int ret = WLAN_IPA_FORWARD_PKT_NONE; 480 void *soc = ipa_ctx->dp_soc; 481 482 if ((desc & FW_RX_DESC_FORWARD_M)) { 483 if (wlan_ipa_tx_desc_thresh_reached(soc, 484 iface_ctx->session_id)) { 485 /* Drop the packet*/ 486 ipa_ctx->stats.num_tx_fwd_err++; 487 goto drop_pkt; 488 } 489 490 ipa_debug_rl("Forward packet to Tx (fw_desc=%d)", desc); 491 ipa_ctx->ipa_tx_forward++; 492 493 if ((desc & FW_RX_DESC_DISCARD_M)) { 494 wlan_ipa_forward(ipa_ctx, iface_ctx, skb); 495 ipa_ctx->ipa_rx_internal_drop_count++; 496 ipa_ctx->ipa_rx_discard++; 497 ret = WLAN_IPA_FORWARD_PKT_DISCARD; 498 } else { 499 struct sk_buff *cloned_skb = skb_clone(skb, GFP_ATOMIC); 500 501 if (cloned_skb) 502 wlan_ipa_forward(ipa_ctx, iface_ctx, 503 cloned_skb); 504 else 505 ipa_err_rl("tx skb alloc failed"); 506 ret = WLAN_IPA_FORWARD_PKT_LOCAL_STACK; 507 } 508 } 509 return ret; 510 511 drop_pkt: 512 dev_kfree_skb_any(skb); 513 ret = WLAN_IPA_FORWARD_PKT_DISCARD; 514 return ret; 515 } 516 517 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 10, 0)) || \ 518 defined(CONFIG_IPA_WDI_UNIFIED_API) 519 /* 520 * TODO: Get WDI version through FW capabilities 521 */ 522 #if defined(QCA_WIFI_QCA6290) || defined(QCA_WIFI_QCA6390) || \ 523 defined(QCA_WIFI_QCA6490) || defined(QCA_WIFI_QCA6750) || \ 524 defined(QCA_WIFI_WCN7850) wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv * ipa_ctx)525 static inline void wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv *ipa_ctx) 526 { 527 ipa_ctx->wdi_version = IPA_WDI_3; 528 } 529 #elif defined(QCA_WIFI_KIWI) || defined(QCA_WIFI_KIWI_V2) wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv * ipa_ctx)530 static inline void wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv *ipa_ctx) 531 { 532 ipa_ctx->wdi_version = IPA_WDI_3_V2; 533 } 534 #elif defined(QCA_WIFI_QCN9000) || defined(QCA_WIFI_QCN9224) wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv * ipa_ctx)535 static inline void wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv *ipa_ctx) 536 { 537 uint8_t wdi_ver; 538 539 cdp_ipa_get_wdi_version(ipa_ctx->dp_soc, &wdi_ver); 540 ipa_ctx->wdi_version = wdi_ver; 541 } 542 #elif defined(QCA_WIFI_3_0) wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv * ipa_ctx)543 static inline void wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv *ipa_ctx) 544 { 545 ipa_ctx->wdi_version = IPA_WDI_2; 546 } 547 #else wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv * ipa_ctx)548 static inline void wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv *ipa_ctx) 549 { 550 ipa_ctx->wdi_version = IPA_WDI_1; 551 } 552 #endif 553 wlan_ipa_wdi_is_smmu_enabled(struct wlan_ipa_priv * ipa_ctx,qdf_device_t osdev)554 static inline bool wlan_ipa_wdi_is_smmu_enabled(struct wlan_ipa_priv *ipa_ctx, 555 qdf_device_t osdev) 556 { 557 return ipa_ctx->is_smmu_enabled && qdf_mem_smmu_s1_enabled(osdev); 558 } 559 560 #ifdef IPA_WDS_EASYMESH_FEATURE 561 /** 562 * wlan_ipa_ast_notify_cb() - IPA AST create/update CB 563 * @priv: IPA context 564 * @data: Structure used for updating the AST table 565 * 566 * Will be called by IPA context. 567 * 568 * Return: None 569 */ wlan_ipa_ast_notify_cb(void * priv,void * data)570 static void wlan_ipa_ast_notify_cb(void *priv, void *data) 571 { 572 qdf_ipa_ast_info_type_t *ast_info; 573 struct wlan_ipa_priv *ipa_ctx; 574 575 if (!data) { 576 dp_err("Invalid IPA AST data context"); 577 return; 578 } 579 580 if (!priv) { 581 dp_err("Invalid IPA context"); 582 return; 583 } 584 585 ast_info = (qdf_ipa_ast_info_type_t *)data; 586 ipa_ctx = (struct wlan_ipa_priv *)priv; 587 588 cdp_ipa_ast_create(ipa_ctx->dp_soc, ast_info); 589 } 590 #else wlan_ipa_ast_notify_cb(void * priv,void * data)591 static inline void wlan_ipa_ast_notify_cb(void *priv, void *data) 592 { 593 } 594 #endif 595 596 static inline QDF_STATUS wlan_ipa_wdi_setup(struct wlan_ipa_priv * ipa_ctx,qdf_device_t osdev)597 wlan_ipa_wdi_setup(struct wlan_ipa_priv *ipa_ctx, 598 qdf_device_t osdev) 599 { 600 qdf_ipa_sys_connect_params_t *sys_in = NULL; 601 int i; 602 QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; 603 604 sys_in = qdf_mem_malloc(sizeof(*sys_in) * WLAN_IPA_MAX_IFACE); 605 if (!sys_in) 606 return QDF_STATUS_E_NOMEM; 607 608 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) 609 qdf_mem_copy(sys_in + i, 610 &ipa_ctx->sys_pipe[i].ipa_sys_params, 611 sizeof(qdf_ipa_sys_connect_params_t)); 612 613 qdf_status = cdp_ipa_setup(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id, 614 wlan_ipa_i2w_cb, wlan_ipa_w2i_cb, 615 wlan_ipa_wdi_meter_notifier_cb, 616 ipa_ctx->config->desc_size, 617 ipa_ctx, 618 wlan_ipa_is_rm_enabled(ipa_ctx->config), 619 &ipa_ctx->tx_pipe_handle, 620 &ipa_ctx->rx_pipe_handle, 621 wlan_ipa_wdi_is_smmu_enabled(ipa_ctx, osdev), 622 sys_in, ipa_ctx->over_gsi, ipa_ctx->hdl, 623 (qdf_ipa_wdi_hdl_t)ipa_ctx->instance_id, 624 wlan_ipa_ast_notify_cb); 625 626 qdf_mem_free(sys_in); 627 628 return qdf_status; 629 } 630 631 #ifdef FEATURE_METERING 632 /** 633 * wlan_ipa_wdi_init_metering() - IPA WDI metering init 634 * @ipa_ctxt: IPA context 635 * @in: IPA WDI in param 636 * 637 * Return: QDF_STATUS 638 */ wlan_ipa_wdi_init_metering(struct wlan_ipa_priv * ipa_ctxt,qdf_ipa_wdi_init_in_params_t * in)639 static inline void wlan_ipa_wdi_init_metering(struct wlan_ipa_priv *ipa_ctxt, 640 qdf_ipa_wdi_init_in_params_t *in) 641 { 642 QDF_IPA_WDI_INIT_IN_PARAMS_WDI_NOTIFY(in) = 643 wlan_ipa_wdi_meter_notifier_cb; 644 } 645 #else wlan_ipa_wdi_init_metering(struct wlan_ipa_priv * ipa_ctxt,qdf_ipa_wdi_init_in_params_t * in)646 static inline void wlan_ipa_wdi_init_metering(struct wlan_ipa_priv *ipa_ctxt, 647 qdf_ipa_wdi_init_in_params_t *in) 648 { 649 } 650 #endif 651 652 #ifdef IPA_OPT_WIFI_DP 653 /** 654 * wlan_ipa_wdi_init_set_opt_wifi_dp - set if optional wifi dp enabled from IPA 655 * @ipa_ctxt: IPA context 656 * @out: IPA WDI out param 657 * 658 * Return: QDF_STATUS 659 */ wlan_ipa_wdi_init_set_opt_wifi_dp(struct wlan_ipa_priv * ipa_ctxt,qdf_ipa_wdi_init_out_params_t * out)660 static inline QDF_STATUS wlan_ipa_wdi_init_set_opt_wifi_dp( 661 struct wlan_ipa_priv *ipa_ctxt, 662 qdf_ipa_wdi_init_out_params_t *out) 663 { 664 uint32_t val; 665 val = cfg_get(ipa_ctxt->pdev->pdev_objmgr.wlan_psoc, 666 CFG_DP_IPA_OFFLOAD_CONFIG); 667 668 ipa_ctxt->opt_wifi_datapath = 669 QDF_IPA_WDI_INIT_OUT_PARAMS_OPT_WIFI_DP(out); 670 if (!ipa_ctxt->opt_wifi_datapath && 671 !(val & WLAN_IPA_ENABLE_MASK) && 672 (ipa_ctxt->config->ipa_config == INTRL_MODE_ENABLE)) { 673 ipa_err(" opt_wifi_datapath not support by IPA"); 674 return QDF_STATUS_E_INVAL; 675 } 676 677 return QDF_STATUS_SUCCESS; 678 } 679 680 /** 681 * wlan_ipa_opt_wifi_dp_enabled - set if optional wifi dp enabled in WLAN 682 * 683 * Return: bool 684 */ wlan_ipa_opt_wifi_dp_enabled(void)685 static inline bool wlan_ipa_opt_wifi_dp_enabled(void) 686 { 687 return true; 688 } 689 #else wlan_ipa_wdi_init_set_opt_wifi_dp(struct wlan_ipa_priv * ipa_ctxt,qdf_ipa_wdi_init_out_params_t * out)690 static inline QDF_STATUS wlan_ipa_wdi_init_set_opt_wifi_dp( 691 struct wlan_ipa_priv *ipa_ctxt, 692 qdf_ipa_wdi_init_out_params_t *out) 693 { 694 return QDF_STATUS_SUCCESS; 695 } 696 wlan_ipa_opt_wifi_dp_enabled(void)697 static inline bool wlan_ipa_opt_wifi_dp_enabled(void) 698 { 699 return false; 700 } 701 #endif 702 703 #ifdef IPA_WDS_EASYMESH_FEATURE 704 /** 705 * wlan_ipa_update_wds_params() - IPA update WDS parameters 706 * @ipa_ctx: IPA context 707 * @in: IPA wdi init in params 708 * 709 * This function is to update wds status to IPA in wdi init params 710 * 711 * Return: None 712 */ wlan_ipa_update_wds_params(struct wlan_ipa_priv * ipa_ctx,qdf_ipa_wdi_init_in_params_t * in)713 static void wlan_ipa_update_wds_params(struct wlan_ipa_priv *ipa_ctx, 714 qdf_ipa_wdi_init_in_params_t *in) 715 { 716 QDF_IPA_WDI_INIT_IN_PARAMS_WDS_UPDATE(in) = ipa_ctx->config->ipa_wds; 717 } 718 719 /** 720 * wlan_ipa_msg_wds_update() - IPA message WDS update 721 * @ipa_wds: IPA WDS status 722 * @msg: Meta data message for IPA 723 * 724 * This function is to update wds status to IPA in meta message 725 * 726 * Return: None 727 */ wlan_ipa_msg_wds_update(bool ipa_wds,qdf_ipa_wlan_msg_t * msg)728 static void wlan_ipa_msg_wds_update(bool ipa_wds, 729 qdf_ipa_wlan_msg_t *msg) 730 { 731 QDF_IPA_WLAN_MSG_WDS_UPDATE(msg) = ipa_wds; 732 } 733 #else wlan_ipa_update_wds_params(struct wlan_ipa_priv * ipa_ctx,qdf_ipa_wdi_init_in_params_t * in)734 static void wlan_ipa_update_wds_params(struct wlan_ipa_priv *ipa_ctx, 735 qdf_ipa_wdi_init_in_params_t *in) 736 { 737 } 738 wlan_ipa_msg_wds_update(bool ipa_wds,qdf_ipa_wlan_msg_t * msg)739 static void wlan_ipa_msg_wds_update(bool ipa_wds, 740 qdf_ipa_wlan_msg_t *msg) 741 { 742 } 743 #endif 744 745 /** 746 * wlan_ipa_wdi_init() - IPA WDI init 747 * @ipa_ctx: IPA context 748 * 749 * Return: QDF_STATUS 750 */ wlan_ipa_wdi_init(struct wlan_ipa_priv * ipa_ctx)751 static inline QDF_STATUS wlan_ipa_wdi_init(struct wlan_ipa_priv *ipa_ctx) 752 { 753 qdf_ipa_wdi_init_in_params_t in; 754 qdf_ipa_wdi_init_out_params_t out; 755 QDF_STATUS status; 756 int ret; 757 758 ipa_ctx->uc_loaded = false; 759 760 qdf_mem_zero(&in, sizeof(in)); 761 qdf_mem_zero(&out, sizeof(out)); 762 763 QDF_IPA_WDI_INIT_IN_PARAMS_WDI_VERSION(&in) = ipa_ctx->wdi_version; 764 QDF_IPA_WDI_INIT_IN_PARAMS_NOTIFY(&in) = wlan_ipa_uc_loaded_uc_cb; 765 QDF_IPA_WDI_INIT_IN_PARAMS_PRIV(&in) = ipa_ctx; 766 QDF_IPA_WDI_INIT_IN_PARAMS_INSTANCE_ID(&in) = ipa_ctx->instance_id; 767 wlan_ipa_update_wds_params(ipa_ctx, &in); 768 wlan_ipa_wdi_init_metering(ipa_ctx, &in); 769 ret = qdf_ipa_wdi_init(&in, &out); 770 if (ret) { 771 ipa_err("ipa_wdi_init failed with ret=%d", ret); 772 return QDF_STATUS_E_FAILURE; 773 } 774 775 ipa_ctx->over_gsi = 776 QDF_IPA_WDI_INIT_OUT_PARAMS_IS_OVER_GSI(&out); 777 ipa_ctx->is_smmu_enabled = 778 QDF_IPA_WDI_INIT_OUT_PARAMS_IS_SMMU_ENABLED(&out); 779 ipa_ctx->hdl = QDF_IPA_WDI_INIT_OUT_PARAMS_HANDLE(&out); 780 781 ipa_info("ipa_over_gsi: %d, is_smmu_enabled: %d, handle: %d", 782 ipa_ctx->over_gsi, ipa_ctx->is_smmu_enabled, ipa_ctx->hdl); 783 784 if (QDF_IPA_WDI_INIT_OUT_PARAMS_IS_UC_READY(&out)) { 785 ipa_debug("IPA uC READY"); 786 ipa_ctx->uc_loaded = true; 787 } else { 788 ipa_info("IPA uc not ready"); 789 return QDF_STATUS_E_BUSY; 790 } 791 792 status = wlan_ipa_wdi_init_set_opt_wifi_dp(ipa_ctx, &out); 793 if (QDF_IS_STATUS_ERROR(status)) { 794 ret = qdf_ipa_wdi_cleanup(ipa_ctx->hdl); 795 if (ret) 796 ipa_info("ipa_wdi_cleanup failed ret=%d", ret); 797 ipa_set_cap_offload(false); 798 return status; 799 } 800 ipa_debug("opt_dp: enabled from IPA : %d", 801 ipa_ctx->opt_wifi_datapath); 802 803 return QDF_STATUS_SUCCESS; 804 } 805 wlan_ipa_wdi_cleanup(qdf_ipa_wdi_hdl_t hdl)806 static inline int wlan_ipa_wdi_cleanup(qdf_ipa_wdi_hdl_t hdl) 807 { 808 int ret; 809 810 ret = qdf_ipa_wdi_cleanup(hdl); 811 if (ret) 812 ipa_info("ipa_wdi_cleanup failed ret=%d", ret); 813 return ret; 814 } 815 wlan_ipa_wdi_setup_sys_pipe(struct wlan_ipa_priv * ipa_ctx,struct ipa_sys_connect_params * sys,uint32_t * handle)816 static inline int wlan_ipa_wdi_setup_sys_pipe(struct wlan_ipa_priv *ipa_ctx, 817 struct ipa_sys_connect_params *sys, 818 uint32_t *handle) 819 { 820 return 0; 821 } 822 wlan_ipa_wdi_teardown_sys_pipe(struct wlan_ipa_priv * ipa_ctx,uint32_t handle)823 static inline int wlan_ipa_wdi_teardown_sys_pipe(struct wlan_ipa_priv *ipa_ctx, 824 uint32_t handle) 825 { 826 return 0; 827 } 828 829 /** 830 * wlan_ipa_pm_flush() - flush queued packets 831 * @data: IPA context 832 * 833 * Called during PM resume to send packets to TL which were queued 834 * while host was in the process of suspending. 835 * 836 * Return: None 837 */ wlan_ipa_pm_flush(void * data)838 static void wlan_ipa_pm_flush(void *data) 839 { 840 struct wlan_ipa_priv *ipa_ctx = (struct wlan_ipa_priv *)data; 841 struct wlan_ipa_pm_tx_cb *pm_tx_cb = NULL; 842 qdf_nbuf_t skb; 843 uint32_t dequeued = 0; 844 qdf_netdev_t ndev; 845 846 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 847 while (((skb = qdf_nbuf_queue_remove(&ipa_ctx->pm_queue_head)) != 848 NULL)) { 849 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 850 851 pm_tx_cb = (struct wlan_ipa_pm_tx_cb *)skb->cb; 852 dequeued++; 853 854 if (pm_tx_cb->exception) { 855 if (ipa_ctx->softap_xmit && 856 pm_tx_cb->iface_context->dev) { 857 ipa_ctx->softap_xmit(skb, 858 pm_tx_cb->iface_context->dev); 859 ipa_ctx->stats.num_tx_fwd_ok++; 860 } else { 861 dev_kfree_skb_any(skb); 862 } 863 } else if (pm_tx_cb->send_to_nw) { 864 ndev = pm_tx_cb->iface_context->dev; 865 866 if (ipa_ctx->send_to_nw && ndev) { 867 ipa_ctx->send_to_nw(skb, ndev); 868 ipa_ctx->ipa_rx_net_send_count++; 869 } else { 870 dev_kfree_skb_any(skb); 871 } 872 } else { 873 wlan_ipa_send_pkt_to_tl(pm_tx_cb->iface_context, 874 pm_tx_cb->ipa_tx_desc); 875 } 876 877 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 878 } 879 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 880 881 ipa_ctx->stats.num_tx_dequeued += dequeued; 882 if (dequeued > ipa_ctx->stats.num_max_pm_queue) 883 ipa_ctx->stats.num_max_pm_queue = dequeued; 884 } 885 wlan_ipa_uc_smmu_map(bool map,uint32_t num_buf,qdf_mem_info_t * buf_arr)886 int wlan_ipa_uc_smmu_map(bool map, uint32_t num_buf, qdf_mem_info_t *buf_arr) 887 { 888 if (!ipa_cb_is_ready()) { 889 ipa_info("IPA is not READY"); 890 return 0; 891 } 892 893 if (!num_buf) { 894 ipa_info("No buffers to map/unmap"); 895 return 0; 896 } 897 /** 898 * This API will compile for prelithium chipset 899 * where we have only one soc so passing default 900 * handle to IPA which is 0. 901 */ 902 if (map) 903 return qdf_ipa_wdi_create_smmu_mapping(IPA_DEFAULT_HDL, 904 num_buf, buf_arr); 905 else 906 return qdf_ipa_wdi_release_smmu_mapping(IPA_DEFAULT_HDL, 907 num_buf, buf_arr); 908 return 0; 909 } 910 911 #ifdef MDM_PLATFORM 912 /** 913 * is_rx_dest_bridge_dev() - is RX skb bridge device terminated 914 * @iface_ctx: pointer to WLAN IPA interface context 915 * @nbuf: skb buffer 916 * 917 * Check if skb is destined for bridge device, where SAP is a bridge 918 * port of it. 919 * 920 * FIXME: If there's a BH lockless API to check if destination MAC 921 * address is a valid peer, this check can be deleted. Currently 922 * dp_find_peer_by_addr() is used to check if destination MAC 923 * is a valid peer. Since WLAN IPA RX is in process context, 924 * qdf_spin_lock_bh in dp_find_peer_by_addr() turns to spin_lock_bh 925 * and this BH lock hurts netif_rx. 926 * 927 * Return: true/false 928 */ is_rx_dest_bridge_dev(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t nbuf)929 static bool is_rx_dest_bridge_dev(struct wlan_ipa_iface_context *iface_ctx, 930 qdf_nbuf_t nbuf) 931 { 932 qdf_netdev_t master_ndev; 933 qdf_netdev_t ndev; 934 struct ethhdr *eh; 935 uint8_t da_is_bcmc; 936 bool ret; 937 938 /* 939 * WDI 3.0 skb->cb[] info from IPA driver 940 * skb->cb[0] = vdev_id 941 * skb->cb[1].bit#1 = da_is_bcmc 942 */ 943 da_is_bcmc = ((uint8_t)nbuf->cb[1]) & 0x2; 944 if (da_is_bcmc) 945 return false; 946 947 ndev = iface_ctx->dev; 948 if (!ndev) 949 return false; 950 951 if (!netif_is_bridge_port(ndev)) 952 return false; 953 954 qal_vbus_rcu_read_lock(); 955 956 master_ndev = netdev_master_upper_dev_get_rcu(ndev); 957 if (!master_ndev) { 958 ret = false; 959 goto out; 960 } 961 962 eh = (struct ethhdr *)qdf_nbuf_data(nbuf); 963 if (qdf_mem_cmp(eh->h_dest, master_ndev->dev_addr, QDF_MAC_ADDR_SIZE)) { 964 ret = false; 965 goto out; 966 } 967 968 ret = true; 969 970 out: 971 qal_vbus_rcu_read_unlock(); 972 return ret; 973 } 974 #else /* !MDM_PLATFORM */ is_rx_dest_bridge_dev(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t nbuf)975 static bool is_rx_dest_bridge_dev(struct wlan_ipa_iface_context *iface_ctx, 976 qdf_nbuf_t nbuf) 977 { 978 return false; 979 } 980 #endif /* MDM_PLATFORM */ 981 982 static enum wlan_ipa_forward_type wlan_ipa_rx_intrabss_fwd(struct wlan_ipa_priv * ipa_ctx,struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t nbuf)983 wlan_ipa_rx_intrabss_fwd(struct wlan_ipa_priv *ipa_ctx, 984 struct wlan_ipa_iface_context *iface_ctx, 985 qdf_nbuf_t nbuf) 986 { 987 uint8_t fw_desc = 0; 988 bool fwd_success; 989 int ret; 990 991 /* legacy intra-bss forwarding for WDI 1.0 and 2.0 */ 992 if (ipa_ctx->wdi_version < IPA_WDI_3) { 993 fw_desc = (uint8_t)nbuf->cb[1]; 994 return wlan_ipa_intrabss_forward(ipa_ctx, iface_ctx, fw_desc, 995 nbuf); 996 } 997 998 if (is_rx_dest_bridge_dev(iface_ctx, nbuf)) { 999 fwd_success = 0; 1000 ret = WLAN_IPA_FORWARD_PKT_LOCAL_STACK; 1001 goto exit; 1002 } 1003 1004 if (cdp_ipa_rx_intrabss_fwd(ipa_ctx->dp_soc, iface_ctx->session_id, 1005 nbuf, &fwd_success)) { 1006 ipa_ctx->ipa_rx_internal_drop_count++; 1007 ipa_ctx->ipa_rx_discard++; 1008 1009 ret = WLAN_IPA_FORWARD_PKT_DISCARD; 1010 } else { 1011 ret = WLAN_IPA_FORWARD_PKT_LOCAL_STACK; 1012 } 1013 1014 exit: 1015 if (fwd_success) 1016 ipa_ctx->stats.num_tx_fwd_ok++; 1017 else 1018 ipa_ctx->stats.num_tx_fwd_err++; 1019 1020 return ret; 1021 } 1022 1023 #else /* CONFIG_IPA_WDI_UNIFIED_API */ 1024 wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv * ipa_ctx)1025 static inline void wlan_ipa_wdi_get_wdi_version(struct wlan_ipa_priv *ipa_ctx) 1026 { 1027 } 1028 wlan_ipa_wdi_is_smmu_enabled(struct wlan_ipa_priv * ipa_ctx,qdf_device_t osdev)1029 static inline int wlan_ipa_wdi_is_smmu_enabled(struct wlan_ipa_priv *ipa_ctx, 1030 qdf_device_t osdev) 1031 { 1032 return qdf_mem_smmu_s1_enabled(osdev); 1033 } 1034 wlan_ipa_wdi_setup(struct wlan_ipa_priv * ipa_ctx,qdf_device_t osdev)1035 static inline QDF_STATUS wlan_ipa_wdi_setup(struct wlan_ipa_priv *ipa_ctx, 1036 qdf_device_t osdev) 1037 { 1038 return cdp_ipa_setup(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id, 1039 wlan_ipa_i2w_cb, wlan_ipa_w2i_cb, 1040 wlan_ipa_wdi_meter_notifier_cb, 1041 ipa_ctx->config->desc_size, 1042 ipa_ctx, wlan_ipa_is_rm_enabled(ipa_ctx->config), 1043 &ipa_ctx->tx_pipe_handle, 1044 &ipa_ctx->rx_pipe_handle); 1045 } 1046 wlan_ipa_wdi_init(struct wlan_ipa_priv * ipa_ctx)1047 static inline QDF_STATUS wlan_ipa_wdi_init(struct wlan_ipa_priv *ipa_ctx) 1048 { 1049 struct ipa_wdi_uc_ready_params uc_ready_param; 1050 1051 ipa_ctx->uc_loaded = false; 1052 uc_ready_param.priv = (void *)ipa_ctx; 1053 uc_ready_param.notify = wlan_ipa_uc_loaded_uc_cb; 1054 if (qdf_ipa_uc_reg_rdyCB(&uc_ready_param)) { 1055 ipa_info("UC Ready CB register fail"); 1056 return QDF_STATUS_E_FAILURE; 1057 } 1058 1059 if (true == uc_ready_param.is_uC_ready) { 1060 ipa_info("UC Ready"); 1061 ipa_ctx->uc_loaded = true; 1062 } else { 1063 return QDF_STATUS_E_BUSY; 1064 } 1065 1066 return QDF_STATUS_SUCCESS; 1067 } 1068 wlan_ipa_wdi_cleanup(void)1069 static inline int wlan_ipa_wdi_cleanup(void) 1070 { 1071 int ret; 1072 1073 ret = qdf_ipa_uc_dereg_rdyCB(); 1074 if (ret) 1075 ipa_info("UC Ready CB deregister fail"); 1076 return ret; 1077 } 1078 wlan_ipa_wdi_setup_sys_pipe(struct wlan_ipa_priv * ipa_ctx,struct ipa_sys_connect_params * sys,uint32_t * handle)1079 static inline int wlan_ipa_wdi_setup_sys_pipe( 1080 struct wlan_ipa_priv *ipa_ctx, 1081 struct ipa_sys_connect_params *sys, uint32_t *handle) 1082 { 1083 return qdf_ipa_setup_sys_pipe(sys, handle); 1084 } 1085 wlan_ipa_wdi_teardown_sys_pipe(struct wlan_ipa_priv * ipa_ctx,uint32_t handle)1086 static inline int wlan_ipa_wdi_teardown_sys_pipe( 1087 struct wlan_ipa_priv *ipa_ctx, 1088 uint32_t handle) 1089 { 1090 return qdf_ipa_teardown_sys_pipe(handle); 1091 } 1092 1093 /** 1094 * wlan_ipa_pm_flush() - flush queued packets 1095 * @data: IPA context 1096 * 1097 * Called during PM resume to send packets to TL which were queued 1098 * while host was in the process of suspending. 1099 * 1100 * Return: None 1101 */ wlan_ipa_pm_flush(void * data)1102 static void wlan_ipa_pm_flush(void *data) 1103 { 1104 struct wlan_ipa_priv *ipa_ctx = (struct wlan_ipa_priv *)data; 1105 struct wlan_ipa_pm_tx_cb *pm_tx_cb = NULL; 1106 qdf_nbuf_t skb; 1107 uint32_t dequeued = 0; 1108 1109 qdf_wake_lock_acquire(&ipa_ctx->wake_lock, 1110 WIFI_POWER_EVENT_WAKELOCK_IPA); 1111 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 1112 while (((skb = qdf_nbuf_queue_remove(&ipa_ctx->pm_queue_head)) != 1113 NULL)) { 1114 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1115 1116 pm_tx_cb = (struct wlan_ipa_pm_tx_cb *)skb->cb; 1117 dequeued++; 1118 1119 if (pm_tx_cb->exception) { 1120 if (ipa_ctx->softap_xmit && 1121 pm_tx_cb->iface_context->dev) { 1122 ipa_ctx->softap_xmit(skb, 1123 pm_tx_cb->iface_context->dev); 1124 ipa_ctx->stats.num_tx_fwd_ok++; 1125 } else { 1126 dev_kfree_skb_any(skb); 1127 } 1128 } else { 1129 wlan_ipa_send_pkt_to_tl(pm_tx_cb->iface_context, 1130 pm_tx_cb->ipa_tx_desc); 1131 } 1132 1133 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 1134 } 1135 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1136 qdf_wake_lock_release(&ipa_ctx->wake_lock, 1137 WIFI_POWER_EVENT_WAKELOCK_IPA); 1138 1139 ipa_ctx->stats.num_tx_dequeued += dequeued; 1140 if (dequeued > ipa_ctx->stats.num_max_pm_queue) 1141 ipa_ctx->stats.num_max_pm_queue = dequeued; 1142 } 1143 wlan_ipa_uc_smmu_map(bool map,uint32_t num_buf,qdf_mem_info_t * buf_arr)1144 int wlan_ipa_uc_smmu_map(bool map, uint32_t num_buf, qdf_mem_info_t *buf_arr) 1145 { 1146 if (!num_buf) { 1147 ipa_info("No buffers to map/unmap"); 1148 return 0; 1149 } 1150 1151 if (map) 1152 return qdf_ipa_wdi_create_smmu_mapping(IPA_DEFAULT_HDL, 1153 num_buf, buf_arr); 1154 else 1155 return qdf_ipa_wdi_release_smmu_mapping(IPA_DEFAULT_HDL, 1156 num_buf, buf_arr); 1157 return 0; 1158 } 1159 1160 static enum wlan_ipa_forward_type wlan_ipa_rx_intrabss_fwd(struct wlan_ipa_priv * ipa_ctx,struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t nbuf)1161 wlan_ipa_rx_intrabss_fwd(struct wlan_ipa_priv *ipa_ctx, 1162 struct wlan_ipa_iface_context *iface_ctx, 1163 qdf_nbuf_t nbuf) 1164 { 1165 uint8_t fw_desc; 1166 1167 fw_desc = (uint8_t)nbuf->cb[1]; 1168 1169 return wlan_ipa_intrabss_forward(ipa_ctx, iface_ctx, fw_desc, nbuf); 1170 } 1171 1172 #endif /* CONFIG_IPA_WDI_UNIFIED_API */ 1173 1174 /** 1175 * wlan_ipa_send_sta_eapol_to_nw() - Send Rx EAPOL pkt for STA to Kernel 1176 * @skb: network buffer 1177 * @pdev: pdev obj 1178 * 1179 * Called when a EAPOL packet is received via IPA Exception path 1180 * before wlan_ipa_setup_iface is done for STA. 1181 * 1182 * Return: 0 on success, err_code for failure. 1183 */ wlan_ipa_send_sta_eapol_to_nw(qdf_nbuf_t skb,struct wlan_objmgr_pdev * pdev)1184 static int wlan_ipa_send_sta_eapol_to_nw(qdf_nbuf_t skb, 1185 struct wlan_objmgr_pdev *pdev) 1186 { 1187 struct wlan_ipa_priv *ipa_ctx; 1188 struct ethhdr *eh; 1189 struct wlan_objmgr_vdev *vdev = NULL; 1190 1191 ipa_ctx = ipa_pdev_get_priv_obj(pdev); 1192 if (!ipa_ctx) 1193 return -EINVAL; 1194 1195 eh = (struct ethhdr *)qdf_nbuf_data(skb); 1196 vdev = wlan_objmgr_get_vdev_by_macaddr_from_pdev( 1197 pdev, eh->h_dest, WLAN_IPA_ID); 1198 if (!vdev) { 1199 ipa_err_rl("Invalid vdev"); 1200 return -EINVAL; 1201 } 1202 1203 if (wlan_vdev_mlme_get_opmode(vdev) != QDF_STA_MODE) { 1204 ipa_err_rl("device_mode is not STA"); 1205 wlan_objmgr_vdev_release_ref(vdev, WLAN_IPA_ID); 1206 return -EINVAL; 1207 } 1208 1209 skb->destructor = wlan_ipa_uc_rt_debug_destructor; 1210 1211 if (ipa_ctx->send_to_nw) 1212 ipa_ctx->send_to_nw(skb, vdev->vdev_nif.osdev->wdev->netdev); 1213 1214 ipa_ctx->ipa_rx_net_send_count++; 1215 ipa_ctx->stats.num_rx_no_iface_eapol++; 1216 wlan_objmgr_vdev_release_ref(vdev, WLAN_IPA_ID); 1217 return 0; 1218 } 1219 1220 #ifndef QCA_IPA_LL_TX_FLOW_CONTROL 1221 1222 #ifdef SAP_DHCP_FW_IND 1223 /** 1224 * wlan_ipa_send_to_nw_sap_dhcp - Check if SAP mode and skb is a DHCP packet 1225 * @iface_ctx: IPA per-interface ctx 1226 * @skb: socket buffer 1227 * 1228 * Check if @iface_ctx is SAP and @skb is a DHCP packet. 1229 * 1230 * When SAP_DHCP_FW_IND feature is enabled, DHCP packets received will be 1231 * notified to target via WMI cmd. However if system is suspended, WMI 1232 * cmd is not allowed from Host to Target. 1233 * 1234 * Return: true if iface is SAP mode and skb is a DHCP packet. Otherwise false 1235 */ 1236 static bool wlan_ipa_send_to_nw_sap_dhcp(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t skb)1237 wlan_ipa_send_to_nw_sap_dhcp(struct wlan_ipa_iface_context *iface_ctx, 1238 qdf_nbuf_t skb) 1239 { 1240 if (iface_ctx->device_mode == QDF_SAP_MODE && 1241 qdf_nbuf_is_ipv4_dhcp_pkt(skb) == true) 1242 return true; 1243 1244 return false; 1245 } 1246 #else /* !SAP_DHCP_FW_IND */ 1247 static inline bool wlan_ipa_send_to_nw_sap_dhcp(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t skb)1248 wlan_ipa_send_to_nw_sap_dhcp(struct wlan_ipa_iface_context *iface_ctx, 1249 qdf_nbuf_t skb) 1250 { 1251 return false; 1252 } 1253 #endif /* SAP_DHCP_FW_IND */ 1254 1255 /** 1256 * wlan_ipa_send_to_nw_defer - Check if skb needs to deferred to network stack 1257 * @iface_ctx: IPA per-interface ctx 1258 * @skb: socket buffer 1259 * 1260 * Check if @skb received on @iface_ctx needs to be deferred to be passed 1261 * up to network stack. 1262 * 1263 * Return: true if needs to be deferred, otherwise false 1264 */ wlan_ipa_send_to_nw_defer(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t skb)1265 static bool wlan_ipa_send_to_nw_defer(struct wlan_ipa_iface_context *iface_ctx, 1266 qdf_nbuf_t skb) 1267 { 1268 struct wlan_ipa_priv *ipa_ctx = iface_ctx->ipa_ctx; 1269 1270 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 1271 if (!ipa_ctx->suspended) { 1272 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1273 return false; 1274 } 1275 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1276 1277 return wlan_ipa_send_to_nw_sap_dhcp(iface_ctx, skb); 1278 } 1279 1280 /** 1281 * wlan_ipa_send_to_nw_queue - Add skb to pm_queue_head if deferred 1282 * @iface_ctx: IPA per-interface ctx 1283 * @skb: socket buffer 1284 * 1285 * Add @skb to pm_queue_head to defer passing up to network stack due to 1286 * system suspended. 1287 * 1288 * Return: None 1289 */ wlan_ipa_send_to_nw_queue(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t skb)1290 static void wlan_ipa_send_to_nw_queue(struct wlan_ipa_iface_context *iface_ctx, 1291 qdf_nbuf_t skb) 1292 { 1293 struct wlan_ipa_priv *ipa_ctx = iface_ctx->ipa_ctx; 1294 struct wlan_ipa_pm_tx_cb *pm_cb; 1295 1296 qdf_mem_zero(skb->cb, sizeof(skb->cb)); 1297 pm_cb = (struct wlan_ipa_pm_tx_cb *)skb->cb; 1298 1299 pm_cb->send_to_nw = true; 1300 pm_cb->iface_context = iface_ctx; 1301 1302 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 1303 qdf_nbuf_queue_add(&ipa_ctx->pm_queue_head, skb); 1304 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1305 1306 ipa_ctx->stats.num_tx_queued++; 1307 } 1308 #else /* QCA_IPA_LL_TX_FLOW_CONTROL */ 1309 static inline bool wlan_ipa_send_to_nw_defer(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t skb)1310 wlan_ipa_send_to_nw_defer(struct wlan_ipa_iface_context *iface_ctx, 1311 qdf_nbuf_t skb) 1312 { 1313 return false; 1314 } 1315 1316 static inline void wlan_ipa_send_to_nw_queue(struct wlan_ipa_iface_context * iface_ctx,qdf_nbuf_t skb)1317 wlan_ipa_send_to_nw_queue(struct wlan_ipa_iface_context *iface_ctx, 1318 qdf_nbuf_t skb) 1319 { 1320 } 1321 #endif /* QCA_IPA_LL_TX_FLOW_CONTROL */ 1322 1323 #if defined(IPA_OFFLOAD) && defined(QCA_SUPPORT_WDS_EXTENDED) 1324 /** 1325 * wlan_ipa_send_skb_to_network() - Send skb to kernel 1326 * @skb: network buffer 1327 * @peer_id: Peer id to get respective peer 1328 * @iface_ctx: IPA interface context 1329 * 1330 * Called when a network buffer is received which should not be routed 1331 * to the IPA module. 1332 * 1333 * Return: None 1334 */ 1335 static void wlan_ipa_send_skb_to_network(qdf_nbuf_t skb,uint8_t peer_id,struct wlan_ipa_iface_context * iface_ctx)1336 wlan_ipa_send_skb_to_network(qdf_nbuf_t skb, uint8_t peer_id, 1337 struct wlan_ipa_iface_context *iface_ctx) 1338 { 1339 struct wlan_ipa_priv *ipa_ctx; 1340 1341 ipa_ctx = iface_ctx->ipa_ctx; 1342 1343 if (!iface_ctx->dev) { 1344 ipa_debug_rl("Invalid interface"); 1345 ipa_ctx->ipa_rx_internal_drop_count++; 1346 dev_kfree_skb_any(skb); 1347 return; 1348 } 1349 1350 skb->destructor = wlan_ipa_uc_rt_debug_destructor; 1351 1352 if (wlan_ipa_send_to_nw_defer(iface_ctx, skb)) { 1353 wlan_ipa_send_to_nw_queue(iface_ctx, skb); 1354 } else { 1355 if (!cdp_ipa_rx_wdsext_iface(ipa_ctx->dp_soc, peer_id, skb)) { 1356 if (ipa_ctx->send_to_nw) 1357 ipa_ctx->send_to_nw(skb, iface_ctx->dev); 1358 } 1359 ipa_ctx->ipa_rx_net_send_count++; 1360 } 1361 } 1362 #else 1363 /** 1364 * wlan_ipa_send_skb_to_network() - Send skb to kernel 1365 * @skb: network buffer 1366 * @peer_id: Peer id to get respective peer 1367 * @iface_ctx: IPA interface context 1368 * 1369 * Called when a network buffer is received which should not be routed 1370 * to the IPA module. 1371 * 1372 * Return: None 1373 */ 1374 static void wlan_ipa_send_skb_to_network(qdf_nbuf_t skb,uint8_t peer_id,struct wlan_ipa_iface_context * iface_ctx)1375 wlan_ipa_send_skb_to_network(qdf_nbuf_t skb, uint8_t peer_id, 1376 struct wlan_ipa_iface_context *iface_ctx) 1377 { 1378 struct wlan_ipa_priv *ipa_ctx; 1379 1380 ipa_ctx = iface_ctx->ipa_ctx; 1381 1382 if (!iface_ctx->dev) { 1383 ipa_debug_rl("Invalid interface"); 1384 ipa_ctx->ipa_rx_internal_drop_count++; 1385 dev_kfree_skb_any(skb); 1386 return; 1387 } 1388 1389 skb->destructor = wlan_ipa_uc_rt_debug_destructor; 1390 1391 if (wlan_ipa_send_to_nw_defer(iface_ctx, skb)) { 1392 wlan_ipa_send_to_nw_queue(iface_ctx, skb); 1393 } else { 1394 if (ipa_ctx->send_to_nw) 1395 ipa_ctx->send_to_nw(skb, iface_ctx->dev); 1396 1397 ipa_ctx->ipa_rx_net_send_count++; 1398 } 1399 } 1400 #endif 1401 1402 /** 1403 * wlan_ipa_eapol_intrabss_fwd_check() - Check if eapol pkt intrabss fwd is 1404 * allowed or not 1405 * @ipa_ctx: IPA global context 1406 * @vdev_id: vdev id 1407 * @nbuf: network buffer 1408 * 1409 * Return: true if intrabss fwd is allowed for eapol else false 1410 */ 1411 static bool wlan_ipa_eapol_intrabss_fwd_check(struct wlan_ipa_priv * ipa_ctx,uint8_t vdev_id,qdf_nbuf_t nbuf)1412 wlan_ipa_eapol_intrabss_fwd_check(struct wlan_ipa_priv *ipa_ctx, 1413 uint8_t vdev_id, qdf_nbuf_t nbuf) 1414 { 1415 uint8_t *vdev_mac_addr; 1416 1417 vdev_mac_addr = cdp_get_vdev_mac_addr(ipa_ctx->dp_soc, vdev_id); 1418 1419 if (!vdev_mac_addr) 1420 return false; 1421 1422 if (qdf_mem_cmp(qdf_nbuf_data(nbuf) + QDF_NBUF_DEST_MAC_OFFSET, 1423 vdev_mac_addr, QDF_MAC_ADDR_SIZE)) 1424 return false; 1425 1426 return true; 1427 } 1428 1429 #ifdef MDM_PLATFORM 1430 static inline void wlan_ipa_set_sap_client_auth(struct wlan_ipa_priv * ipa_ctx,const uint8_t * peer_mac,uint8_t is_authenticated)1431 wlan_ipa_set_sap_client_auth(struct wlan_ipa_priv *ipa_ctx, 1432 const uint8_t *peer_mac, 1433 uint8_t is_authenticated) 1434 { 1435 uint8_t idx; 1436 struct ipa_uc_stas_map *sta_map; 1437 1438 for (idx = 0; idx < WLAN_IPA_MAX_STA_COUNT; idx++) { 1439 sta_map = &ipa_ctx->assoc_stas_map[idx]; 1440 if (sta_map->is_reserved && 1441 qdf_is_macaddr_equal(&sta_map->mac_addr, 1442 (struct qdf_mac_addr *)peer_mac)) { 1443 sta_map->is_authenticated = is_authenticated; 1444 break; 1445 } 1446 } 1447 } 1448 1449 static inline uint8_t wlan_ipa_get_sap_client_auth(struct wlan_ipa_priv * ipa_ctx,uint8_t * peer_mac)1450 wlan_ipa_get_sap_client_auth(struct wlan_ipa_priv *ipa_ctx, uint8_t *peer_mac) 1451 { 1452 uint8_t idx; 1453 struct ipa_uc_stas_map *sta_map; 1454 1455 for (idx = 0; idx < WLAN_IPA_MAX_STA_COUNT; idx++) { 1456 sta_map = &ipa_ctx->assoc_stas_map[idx]; 1457 if (sta_map->is_reserved && 1458 qdf_is_macaddr_equal(&sta_map->mac_addr, 1459 (struct qdf_mac_addr *)peer_mac)) { 1460 return sta_map->is_authenticated; 1461 } 1462 } 1463 1464 return false; 1465 } 1466 1467 /** 1468 * wlan_ipa_check_peer_auth() - Check whether peer is authenticated or not 1469 * @dp_soc: soc handle 1470 * @peer_mac: peer mac address 1471 * @iface: wlan ipa iface context 1472 * 1473 * Return: true if peer is authenticated 1474 */ 1475 #ifdef QCA_WIFI_QCN9224 1476 static inline bool wlan_ipa_check_peer_auth(ol_txrx_soc_handle dp_soc,uint8_t * peer_mac,struct wlan_ipa_iface_context * iface)1477 wlan_ipa_check_peer_auth(ol_txrx_soc_handle dp_soc, 1478 uint8_t *peer_mac, 1479 struct wlan_ipa_iface_context *iface) 1480 { 1481 uint8_t is_authenticated = false; 1482 struct cdp_ast_entry_info ast_info = {0}; 1483 1484 cdp_peer_get_ast_info_by_soc(dp_soc, peer_mac, 1485 &ast_info); 1486 peer_mac = &ast_info.peer_mac_addr[0]; 1487 is_authenticated = wlan_ipa_get_peer_state(dp_soc, 1488 iface->session_id, 1489 peer_mac); 1490 1491 return is_authenticated; 1492 } 1493 #else 1494 static inline bool wlan_ipa_check_peer_auth(ol_txrx_soc_handle dp_soc,uint8_t * peer_mac,struct wlan_ipa_iface_context * iface)1495 wlan_ipa_check_peer_auth(ol_txrx_soc_handle dp_soc, 1496 uint8_t *peer_mac, 1497 struct wlan_ipa_iface_context *iface) 1498 { 1499 uint8_t is_authenticated = false; 1500 1501 is_authenticated = wlan_ipa_get_peer_state(dp_soc, iface->session_id, 1502 peer_mac); 1503 1504 return is_authenticated; 1505 } 1506 #endif 1507 1508 #ifdef IPA_WDS_EASYMESH_FEATURE 1509 static inline uint8_t wlan_ipa_get_peer_auth_state(ol_txrx_soc_handle dp_soc,uint8_t * peer_mac,struct wlan_ipa_iface_context * iface)1510 wlan_ipa_get_peer_auth_state(ol_txrx_soc_handle dp_soc, uint8_t *peer_mac, 1511 struct wlan_ipa_iface_context *iface) 1512 { 1513 uint8_t is_authenticated = false; 1514 struct cdp_ast_entry_info ast_info = {0}; 1515 1516 if (ipa_is_wds_enabled()) { 1517 cdp_peer_get_ast_info_by_soc(dp_soc, peer_mac, 1518 &ast_info); 1519 peer_mac = &ast_info.peer_mac_addr[0]; 1520 is_authenticated = wlan_ipa_get_peer_state(dp_soc, 1521 iface->session_id, 1522 peer_mac); 1523 } else { 1524 is_authenticated = wlan_ipa_get_peer_state(dp_soc, 1525 iface->session_id, 1526 peer_mac); 1527 } 1528 1529 return is_authenticated; 1530 } 1531 #else 1532 static inline uint8_t wlan_ipa_get_peer_auth_state(ol_txrx_soc_handle dp_soc,uint8_t * peer_mac,struct wlan_ipa_iface_context * iface)1533 wlan_ipa_get_peer_auth_state(ol_txrx_soc_handle dp_soc, uint8_t *peer_mac, 1534 struct wlan_ipa_iface_context *iface) 1535 { 1536 1537 return wlan_ipa_check_peer_auth(dp_soc, peer_mac, iface); 1538 } 1539 #endif 1540 1541 static inline bool wlan_ipa_is_peer_authenticated(ol_txrx_soc_handle dp_soc,struct wlan_ipa_iface_context * iface,uint8_t * peer_mac)1542 wlan_ipa_is_peer_authenticated(ol_txrx_soc_handle dp_soc, 1543 struct wlan_ipa_iface_context *iface, 1544 uint8_t *peer_mac) 1545 { 1546 uint8_t is_authenticated = false; 1547 1548 if (iface->device_mode == QDF_SAP_MODE) { 1549 is_authenticated = wlan_ipa_get_sap_client_auth(iface->ipa_ctx, 1550 peer_mac); 1551 if (is_authenticated) 1552 return is_authenticated; 1553 1554 is_authenticated = wlan_ipa_get_peer_auth_state(dp_soc, 1555 peer_mac, 1556 iface); 1557 1558 if (is_authenticated) 1559 wlan_ipa_set_sap_client_auth(iface->ipa_ctx, 1560 peer_mac, 1561 true); 1562 1563 } else if (iface->device_mode == QDF_STA_MODE) { 1564 is_authenticated = iface->is_authenticated; 1565 if (is_authenticated) 1566 return is_authenticated; 1567 is_authenticated = wlan_ipa_get_peer_state(dp_soc, 1568 iface->session_id, 1569 peer_mac); 1570 if (is_authenticated) 1571 iface->is_authenticated = true; 1572 } 1573 1574 return is_authenticated; 1575 } 1576 #else /* !MDM_PLATFORM */ 1577 static inline void wlan_ipa_set_sap_client_auth(struct wlan_ipa_priv * ipa_ctx,const uint8_t * peer_mac,uint8_t is_authenticated)1578 wlan_ipa_set_sap_client_auth(struct wlan_ipa_priv *ipa_ctx, 1579 const uint8_t *peer_mac, 1580 uint8_t is_authenticated) 1581 {} 1582 1583 static inline bool wlan_ipa_is_peer_authenticated(ol_txrx_soc_handle dp_soc,struct wlan_ipa_iface_context * iface,uint8_t * peer_mac)1584 wlan_ipa_is_peer_authenticated(ol_txrx_soc_handle dp_soc, 1585 struct wlan_ipa_iface_context *iface, 1586 uint8_t *peer_mac) 1587 { 1588 uint8_t is_authenticated = 0; 1589 1590 is_authenticated = wlan_ipa_get_peer_state(dp_soc, 1591 iface->session_id, 1592 peer_mac); 1593 1594 return is_authenticated; 1595 } 1596 #endif /* MDM_PLATFORM */ 1597 1598 /** 1599 * __wlan_ipa_w2i_cb() - WLAN to IPA callback handler 1600 * @priv: pointer to private data registered with IPA (we register a 1601 * pointer to the global IPA context) 1602 * @evt: the IPA event which triggered the callback 1603 * @data: data associated with the event 1604 * 1605 * Return: None 1606 */ __wlan_ipa_w2i_cb(void * priv,qdf_ipa_dp_evt_type_t evt,unsigned long data)1607 static void __wlan_ipa_w2i_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 1608 unsigned long data) 1609 { 1610 struct wlan_ipa_priv *ipa_ctx = NULL; 1611 qdf_nbuf_t skb; 1612 uint8_t iface_id; 1613 uint8_t session_id = 0xff; 1614 struct wlan_ipa_iface_context *iface_context; 1615 bool is_eapol_wapi = false; 1616 struct qdf_mac_addr peer_mac_addr = QDF_MAC_ADDR_ZERO_INIT; 1617 uint8_t peer_id; 1618 1619 ipa_ctx = (struct wlan_ipa_priv *)priv; 1620 if (!ipa_ctx) { 1621 if (evt == IPA_RECEIVE) { 1622 skb = (qdf_nbuf_t)data; 1623 dev_kfree_skb_any(skb); 1624 } 1625 return; 1626 } 1627 1628 switch (evt) { 1629 case IPA_RECEIVE: 1630 skb = (qdf_nbuf_t) data; 1631 if (wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 1632 session_id = (uint8_t)skb->cb[0]; 1633 iface_id = ipa_ctx->vdev_to_iface[session_id]; 1634 ipa_ctx->stats.num_rx_excep++; 1635 qdf_nbuf_pull_head(skb, WLAN_IPA_UC_WLAN_CLD_HDR_LEN); 1636 } else { 1637 iface_id = WLAN_IPA_GET_IFACE_ID(skb->data); 1638 qdf_nbuf_pull_head(skb, WLAN_IPA_WLAN_CLD_HDR_LEN); 1639 } 1640 1641 if (iface_id >= WLAN_IPA_MAX_IFACE) { 1642 ipa_err_rl("Invalid iface_id %u,session_id %x %x %x %x", 1643 iface_id, session_id, (uint8_t)skb->cb[1], 1644 (uint8_t)skb->cb[2], (uint8_t)skb->cb[3]); 1645 1646 if (qdf_nbuf_is_ipv4_eapol_pkt(skb)) { 1647 ipa_err_rl("EAPOL pkt. Sending to NW!"); 1648 if (!wlan_ipa_send_sta_eapol_to_nw( 1649 skb, ipa_ctx->pdev)) 1650 break; 1651 } 1652 ipa_err_rl("Pkt Dropped!"); 1653 ipa_ctx->ipa_rx_internal_drop_count++; 1654 dev_kfree_skb_any(skb); 1655 return; 1656 } 1657 1658 iface_context = &ipa_ctx->iface_context[iface_id]; 1659 if (iface_context->session_id >= WLAN_IPA_MAX_SESSION) { 1660 ipa_err_rl("session_id of iface_id %u is invalid:%d", 1661 iface_id, iface_context->session_id); 1662 ipa_ctx->ipa_rx_internal_drop_count++; 1663 dev_kfree_skb_any(skb); 1664 return; 1665 } 1666 iface_context->stats.num_rx_ipa_excep++; 1667 1668 if (iface_context->device_mode == QDF_STA_MODE) 1669 qdf_copy_macaddr(&peer_mac_addr, &iface_context->bssid); 1670 else if (iface_context->device_mode == QDF_SAP_MODE) 1671 qdf_mem_copy(&peer_mac_addr.bytes[0], 1672 qdf_nbuf_data(skb) + 1673 QDF_NBUF_SRC_MAC_OFFSET, 1674 QDF_MAC_ADDR_SIZE); 1675 1676 cdp_ipa_update_peer_rx_stats(ipa_ctx->dp_soc, 1677 iface_context->session_id, 1678 &peer_mac_addr.bytes[0], 1679 skb); 1680 if (qdf_nbuf_is_ipv4_eapol_pkt(skb)) { 1681 is_eapol_wapi = true; 1682 if (iface_context->device_mode == QDF_SAP_MODE && 1683 !wlan_ipa_eapol_intrabss_fwd_check(ipa_ctx, 1684 iface_context->session_id, skb)) { 1685 ipa_err_rl("EAPOL intrabss fwd drop DA:" QDF_MAC_ADDR_FMT, 1686 QDF_MAC_ADDR_REF(qdf_nbuf_data(skb) + 1687 QDF_NBUF_DEST_MAC_OFFSET)); 1688 ipa_ctx->ipa_rx_internal_drop_count++; 1689 dev_kfree_skb_any(skb); 1690 return; 1691 } 1692 } else if (qdf_nbuf_is_ipv4_wapi_pkt(skb)) { 1693 is_eapol_wapi = true; 1694 } 1695 1696 /* 1697 * Check for peer authorized state before allowing 1698 * non-EAPOL/WAPI frames to be intrabss forwarded 1699 * or submitted to stack. 1700 */ 1701 if (!wlan_ipa_is_peer_authenticated(ipa_ctx->dp_soc, 1702 iface_context, 1703 &peer_mac_addr.bytes[0]) && 1704 !is_eapol_wapi) { 1705 ipa_err_rl("Non EAPOL/WAPI packet received when peer " QDF_MAC_ADDR_FMT " is unauthorized", 1706 QDF_MAC_ADDR_REF(peer_mac_addr.bytes)); 1707 ipa_ctx->ipa_rx_internal_drop_count++; 1708 dev_kfree_skb_any(skb); 1709 return; 1710 } 1711 1712 /* Disable to forward Intra-BSS Rx packets when 1713 * ap_isolate=1 in hostapd.conf 1714 */ 1715 if (!ipa_ctx->disable_intrabss_fwd[iface_context->session_id] && 1716 iface_context->device_mode == QDF_SAP_MODE) { 1717 /* 1718 * When INTRA_BSS_FWD_OFFLOAD is enabled, FW will send 1719 * all Rx packets to IPA uC, which need to be forwarded 1720 * to other interface. 1721 * And, IPA driver will send back to WLAN host driver 1722 * through exception pipe with fw_desc field set by FW. 1723 * Here we are checking fw_desc field for FORWARD bit 1724 * set, and forward to Tx. Then copy to kernel stack 1725 * only when DISCARD bit is not set. 1726 */ 1727 if (WLAN_IPA_FORWARD_PKT_DISCARD == 1728 wlan_ipa_rx_intrabss_fwd(ipa_ctx, iface_context, 1729 skb)) 1730 break; 1731 } else { 1732 ipa_debug_rl("Intra-BSS fwd disabled for session_id %u", 1733 iface_context->session_id); 1734 } 1735 1736 peer_id = (uint8_t)skb->cb[WLAN_IPA_NBUF_CB_PEER_ID_OFFSET]; 1737 wlan_ipa_send_skb_to_network(skb, peer_id, iface_context); 1738 break; 1739 1740 default: 1741 ipa_err_rl("w2i cb wrong event: 0x%x", evt); 1742 return; 1743 } 1744 } 1745 1746 #ifndef MDM_PLATFORM 1747 /** 1748 * wlan_ipa_w2i_cb() - SSR wrapper for __wlan_ipa_w2i_cb 1749 * @priv: pointer to private data registered with IPA (we register a 1750 * pointer to the global IPA context) 1751 * @evt: the IPA event which triggered the callback 1752 * @data: data associated with the event 1753 * 1754 * Return: None 1755 */ wlan_ipa_w2i_cb(void * priv,qdf_ipa_dp_evt_type_t evt,unsigned long data)1756 static void wlan_ipa_w2i_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 1757 unsigned long data) 1758 { 1759 struct qdf_op_sync *op_sync; 1760 1761 if (qdf_op_protect(&op_sync)) { 1762 if (evt == IPA_RECEIVE) { 1763 struct wlan_ipa_priv *ipa_ctx = priv; 1764 qdf_nbuf_t skb = (qdf_nbuf_t)data; 1765 1766 ipa_ctx->ipa_rx_internal_drop_count++; 1767 dev_kfree_skb_any(skb); 1768 } 1769 1770 return; 1771 } 1772 1773 __wlan_ipa_w2i_cb(priv, evt, data); 1774 1775 qdf_op_unprotect(op_sync); 1776 } 1777 #else /* MDM_PLATFORM */ wlan_ipa_w2i_cb(void * priv,qdf_ipa_dp_evt_type_t evt,unsigned long data)1778 static void wlan_ipa_w2i_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 1779 unsigned long data) 1780 { 1781 __wlan_ipa_w2i_cb(priv, evt, data); 1782 } 1783 #endif /* MDM_PLATFORM */ 1784 1785 #if !defined(QCA_LL_TX_FLOW_CONTROL_V2) && !defined(QCA_IPA_LL_TX_FLOW_CONTROL) 1786 1787 /** 1788 * __wlan_ipa_i2w_cb() - IPA to WLAN callback 1789 * @priv: pointer to private data registered with IPA (we register a 1790 * pointer to the interface-specific IPA context) 1791 * @evt: the IPA event which triggered the callback 1792 * @data: data associated with the event 1793 * 1794 * Return: None 1795 */ __wlan_ipa_i2w_cb(void * priv,qdf_ipa_dp_evt_type_t evt,unsigned long data)1796 static void __wlan_ipa_i2w_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 1797 unsigned long data) 1798 { 1799 struct wlan_ipa_priv *ipa_ctx = NULL; 1800 qdf_ipa_rx_data_t *ipa_tx_desc; 1801 struct wlan_ipa_iface_context *iface_context; 1802 qdf_nbuf_t skb; 1803 struct wlan_ipa_pm_tx_cb *pm_tx_cb = NULL; 1804 1805 iface_context = (struct wlan_ipa_iface_context *)priv; 1806 ipa_tx_desc = (qdf_ipa_rx_data_t *)data; 1807 ipa_ctx = iface_context->ipa_ctx; 1808 1809 if (evt != IPA_RECEIVE) { 1810 ipa_err_rl("Event is not IPA_RECEIVE"); 1811 ipa_free_skb(ipa_tx_desc); 1812 iface_context->stats.num_tx_drop++; 1813 return; 1814 } 1815 1816 skb = QDF_IPA_RX_DATA_SKB(ipa_tx_desc); 1817 1818 /* 1819 * If PROD resource is not requested here then there may be cases where 1820 * IPA hardware may be clocked down because of not having proper 1821 * dependency graph between WLAN CONS and modem PROD pipes. Adding the 1822 * workaround to request PROD resource while data is going over CONS 1823 * pipe to prevent the IPA hardware clockdown. 1824 */ 1825 wlan_ipa_wdi_rm_request(ipa_ctx); 1826 1827 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 1828 /* 1829 * If host is still suspended then queue the packets and these will be 1830 * drained later when resume completes. When packet is arrived here and 1831 * host is suspended, this means that there is already resume is in 1832 * progress. 1833 */ 1834 if (ipa_ctx->suspended) { 1835 qdf_mem_zero(skb->cb, sizeof(skb->cb)); 1836 pm_tx_cb = (struct wlan_ipa_pm_tx_cb *)skb->cb; 1837 pm_tx_cb->iface_context = iface_context; 1838 pm_tx_cb->ipa_tx_desc = ipa_tx_desc; 1839 qdf_nbuf_queue_add(&ipa_ctx->pm_queue_head, skb); 1840 ipa_ctx->stats.num_tx_queued++; 1841 1842 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1843 return; 1844 } 1845 1846 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1847 1848 /* 1849 * If we are here means, host is not suspended, wait for the work queue 1850 * to finish. 1851 */ 1852 qdf_flush_work(&ipa_ctx->pm_work); 1853 1854 return wlan_ipa_send_pkt_to_tl(iface_context, ipa_tx_desc); 1855 } 1856 1857 /** 1858 * wlan_ipa_i2w_cb() - IPA to WLAN callback 1859 * @priv: pointer to private data registered with IPA (we register a 1860 * pointer to the interface-specific IPA context) 1861 * @evt: the IPA event which triggered the callback 1862 * @data: data associated with the event 1863 * 1864 * Return: None 1865 */ wlan_ipa_i2w_cb(void * priv,qdf_ipa_dp_evt_type_t evt,unsigned long data)1866 static void wlan_ipa_i2w_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 1867 unsigned long data) 1868 { 1869 struct qdf_op_sync *op_sync; 1870 1871 if (qdf_op_protect(&op_sync)) { 1872 qdf_ipa_rx_data_t *ipa_tx_desc = (qdf_ipa_rx_data_t *)data; 1873 struct wlan_ipa_iface_context *iface_context = priv; 1874 1875 ipa_free_skb(ipa_tx_desc); 1876 iface_context->stats.num_tx_drop++; 1877 1878 return; 1879 } 1880 1881 __wlan_ipa_i2w_cb(priv, evt, data); 1882 1883 qdf_op_unprotect(op_sync); 1884 } 1885 1886 #else /* QCA_LL_TX_FLOW_CONTROL_V2 */ 1887 1888 /** 1889 * wlan_ipa_i2w_cb() - IPA to WLAN callback 1890 * @priv: pointer to private data registered with IPA (we register a 1891 * pointer to the interface-specific IPA context) 1892 * @evt: the IPA event which triggered the callback 1893 * @data: data associated with the event 1894 * 1895 * Return: None 1896 */ wlan_ipa_i2w_cb(void * priv,qdf_ipa_dp_evt_type_t evt,unsigned long data)1897 static void wlan_ipa_i2w_cb(void *priv, qdf_ipa_dp_evt_type_t evt, 1898 unsigned long data) 1899 { 1900 } 1901 1902 #endif /* QCA_LL_TX_FLOW_CONTROL_V2 */ 1903 wlan_ipa_suspend(struct wlan_ipa_priv * ipa_ctx)1904 QDF_STATUS wlan_ipa_suspend(struct wlan_ipa_priv *ipa_ctx) 1905 { 1906 /* 1907 * Check if IPA is ready for suspend, If we are here means, there is 1908 * high chance that suspend would go through but just to avoid any race 1909 * condition after suspend started, these checks are conducted before 1910 * allowing to suspend. 1911 */ 1912 if (atomic_read(&ipa_ctx->tx_ref_cnt)) 1913 return QDF_STATUS_E_AGAIN; 1914 1915 if (!wlan_ipa_is_rm_released(ipa_ctx)) 1916 return QDF_STATUS_E_AGAIN; 1917 1918 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 1919 ipa_ctx->suspended = true; 1920 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1921 1922 if (ipa_ctx->config->ipa_force_voting && 1923 !ipa_ctx->ipa_pipes_down) 1924 wlan_ipa_set_perf_level(ipa_ctx, 1925 ipa_ctx->config->bus_bw_high, 1926 ipa_ctx->config->bus_bw_high); 1927 1928 return QDF_STATUS_SUCCESS; 1929 } 1930 wlan_ipa_resume(struct wlan_ipa_priv * ipa_ctx)1931 QDF_STATUS wlan_ipa_resume(struct wlan_ipa_priv *ipa_ctx) 1932 { 1933 qdf_sched_work(0, &ipa_ctx->pm_work); 1934 1935 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 1936 ipa_ctx->suspended = false; 1937 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 1938 1939 return QDF_STATUS_SUCCESS; 1940 } 1941 wlan_ipa_uc_enable_pipes(struct wlan_ipa_priv * ipa_ctx)1942 QDF_STATUS wlan_ipa_uc_enable_pipes(struct wlan_ipa_priv *ipa_ctx) 1943 { 1944 int result; 1945 QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; 1946 1947 ipa_debug("enter"); 1948 1949 qdf_spin_lock_bh(&ipa_ctx->enable_disable_lock); 1950 if (ipa_ctx->pipes_enable_in_progress) { 1951 ipa_warn("IPA Pipes Enable in progress"); 1952 qdf_spin_unlock_bh(&ipa_ctx->enable_disable_lock); 1953 return QDF_STATUS_E_ALREADY; 1954 } 1955 ipa_ctx->pipes_enable_in_progress = true; 1956 qdf_spin_unlock_bh(&ipa_ctx->enable_disable_lock); 1957 1958 if (qdf_atomic_read(&ipa_ctx->waiting_on_pending_tx)) 1959 wlan_ipa_reset_pending_tx_timer(ipa_ctx); 1960 1961 if (qdf_atomic_read(&ipa_ctx->pipes_disabled)) { 1962 result = cdp_ipa_enable_pipes(ipa_ctx->dp_soc, 1963 ipa_ctx->dp_pdev_id, 1964 ipa_ctx->hdl); 1965 if (result) { 1966 ipa_err("Enable IPA WDI PIPE failed: ret=%d", result); 1967 qdf_status = QDF_STATUS_E_FAILURE; 1968 goto end; 1969 } 1970 qdf_atomic_set(&ipa_ctx->pipes_disabled, 0); 1971 } 1972 1973 qdf_event_reset(&ipa_ctx->ipa_resource_comp); 1974 1975 if (qdf_atomic_read(&ipa_ctx->autonomy_disabled)) { 1976 if (wlan_ipa_opt_wifi_dp_enabled()) { 1977 /* Default packet routing is to HOST REO rings */ 1978 ipa_info("opt_dp: enable pipes. Do not enable autonomy"); 1979 } else { 1980 cdp_ipa_enable_autonomy(ipa_ctx->dp_soc, 1981 ipa_ctx->dp_pdev_id); 1982 qdf_atomic_set(&ipa_ctx->autonomy_disabled, 0); 1983 } 1984 } 1985 end: 1986 qdf_spin_lock_bh(&ipa_ctx->enable_disable_lock); 1987 if (((!qdf_atomic_read(&ipa_ctx->autonomy_disabled)) || 1988 wlan_ipa_opt_wifi_dp_enabled()) && 1989 !qdf_atomic_read(&ipa_ctx->pipes_disabled)) 1990 ipa_ctx->ipa_pipes_down = false; 1991 1992 ipa_ctx->pipes_enable_in_progress = false; 1993 qdf_spin_unlock_bh(&ipa_ctx->enable_disable_lock); 1994 1995 ipa_debug("exit: ipa_pipes_down=%d", ipa_ctx->ipa_pipes_down); 1996 return qdf_status; 1997 } 1998 1999 QDF_STATUS wlan_ipa_uc_disable_pipes(struct wlan_ipa_priv * ipa_ctx,bool force_disable)2000 wlan_ipa_uc_disable_pipes(struct wlan_ipa_priv *ipa_ctx, bool force_disable) 2001 { 2002 QDF_STATUS qdf_status = QDF_STATUS_SUCCESS; 2003 2004 ipa_debug("enter: force_disable %u autonomy_disabled %u pipes_disabled %u", 2005 force_disable, 2006 qdf_atomic_read(&ipa_ctx->autonomy_disabled), 2007 qdf_atomic_read(&ipa_ctx->pipes_disabled)); 2008 2009 qdf_spin_lock_bh(&ipa_ctx->enable_disable_lock); 2010 if (ipa_ctx->ipa_pipes_down || ipa_ctx->pipes_down_in_progress) { 2011 qdf_spin_unlock_bh(&ipa_ctx->enable_disable_lock); 2012 ipa_info("IPA WDI Pipes are already deactivated"); 2013 ipa_info("pipes_down %d, pipes_down_in_progress %d", 2014 ipa_ctx->ipa_pipes_down, 2015 ipa_ctx->pipes_down_in_progress); 2016 return QDF_STATUS_E_ALREADY; 2017 } 2018 ipa_ctx->pipes_down_in_progress = true; 2019 qdf_spin_unlock_bh(&ipa_ctx->enable_disable_lock); 2020 2021 2022 if (!qdf_atomic_read(&ipa_ctx->autonomy_disabled)) { 2023 cdp_ipa_disable_autonomy(ipa_ctx->dp_soc, 2024 ipa_ctx->dp_pdev_id); 2025 qdf_atomic_set(&ipa_ctx->autonomy_disabled, 1); 2026 } 2027 2028 if (!qdf_atomic_read(&ipa_ctx->pipes_disabled)) { 2029 if (!force_disable) { 2030 wlan_ipa_set_pending_tx_timer(ipa_ctx); 2031 } else { 2032 qdf_status = cdp_ipa_disable_pipes(ipa_ctx->dp_soc, 2033 ipa_ctx->dp_pdev_id, 2034 ipa_ctx->hdl); 2035 if (QDF_IS_STATUS_ERROR(qdf_status)) { 2036 ipa_err("Disable IPA WDI PIPE failed: ret=%u", 2037 qdf_status); 2038 qdf_status = QDF_STATUS_E_FAILURE; 2039 goto end; 2040 } 2041 qdf_atomic_set(&ipa_ctx->pipes_disabled, 1); 2042 wlan_ipa_reset_pending_tx_timer(ipa_ctx); 2043 } 2044 } 2045 2046 end: 2047 qdf_spin_lock_bh(&ipa_ctx->enable_disable_lock); 2048 if (qdf_atomic_read(&ipa_ctx->pipes_disabled) && 2049 qdf_atomic_read(&ipa_ctx->autonomy_disabled)) { 2050 ipa_ctx->ipa_pipes_down = true; 2051 } 2052 ipa_ctx->pipes_down_in_progress = false; 2053 qdf_spin_unlock_bh(&ipa_ctx->enable_disable_lock); 2054 2055 ipa_debug("exit: ipa_pipes_down %u autonomy_disabled %u pipes_disabled %u", 2056 ipa_ctx->ipa_pipes_down, 2057 qdf_atomic_read(&ipa_ctx->autonomy_disabled), 2058 qdf_atomic_read(&ipa_ctx->pipes_disabled)); 2059 return qdf_status; 2060 } 2061 2062 /** 2063 * wlan_ipa_uc_find_add_assoc_sta() - Find associated station 2064 * @ipa_ctx: Global IPA IPA context 2065 * @sta_add: Should station be added 2066 * @mac_addr: mac address of station being queried 2067 * 2068 * Return: true if the station was found 2069 */ wlan_ipa_uc_find_add_assoc_sta(struct wlan_ipa_priv * ipa_ctx,bool sta_add,const uint8_t * mac_addr)2070 static bool wlan_ipa_uc_find_add_assoc_sta(struct wlan_ipa_priv *ipa_ctx, 2071 bool sta_add, 2072 const uint8_t *mac_addr) 2073 { 2074 bool sta_found = false; 2075 uint8_t idx; 2076 2077 for (idx = 0; idx < WLAN_IPA_MAX_STA_COUNT; idx++) { 2078 if ((ipa_ctx->assoc_stas_map[idx].is_reserved) && 2079 (qdf_is_macaddr_equal( 2080 &ipa_ctx->assoc_stas_map[idx].mac_addr, 2081 (struct qdf_mac_addr *)mac_addr))) { 2082 sta_found = true; 2083 break; 2084 } 2085 } 2086 if (sta_add && sta_found) { 2087 ipa_err("STA already exist, cannot add: " QDF_MAC_ADDR_FMT, 2088 QDF_MAC_ADDR_REF(mac_addr)); 2089 return sta_found; 2090 } 2091 if (sta_add) { 2092 for (idx = 0; idx < WLAN_IPA_MAX_STA_COUNT; idx++) { 2093 if (!ipa_ctx->assoc_stas_map[idx].is_reserved) { 2094 ipa_ctx->assoc_stas_map[idx].is_reserved = true; 2095 qdf_mem_copy(&ipa_ctx->assoc_stas_map[idx]. 2096 mac_addr, mac_addr, 2097 QDF_NET_ETH_LEN); 2098 return sta_found; 2099 } 2100 } 2101 } 2102 if (!sta_add && !sta_found) { 2103 ipa_info("STA does not exist, cannot delete: " 2104 QDF_MAC_ADDR_FMT, QDF_MAC_ADDR_REF(mac_addr)); 2105 return sta_found; 2106 } 2107 if (!sta_add) { 2108 for (idx = 0; idx < WLAN_IPA_MAX_STA_COUNT; idx++) { 2109 if ((ipa_ctx->assoc_stas_map[idx].is_reserved) && 2110 (qdf_is_macaddr_equal( 2111 &ipa_ctx->assoc_stas_map[idx].mac_addr, 2112 (struct qdf_mac_addr *)mac_addr))) { 2113 ipa_ctx->assoc_stas_map[idx].is_reserved = 2114 false; 2115 qdf_mem_zero( 2116 &ipa_ctx->assoc_stas_map[idx].mac_addr, 2117 QDF_NET_ETH_LEN); 2118 return sta_found; 2119 } 2120 } 2121 } 2122 2123 return sta_found; 2124 } 2125 2126 /** 2127 * wlan_ipa_get_ifaceid() - Get IPA context interface ID 2128 * @ipa_ctx: IPA context 2129 * @session_id: Session ID 2130 * 2131 * Return: None 2132 */ wlan_ipa_get_ifaceid(struct wlan_ipa_priv * ipa_ctx,uint8_t session_id)2133 static int wlan_ipa_get_ifaceid(struct wlan_ipa_priv *ipa_ctx, 2134 uint8_t session_id) 2135 { 2136 struct wlan_ipa_iface_context *iface_ctx; 2137 int i; 2138 2139 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 2140 iface_ctx = &ipa_ctx->iface_context[i]; 2141 if (iface_ctx->session_id == session_id) 2142 break; 2143 } 2144 2145 return i; 2146 } 2147 2148 #ifdef IPA_WDI3_TX_TWO_PIPES 2149 #define WLAN_IPA_SESSION_ID_SHIFT 1 wlan_ipa_set_session_id(uint8_t session_id,bool is_2g_iface)2150 static uint8_t wlan_ipa_set_session_id(uint8_t session_id, bool is_2g_iface) 2151 { 2152 return (session_id << WLAN_IPA_SESSION_ID_SHIFT) | is_2g_iface; 2153 } 2154 2155 static void wlan_ipa_setup_iface_alt_pipe(struct wlan_ipa_iface_context * iface_context,bool alt_pipe)2156 wlan_ipa_setup_iface_alt_pipe(struct wlan_ipa_iface_context *iface_context, 2157 bool alt_pipe) 2158 { 2159 iface_context->alt_pipe = alt_pipe; 2160 } 2161 2162 static void wlan_ipa_cleanup_iface_alt_pipe(struct wlan_ipa_iface_context * iface_context)2163 wlan_ipa_cleanup_iface_alt_pipe(struct wlan_ipa_iface_context *iface_context) 2164 { 2165 iface_context->alt_pipe = false; 2166 } 2167 2168 #else wlan_ipa_set_session_id(uint8_t session_id,bool is_2g_iface)2169 static uint8_t wlan_ipa_set_session_id(uint8_t session_id, bool is_2g_iface) 2170 { 2171 return session_id; 2172 } 2173 2174 static void wlan_ipa_setup_iface_alt_pipe(struct wlan_ipa_iface_context * iface_context,bool alt_pipe)2175 wlan_ipa_setup_iface_alt_pipe(struct wlan_ipa_iface_context *iface_context, 2176 bool alt_pipe) 2177 { 2178 } 2179 2180 static void wlan_ipa_cleanup_iface_alt_pipe(struct wlan_ipa_iface_context * iface_context)2181 wlan_ipa_cleanup_iface_alt_pipe(struct wlan_ipa_iface_context *iface_context) 2182 { 2183 } 2184 2185 #endif 2186 2187 /** 2188 * wlan_ipa_cleanup_iface() - Cleanup IPA on a given interface 2189 * @iface_context: interface-specific IPA context 2190 * @mac_addr: MAC address 2191 * 2192 * Return: None 2193 */ wlan_ipa_cleanup_iface(struct wlan_ipa_iface_context * iface_context,const uint8_t * mac_addr)2194 static void wlan_ipa_cleanup_iface(struct wlan_ipa_iface_context *iface_context, 2195 const uint8_t *mac_addr) 2196 { 2197 struct wlan_ipa_priv *ipa_ctx = iface_context->ipa_ctx; 2198 2199 ipa_debug("enter"); 2200 ipa_err("net:%pK mode:%d MAC:"QDF_MAC_ADDR_FMT" id:%d", 2201 iface_context->dev, iface_context->device_mode, 2202 QDF_MAC_ADDR_REF(mac_addr), iface_context->session_id); 2203 2204 if (iface_context->session_id == WLAN_IPA_MAX_SESSION) 2205 return; 2206 2207 if (mac_addr && qdf_mem_cmp(iface_context->mac_addr, 2208 mac_addr, QDF_MAC_ADDR_SIZE)) { 2209 ipa_err("MAC mismatch "QDF_MAC_ADDR_FMT":"QDF_MAC_ADDR_FMT"", 2210 QDF_MAC_ADDR_REF(mac_addr), 2211 QDF_MAC_ADDR_REF(iface_context->mac_addr)); 2212 } 2213 2214 if (cdp_ipa_cleanup_iface(ipa_ctx->dp_soc, 2215 iface_context->dev->name, 2216 wlan_ipa_is_ipv6_enabled(ipa_ctx->config), 2217 ipa_ctx->hdl)) { 2218 ipa_err("ipa_cleanup_iface failed"); 2219 } 2220 2221 if (iface_context->device_mode == QDF_SAP_MODE) 2222 ipa_ctx->num_sap_connected--; 2223 2224 qdf_spin_lock_bh(&iface_context->interface_lock); 2225 if (qdf_atomic_read(&iface_context->disconn_count) == 2226 qdf_atomic_read(&iface_context->conn_count) - 1) { 2227 qdf_atomic_inc(&iface_context->disconn_count); 2228 } else { 2229 ipa_err("connect/disconnect out of sync"); 2230 QDF_BUG(0); 2231 } 2232 2233 iface_context->is_authenticated = false; 2234 iface_context->dev = NULL; 2235 iface_context->device_mode = QDF_MAX_NO_OF_MODE; 2236 iface_context->session_id = WLAN_IPA_MAX_SESSION; 2237 qdf_mem_set(iface_context->mac_addr, QDF_MAC_ADDR_SIZE, 0); 2238 wlan_ipa_cleanup_iface_alt_pipe(iface_context); 2239 qdf_spin_unlock_bh(&iface_context->interface_lock); 2240 iface_context->ifa_address = 0; 2241 qdf_zero_macaddr(&iface_context->bssid); 2242 if (!iface_context->ipa_ctx->num_iface) { 2243 ipa_err("NUM INTF 0, Invalid"); 2244 QDF_ASSERT(0); 2245 } 2246 iface_context->ipa_ctx->num_iface--; 2247 ipa_debug("exit: num_iface=%d", iface_context->ipa_ctx->num_iface); 2248 } 2249 2250 #if !defined(QCA_LL_TX_FLOW_CONTROL_V2) && !defined(QCA_IPA_LL_TX_FLOW_CONTROL) 2251 2252 /** 2253 * wlan_ipa_nbuf_cb() - IPA TX complete callback 2254 * @skb: packet buffer which was transmitted 2255 * 2256 * Return: None 2257 */ wlan_ipa_nbuf_cb(qdf_nbuf_t skb)2258 static void wlan_ipa_nbuf_cb(qdf_nbuf_t skb) 2259 { 2260 struct wlan_ipa_priv *ipa_ctx = gp_ipa; 2261 qdf_ipa_rx_data_t *ipa_tx_desc; 2262 struct wlan_ipa_tx_desc *tx_desc; 2263 uint16_t id; 2264 struct wlan_objmgr_pdev *pdev; 2265 struct wlan_objmgr_psoc *psoc; 2266 qdf_device_t osdev; 2267 2268 if (!qdf_nbuf_ipa_owned_get(skb)) { 2269 dev_kfree_skb_any(skb); 2270 return; 2271 } 2272 2273 if (!ipa_ctx) 2274 return; 2275 pdev = ipa_ctx->pdev; 2276 psoc = wlan_pdev_get_psoc(pdev); 2277 osdev = wlan_psoc_get_qdf_dev(psoc); 2278 2279 if (osdev && qdf_mem_smmu_s1_enabled(osdev)) { 2280 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 2281 qdf_dma_addr_t paddr = QDF_NBUF_CB_PADDR(skb); 2282 2283 qdf_nbuf_mapped_paddr_set(skb, 2284 paddr - 2285 WLAN_IPA_WLAN_FRAG_HEADER - 2286 WLAN_IPA_WLAN_IPA_HEADER); 2287 } 2288 2289 qdf_nbuf_unmap(osdev, skb, QDF_DMA_TO_DEVICE); 2290 } 2291 2292 /* Get Tx desc pointer from SKB CB */ 2293 id = qdf_nbuf_ipa_priv_get(skb); 2294 tx_desc = &ipa_ctx->tx_desc_pool[id]; 2295 ipa_tx_desc = tx_desc->ipa_tx_desc_ptr; 2296 2297 /* Return Tx Desc to IPA */ 2298 qdf_ipa_free_skb(ipa_tx_desc); 2299 2300 /* Return to free tx desc list */ 2301 qdf_spin_lock_bh(&ipa_ctx->q_lock); 2302 tx_desc->ipa_tx_desc_ptr = NULL; 2303 qdf_list_insert_back(&ipa_ctx->tx_desc_free_list, &tx_desc->node); 2304 ipa_ctx->stats.num_tx_desc_q_cnt--; 2305 qdf_spin_unlock_bh(&ipa_ctx->q_lock); 2306 2307 ipa_ctx->stats.num_tx_comp_cnt++; 2308 2309 qdf_atomic_dec(&ipa_ctx->tx_ref_cnt); 2310 2311 wlan_ipa_wdi_rm_try_release(ipa_ctx); 2312 } 2313 2314 #else /* QCA_LL_TX_FLOW_CONTROL_V2 */ 2315 2316 /** 2317 * wlan_ipa_nbuf_cb() - IPA TX complete callback 2318 * @skb: packet buffer which was transmitted 2319 * 2320 * Return: None 2321 */ wlan_ipa_nbuf_cb(qdf_nbuf_t skb)2322 static void wlan_ipa_nbuf_cb(qdf_nbuf_t skb) 2323 { 2324 dev_kfree_skb_any(skb); 2325 } 2326 2327 #endif /* QCA_LL_TX_FLOW_CONTROL_V2 */ 2328 2329 /** 2330 * wlan_ipa_setup_iface() - Setup IPA on a given interface 2331 * @ipa_ctx: IPA IPA global context 2332 * @net_dev: Interface net device 2333 * @device_mode: Net interface device mode 2334 * @session_id: Session ID 2335 * @mac_addr: MAC address associated with the event 2336 * @is_2g_iface: true if Net interface is operating on 2G band, otherwise false 2337 * 2338 * Return: QDF STATUS 2339 */ wlan_ipa_setup_iface(struct wlan_ipa_priv * ipa_ctx,qdf_netdev_t net_dev,uint8_t device_mode,uint8_t session_id,const uint8_t * mac_addr,bool is_2g_iface)2340 static QDF_STATUS wlan_ipa_setup_iface(struct wlan_ipa_priv *ipa_ctx, 2341 qdf_netdev_t net_dev, 2342 uint8_t device_mode, 2343 uint8_t session_id, 2344 const uint8_t *mac_addr, 2345 bool is_2g_iface) 2346 { 2347 struct wlan_ipa_iface_context *iface_context = NULL; 2348 int i; 2349 QDF_STATUS status; 2350 2351 ipa_err("net:%pK mode:%d MAC:"QDF_MAC_ADDR_FMT" id:%d", 2352 net_dev, device_mode, QDF_MAC_ADDR_REF(mac_addr), session_id); 2353 2354 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 2355 iface_context = &(ipa_ctx->iface_context[i]); 2356 if (wlan_ipa_check_iface_netdev_sessid(iface_context, net_dev, 2357 session_id)) { 2358 if (iface_context->device_mode == device_mode) { 2359 /** 2360 * Lower layer may send multiple START_BSS_EVENT 2361 * in DFS mode or during channel change. 2362 * Since these indications are sent by lower 2363 * layer as SAP updates and IPA doesn't have to 2364 * do anything for these updates so ignoring! 2365 */ 2366 if (device_mode == QDF_SAP_MODE) { 2367 ipa_debug("found iface %u device_mode %u", 2368 i, device_mode); 2369 return QDF_STATUS_SUCCESS; 2370 } else if (device_mode == QDF_STA_MODE && 2371 qdf_mem_cmp( 2372 iface_context->mac_addr, 2373 mac_addr, 2374 QDF_MAC_ADDR_SIZE) == 0) { 2375 ipa_err("same STA iface already connected"); 2376 } 2377 2378 } 2379 2380 ipa_err("Obsolete iface %u found, device_mode %u, will remove it.", 2381 i, iface_context->device_mode); 2382 wlan_ipa_cleanup_iface(iface_context, NULL); 2383 } else if (iface_context->session_id == session_id) { 2384 ipa_err("Obsolete iface %u found, net_dev %pK, will remove it.", 2385 i, iface_context->dev); 2386 wlan_ipa_cleanup_iface(iface_context, NULL); 2387 } 2388 } 2389 2390 if (WLAN_IPA_MAX_IFACE == ipa_ctx->num_iface) { 2391 ipa_err("Max interface reached %d", WLAN_IPA_MAX_IFACE); 2392 status = QDF_STATUS_E_NOMEM; 2393 iface_context = NULL; 2394 QDF_ASSERT(0); 2395 goto end; 2396 } 2397 2398 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 2399 if (ipa_ctx->iface_context[i].session_id == 2400 WLAN_IPA_MAX_SESSION) { 2401 iface_context = &(ipa_ctx->iface_context[i]); 2402 break; 2403 } 2404 } 2405 2406 if (!iface_context) { 2407 ipa_err("All the IPA interfaces are in use"); 2408 status = QDF_STATUS_E_NOMEM; 2409 QDF_ASSERT(0); 2410 goto end; 2411 } 2412 2413 qdf_spin_lock_bh(&iface_context->interface_lock); 2414 if (qdf_atomic_read(&iface_context->conn_count) == 2415 qdf_atomic_read(&iface_context->disconn_count)) { 2416 qdf_atomic_inc(&iface_context->conn_count); 2417 } else { 2418 ipa_err("connect/disconnect out of sync"); 2419 QDF_BUG(0); 2420 } 2421 2422 iface_context->dev = net_dev; 2423 iface_context->device_mode = device_mode; 2424 iface_context->session_id = session_id; 2425 qdf_mem_copy(iface_context->mac_addr, mac_addr, QDF_MAC_ADDR_SIZE); 2426 wlan_ipa_setup_iface_alt_pipe(iface_context, is_2g_iface); 2427 qdf_spin_unlock_bh(&iface_context->interface_lock); 2428 2429 status = cdp_ipa_setup_iface(ipa_ctx->dp_soc, net_dev->name, 2430 (uint8_t *)net_dev->dev_addr, 2431 iface_context->prod_client, 2432 iface_context->cons_client, 2433 wlan_ipa_set_session_id(session_id, 2434 is_2g_iface), 2435 wlan_ipa_is_ipv6_enabled(ipa_ctx->config), 2436 ipa_ctx->hdl); 2437 if (status != QDF_STATUS_SUCCESS) 2438 goto end; 2439 2440 /* Register IPA Tx desc free callback */ 2441 qdf_nbuf_reg_free_cb(wlan_ipa_nbuf_cb); 2442 2443 ipa_ctx->num_iface++; 2444 2445 if (device_mode == QDF_SAP_MODE) 2446 ipa_ctx->num_sap_connected++; 2447 2448 ipa_debug("exit: num_iface=%d", ipa_ctx->num_iface); 2449 2450 return status; 2451 2452 end: 2453 if (iface_context) 2454 wlan_ipa_cleanup_iface(iface_context, mac_addr); 2455 2456 return status; 2457 } 2458 2459 #if defined(QCA_WIFI_QCA6290) || defined(QCA_WIFI_QCA6390) || \ 2460 defined(QCA_WIFI_QCA6490) || defined(QCA_WIFI_QCA6750) || \ 2461 defined(QCA_WIFI_WCN7850) || defined(QCA_WIFI_QCN9000) || \ 2462 defined(QCA_WIFI_KIWI) || defined(QCA_WIFI_KIWI_V2) || \ 2463 defined(QCA_WIFI_QCN9224) 2464 2465 #if defined(QCA_CONFIG_RPS) && !defined(MDM_PLATFORM) 2466 /** 2467 * ipa_set_rps(): Enable/disable RPS for all interfaces of specific mode 2468 * @ipa_ctx: IPA context 2469 * @mode: mode of interface for which RPS needs to be enabled 2470 * @enable: Set true to enable RPS 2471 * 2472 * Return: None 2473 */ ipa_set_rps(struct wlan_ipa_priv * ipa_ctx,enum QDF_OPMODE mode,bool enable)2474 static void ipa_set_rps(struct wlan_ipa_priv *ipa_ctx, enum QDF_OPMODE mode, 2475 bool enable) 2476 { 2477 struct wlan_ipa_iface_context *iface_ctx; 2478 wlan_ipa_rps_enable cb = ipa_ctx->rps_enable; 2479 int i; 2480 2481 if (!cb) 2482 return; 2483 2484 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 2485 iface_ctx = &ipa_ctx->iface_context[i]; 2486 if (iface_ctx->device_mode == mode) 2487 cb(iface_ctx->session_id, enable); 2488 } 2489 } 2490 2491 /** 2492 * wlan_ipa_uc_handle_first_con() - Handle first uC IPA connection 2493 * @ipa_ctx: IPA context 2494 * 2495 * Return: QDF STATUS 2496 */ wlan_ipa_uc_handle_first_con(struct wlan_ipa_priv * ipa_ctx)2497 static QDF_STATUS wlan_ipa_uc_handle_first_con(struct wlan_ipa_priv *ipa_ctx) 2498 { 2499 ipa_debug("enter"); 2500 2501 if (qdf_ipa_get_lan_rx_napi() && (ipa_ctx->num_sap_connected > 1)) { 2502 ipa_debug("Multiple SAP connected. Not enabling pipes. Exit"); 2503 return QDF_STATUS_E_PERM; 2504 } 2505 2506 if (qdf_ipa_get_lan_rx_napi() && ipa_ctx->sta_connected) 2507 ipa_set_rps(ipa_ctx, QDF_STA_MODE, true); 2508 2509 if (wlan_ipa_uc_enable_pipes(ipa_ctx) != QDF_STATUS_SUCCESS) { 2510 ipa_err("IPA WDI Pipe activation failed"); 2511 return QDF_STATUS_E_BUSY; 2512 } 2513 2514 ipa_debug("exit"); 2515 2516 return QDF_STATUS_SUCCESS; 2517 } 2518 2519 static wlan_ipa_uc_handle_last_discon(struct wlan_ipa_priv * ipa_ctx,bool force_disable)2520 void wlan_ipa_uc_handle_last_discon(struct wlan_ipa_priv *ipa_ctx, 2521 bool force_disable) 2522 { 2523 ipa_debug("enter"); 2524 2525 wlan_ipa_uc_disable_pipes(ipa_ctx, force_disable); 2526 2527 if (qdf_ipa_get_lan_rx_napi() && ipa_ctx->sta_connected) 2528 ipa_set_rps(ipa_ctx, QDF_STA_MODE, false); 2529 2530 ipa_debug("exit: IPA WDI Pipes deactivated"); 2531 } 2532 #else wlan_ipa_uc_handle_first_con(struct wlan_ipa_priv * ipa_ctx)2533 static QDF_STATUS wlan_ipa_uc_handle_first_con(struct wlan_ipa_priv *ipa_ctx) 2534 { 2535 ipa_debug("enter"); 2536 2537 if (wlan_ipa_uc_enable_pipes(ipa_ctx) != QDF_STATUS_SUCCESS) { 2538 ipa_err("IPA WDI Pipe activation failed"); 2539 return QDF_STATUS_E_BUSY; 2540 } 2541 2542 ipa_debug("exit"); 2543 2544 return QDF_STATUS_SUCCESS; 2545 } 2546 2547 static wlan_ipa_uc_handle_last_discon(struct wlan_ipa_priv * ipa_ctx,bool force_disable)2548 void wlan_ipa_uc_handle_last_discon(struct wlan_ipa_priv *ipa_ctx, 2549 bool force_disable) 2550 { 2551 ipa_debug("enter"); 2552 2553 wlan_ipa_uc_disable_pipes(ipa_ctx, force_disable); 2554 2555 ipa_debug("exit: IPA WDI Pipes deactivated"); 2556 } 2557 #endif 2558 wlan_ipa_is_fw_wdi_activated(struct wlan_ipa_priv * ipa_ctx)2559 bool wlan_ipa_is_fw_wdi_activated(struct wlan_ipa_priv *ipa_ctx) 2560 { 2561 return !ipa_ctx->ipa_pipes_down; 2562 } 2563 2564 /* Time(ms) to wait for pending TX comps after last SAP client disconnects */ 2565 #define WLAN_IPA_TX_PENDING_TIMEOUT_MS 15000 2566 wlan_ipa_set_pending_tx_timer(struct wlan_ipa_priv * ipa_ctx)2567 static void wlan_ipa_set_pending_tx_timer(struct wlan_ipa_priv *ipa_ctx) 2568 { 2569 ipa_ctx->pending_tx_start_ticks = qdf_system_ticks(); 2570 qdf_atomic_set(&ipa_ctx->waiting_on_pending_tx, 1); 2571 ipa_info("done. pending_tx_start_ticks %llu wait_on_pending %u", 2572 ipa_ctx->pending_tx_start_ticks, 2573 qdf_atomic_read(&ipa_ctx->waiting_on_pending_tx)); 2574 } 2575 wlan_ipa_is_tx_pending(struct wlan_ipa_priv * ipa_ctx)2576 bool wlan_ipa_is_tx_pending(struct wlan_ipa_priv *ipa_ctx) 2577 { 2578 bool ret = false; 2579 uint64_t diff_ms = 0; 2580 uint64_t current_ticks = 0; 2581 2582 if (!ipa_ctx) { 2583 ipa_err("IPA private context is NULL"); 2584 return false; 2585 } 2586 2587 if (!qdf_atomic_read(&ipa_ctx->waiting_on_pending_tx)) { 2588 ipa_debug("nothing pending"); 2589 return false; 2590 } 2591 2592 current_ticks = qdf_system_ticks(); 2593 2594 diff_ms = qdf_system_ticks_to_msecs(current_ticks - 2595 ipa_ctx->pending_tx_start_ticks); 2596 2597 if (diff_ms < WLAN_IPA_TX_PENDING_TIMEOUT_MS) { 2598 ret = true; 2599 } else { 2600 ipa_debug("disabling pipes"); 2601 wlan_ipa_uc_disable_pipes(ipa_ctx, true); 2602 } 2603 2604 ipa_debug("diff_ms %llu pending_tx_start_ticks %llu current_ticks %llu wait_on_pending %u", 2605 diff_ms, ipa_ctx->pending_tx_start_ticks, current_ticks, 2606 qdf_atomic_read(&ipa_ctx->waiting_on_pending_tx)); 2607 2608 return ret; 2609 } 2610 wlan_ipa_reset_pending_tx_timer(struct wlan_ipa_priv * ipa_ctx)2611 static void wlan_ipa_reset_pending_tx_timer(struct wlan_ipa_priv *ipa_ctx) 2612 { 2613 ipa_ctx->pending_tx_start_ticks = 0; 2614 qdf_atomic_set(&ipa_ctx->waiting_on_pending_tx, 0); 2615 ipa_info("done"); 2616 } 2617 2618 #else 2619 2620 /** 2621 * wlan_ipa_uc_handle_first_con() - Handle first uC IPA connection 2622 * @ipa_ctx: IPA context 2623 * 2624 * Return: QDF STATUS 2625 */ wlan_ipa_uc_handle_first_con(struct wlan_ipa_priv * ipa_ctx)2626 static QDF_STATUS wlan_ipa_uc_handle_first_con(struct wlan_ipa_priv *ipa_ctx) 2627 { 2628 ipa_debug("enter"); 2629 2630 ipa_ctx->activated_fw_pipe = 0; 2631 ipa_ctx->resource_loading = true; 2632 2633 /* If RM feature enabled 2634 * Request PROD Resource first 2635 * PROD resource may return sync or async manners 2636 */ 2637 if (wlan_ipa_is_rm_enabled(ipa_ctx->config)) { 2638 if (!wlan_ipa_wdi_rm_request_resource(ipa_ctx, 2639 IPA_RM_RESOURCE_WLAN_PROD)) { 2640 /* RM PROD request sync return 2641 * enable pipe immediately 2642 */ 2643 if (wlan_ipa_uc_enable_pipes(ipa_ctx)) { 2644 ipa_err("IPA WDI Pipe activation failed"); 2645 ipa_ctx->resource_loading = false; 2646 return QDF_STATUS_E_BUSY; 2647 } 2648 } else { 2649 ipa_err("IPA WDI Pipe activation deferred"); 2650 } 2651 } else { 2652 /* RM Disabled 2653 * Just enabled all the PIPEs 2654 */ 2655 if (wlan_ipa_uc_enable_pipes(ipa_ctx)) { 2656 ipa_err("IPA WDI Pipe activation failed"); 2657 ipa_ctx->resource_loading = false; 2658 return QDF_STATUS_E_BUSY; 2659 } 2660 ipa_ctx->resource_loading = false; 2661 } 2662 2663 ipa_debug("exit"); 2664 2665 return QDF_STATUS_SUCCESS; 2666 } 2667 2668 /** 2669 * wlan_ipa_uc_handle_last_discon() - Handle last uC IPA disconnection 2670 * @ipa_ctx: IPA context 2671 * @force_disable: force IPA pipes disablement 2672 * 2673 * Return: None 2674 */ 2675 static wlan_ipa_uc_handle_last_discon(struct wlan_ipa_priv * ipa_ctx,bool force_disable)2676 void wlan_ipa_uc_handle_last_discon(struct wlan_ipa_priv *ipa_ctx, 2677 bool force_disable) 2678 { 2679 ipa_debug("enter"); 2680 2681 ipa_ctx->resource_unloading = true; 2682 qdf_event_reset(&ipa_ctx->ipa_resource_comp); 2683 ipa_info("Disable FW RX PIPE"); 2684 cdp_ipa_set_active(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id, false, false); 2685 2686 ipa_debug("exit: IPA WDI Pipes deactivated"); 2687 } 2688 wlan_ipa_is_fw_wdi_activated(struct wlan_ipa_priv * ipa_ctx)2689 bool wlan_ipa_is_fw_wdi_activated(struct wlan_ipa_priv *ipa_ctx) 2690 { 2691 return (WLAN_IPA_UC_NUM_WDI_PIPE == ipa_ctx->activated_fw_pipe); 2692 } 2693 2694 static inline wlan_ipa_set_pending_tx_timer(struct wlan_ipa_priv * ipa_ctx)2695 void wlan_ipa_set_pending_tx_timer(struct wlan_ipa_priv *ipa_ctx) 2696 { 2697 } 2698 wlan_ipa_is_tx_pending(struct wlan_ipa_priv * ipa_ctx)2699 bool wlan_ipa_is_tx_pending(struct wlan_ipa_priv *ipa_ctx) 2700 { 2701 return false; 2702 } 2703 2704 static inline wlan_ipa_reset_pending_tx_timer(struct wlan_ipa_priv * ipa_ctx)2705 void wlan_ipa_reset_pending_tx_timer(struct wlan_ipa_priv *ipa_ctx) 2706 { 2707 } 2708 2709 #endif 2710 2711 static inline wlan_sap_no_client_connected(struct wlan_ipa_priv * ipa_ctx)2712 bool wlan_sap_no_client_connected(struct wlan_ipa_priv *ipa_ctx) 2713 { 2714 return !(ipa_ctx->sap_num_connected_sta); 2715 } 2716 2717 static inline wlan_sta_is_connected(struct wlan_ipa_priv * ipa_ctx)2718 bool wlan_sta_is_connected(struct wlan_ipa_priv *ipa_ctx) 2719 { 2720 return ipa_ctx->sta_connected; 2721 } 2722 2723 static inline wlan_ipa_uc_is_loaded(struct wlan_ipa_priv * ipa_ctx)2724 bool wlan_ipa_uc_is_loaded(struct wlan_ipa_priv *ipa_ctx) 2725 { 2726 return ipa_ctx->uc_loaded; 2727 } 2728 2729 #ifdef INTRA_BSS_FWD_OFFLOAD 2730 /** 2731 * wlan_ipa_intrabss_enable_disable() - wdi intrabss enable/disable notify to fw 2732 * @ipa_ctx: global IPA context 2733 * @session_id: Session Id 2734 * @enable: intrabss enable or disable 2735 * 2736 * Return: none 2737 */ wlan_ipa_intrabss_enable_disable(struct wlan_ipa_priv * ipa_ctx,uint8_t session_id,bool enable)2738 static void wlan_ipa_intrabss_enable_disable(struct wlan_ipa_priv *ipa_ctx, 2739 uint8_t session_id, 2740 bool enable) 2741 { 2742 struct ipa_intrabss_control_params intrabss_req = {0}; 2743 uint32_t intra_bss_fwd = 0; 2744 2745 if (!enable || ipa_ctx->disable_intrabss_fwd[session_id]) { 2746 ipa_debug("%s: ipa_offload->enable=%d, rx_fwd_disabled=%d", 2747 __func__, enable, 2748 ipa_ctx->disable_intrabss_fwd[session_id]); 2749 intra_bss_fwd = 1; 2750 } 2751 2752 intrabss_req.vdev_id = session_id; 2753 intrabss_req.enable = intra_bss_fwd; 2754 2755 if (QDF_STATUS_SUCCESS != 2756 ipa_send_intrabss_enable_disable(ipa_ctx->pdev, &intrabss_req)) { 2757 ipa_err("intrabss offload vdev_id=%d, enable=%d failure", 2758 session_id, intra_bss_fwd); 2759 } 2760 } 2761 #else 2762 static inline wlan_ipa_intrabss_enable_disable(struct wlan_ipa_priv * ipa_ctx,uint8_t session_id,bool enable)2763 void wlan_ipa_intrabss_enable_disable(struct wlan_ipa_priv *ipa_ctx, 2764 uint8_t session_id, 2765 bool enable) 2766 {} 2767 #endif 2768 2769 /** 2770 * wlan_ipa_uc_offload_enable_disable() - wdi enable/disable notify to fw 2771 * @ipa_ctx: global IPA context 2772 * @offload_type: MCC or SCC 2773 * @session_id: Session Id 2774 * @enable: TX offload enable or disable 2775 * 2776 * Return: none 2777 */ wlan_ipa_uc_offload_enable_disable(struct wlan_ipa_priv * ipa_ctx,uint32_t offload_type,uint8_t session_id,bool enable)2778 static void wlan_ipa_uc_offload_enable_disable(struct wlan_ipa_priv *ipa_ctx, 2779 uint32_t offload_type, 2780 uint8_t session_id, 2781 bool enable) 2782 { 2783 2784 struct ipa_uc_offload_control_params req = {0}; 2785 2786 if (session_id >= WLAN_IPA_MAX_SESSION) { 2787 ipa_err("invalid session id: %d", session_id); 2788 return; 2789 } 2790 2791 if (enable == ipa_ctx->vdev_offload_enabled[session_id]) { 2792 ipa_info("IPA offload status is already set"); 2793 ipa_info("offload_type=%d, vdev_id=%d, enable=%d", 2794 offload_type, session_id, enable); 2795 return; 2796 } 2797 2798 ipa_info("offload_type=%d, session_id=%d, enable=%d", 2799 offload_type, session_id, enable); 2800 2801 req.offload_type = offload_type; 2802 req.vdev_id = session_id; 2803 req.enable = enable; 2804 2805 if (QDF_STATUS_SUCCESS != 2806 ipa_send_uc_offload_enable_disable(ipa_ctx->pdev, &req)) { 2807 ipa_err("Fail to enable IPA offload"); 2808 ipa_err("offload type=%d, vdev_id=%d, enable=%d", 2809 offload_type, session_id, enable); 2810 } else { 2811 ipa_ctx->vdev_offload_enabled[session_id] = enable; 2812 } 2813 2814 wlan_ipa_intrabss_enable_disable(ipa_ctx, session_id, enable); 2815 } 2816 2817 #ifdef WDI3_STATS_BW_MONITOR wlan_ipa_uc_bw_monitor(struct wlan_ipa_priv * ipa_ctx,bool stop)2818 static void wlan_ipa_uc_bw_monitor(struct wlan_ipa_priv *ipa_ctx, bool stop) 2819 { 2820 qdf_ipa_wdi_bw_info_t bw_info; 2821 uint32_t bw_low = ipa_ctx->config->ipa_bw_low; 2822 uint32_t bw_medium = ipa_ctx->config->ipa_bw_medium; 2823 uint32_t bw_high = ipa_ctx->config->ipa_bw_high; 2824 int ret; 2825 2826 bw_info.num = WLAN_IPA_UC_BW_MONITOR_LEVEL; 2827 /* IPA uc will mobitor three bw levels for wlan client */ 2828 QDF_IPA_WDI_BW_INFO_THRESHOLD_LEVEL_1(&bw_info) = bw_low; 2829 QDF_IPA_WDI_BW_INFO_THRESHOLD_LEVEL_2(&bw_info) = bw_medium; 2830 QDF_IPA_WDI_BW_INFO_THRESHOLD_LEVEL_3(&bw_info) = bw_high; 2831 QDF_IPA_WDI_BW_INFO_START_STOP(&bw_info) = stop; 2832 2833 ret = qdf_ipa_uc_bw_monitor(&bw_info); 2834 if (ret) 2835 ipa_err("ipa uc bw monitor fails"); 2836 2837 if (!stop) { 2838 cdp_ipa_set_perf_level(ipa_ctx->dp_soc, 2839 QDF_IPA_CLIENT_WLAN2_CONS, 2840 ipa_ctx->config->ipa_bw_low); 2841 ipa_ctx->curr_bw_level = WLAN_IPA_BW_LEVEL_LOW; 2842 } 2843 2844 ipa_debug("ipa uc bw monitor %s", stop ? "stop" : "start"); 2845 } 2846 #else 2847 static inline wlan_ipa_uc_bw_monitor(struct wlan_ipa_priv * ipa_ctx,bool stop)2848 void wlan_ipa_uc_bw_monitor(struct wlan_ipa_priv *ipa_ctx, bool stop) 2849 { 2850 } 2851 #endif 2852 2853 /** 2854 * wlan_ipa_send_msg() - Allocate and send message to IPA 2855 * @net_dev: Interface net device 2856 * @type: event enum of type ipa_wlan_event 2857 * @mac_addr: MAC address associated with the event 2858 * 2859 * Return: QDF STATUS 2860 */ wlan_ipa_send_msg(qdf_netdev_t net_dev,qdf_ipa_wlan_event type,const uint8_t * mac_addr)2861 static QDF_STATUS wlan_ipa_send_msg(qdf_netdev_t net_dev, 2862 qdf_ipa_wlan_event type, 2863 const uint8_t *mac_addr) 2864 { 2865 qdf_ipa_msg_meta_t meta; 2866 qdf_ipa_wlan_msg_t *msg; 2867 2868 QDF_IPA_MSG_META_MSG_LEN(&meta) = sizeof(qdf_ipa_wlan_msg_t); 2869 2870 msg = qdf_mem_malloc(QDF_IPA_MSG_META_MSG_LEN(&meta)); 2871 if (!msg) 2872 return QDF_STATUS_E_NOMEM; 2873 2874 QDF_IPA_SET_META_MSG_TYPE(&meta, type); 2875 strlcpy(QDF_IPA_WLAN_MSG_NAME(msg), net_dev->name, IPA_RESOURCE_NAME_MAX); 2876 qdf_mem_copy(QDF_IPA_WLAN_MSG_MAC_ADDR(msg), mac_addr, QDF_NET_ETH_LEN); 2877 QDF_IPA_WLAN_MSG_NETDEV_IF_ID(msg) = net_dev->ifindex; 2878 2879 ipa_debug("%s: Evt: %d", QDF_IPA_WLAN_MSG_NAME(msg), QDF_IPA_MSG_META_MSG_TYPE(&meta)); 2880 2881 if (qdf_ipa_send_msg(&meta, msg, wlan_ipa_msg_free_fn)) { 2882 ipa_err("%s: Evt: %d fail", 2883 QDF_IPA_WLAN_MSG_NAME(msg), 2884 QDF_IPA_MSG_META_MSG_TYPE(&meta)); 2885 qdf_mem_free(msg); 2886 return QDF_STATUS_E_FAILURE; 2887 } 2888 2889 return QDF_STATUS_SUCCESS; 2890 } 2891 2892 #if defined(QCA_CONFIG_RPS) && !defined(MDM_PLATFORM) 2893 /** 2894 * wlan_ipa_handle_multiple_sap_evt() - Handle multiple SAP connect/disconnect 2895 * @ipa_ctx: IPA global context 2896 * @type: IPA event type 2897 * @session_id: vdev id 2898 * 2899 * This function is used to disable pipes when multiple SAP are connected and 2900 * enable pipes back when only one SAP is connected. 2901 * 2902 * Return: None 2903 */ wlan_ipa_handle_multiple_sap_evt(struct wlan_ipa_priv * ipa_ctx,qdf_ipa_wlan_event type,uint8_t session_id)2904 static void wlan_ipa_handle_multiple_sap_evt(struct wlan_ipa_priv *ipa_ctx, 2905 qdf_ipa_wlan_event type, 2906 uint8_t session_id) 2907 { 2908 struct wlan_ipa_iface_context *iface_ctx; 2909 int i; 2910 2911 if (type == QDF_IPA_AP_DISCONNECT) { 2912 ipa_debug("Multiple SAP disconnecting. Enabling IPA"); 2913 2914 if (ipa_ctx->sap_num_connected_sta > 0) 2915 wlan_ipa_uc_handle_first_con(ipa_ctx); 2916 2917 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 2918 iface_ctx = &ipa_ctx->iface_context[i]; 2919 2920 if (iface_ctx->device_mode == QDF_SAP_MODE) { 2921 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 2922 WMI_AP_RX_DATA_OFFLOAD, 2923 iface_ctx->session_id, 2924 true); 2925 break; 2926 } 2927 } 2928 } else if (type == QDF_IPA_AP_CONNECT) { 2929 ipa_debug("Multiple SAP connected. Disabling IPA"); 2930 2931 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 2932 iface_ctx = &ipa_ctx->iface_context[i]; 2933 2934 if (iface_ctx->device_mode == QDF_SAP_MODE) { 2935 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 2936 WMI_AP_RX_DATA_OFFLOAD, 2937 iface_ctx->session_id, 2938 false); 2939 } 2940 } 2941 2942 if (!ipa_ctx->ipa_pipes_down) 2943 wlan_ipa_uc_handle_last_discon(ipa_ctx, true); 2944 } 2945 } 2946 #else 2947 /** 2948 * wlan_ipa_handle_multiple_sap_evt() - Handle multiple SAP connect/disconnect 2949 * @ipa_ctx: IPA global context 2950 * @type: IPA event type 2951 * @session_id: vdev id 2952 * 2953 * Enable IPA for new SAP when multiple SAP are turned on 2954 * 2955 * Return: None 2956 */ wlan_ipa_handle_multiple_sap_evt(struct wlan_ipa_priv * ipa_ctx,qdf_ipa_wlan_event type,uint8_t session_id)2957 static void wlan_ipa_handle_multiple_sap_evt(struct wlan_ipa_priv *ipa_ctx, 2958 qdf_ipa_wlan_event type, 2959 uint8_t session_id) 2960 { 2961 if (type == QDF_IPA_AP_CONNECT) 2962 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 2963 WMI_AP_RX_DATA_OFFLOAD, 2964 session_id, 2965 true); 2966 } 2967 #endif 2968 2969 static inline void wlan_ipa_save_bssid_iface_ctx(struct wlan_ipa_priv * ipa_ctx,uint8_t iface_id,const uint8_t * mac_addr)2970 wlan_ipa_save_bssid_iface_ctx(struct wlan_ipa_priv *ipa_ctx, uint8_t iface_id, 2971 const uint8_t *mac_addr) 2972 { 2973 qdf_mem_copy(ipa_ctx->iface_context[iface_id].bssid.bytes, 2974 mac_addr, QDF_MAC_ADDR_SIZE); 2975 } 2976 2977 #ifdef IPA_WDS_EASYMESH_FEATURE 2978 /** wlan_ipa_set_peer_id() - Set ta_peer_id in IPA 2979 * @ipa_ctx: ipa context 2980 * @meta: Meta data for IPA 2981 * @net_dev: Interface net device 2982 * @type: WLAN IPA event 2983 * @mac_addr: mac_addr of peer 2984 * 2985 * Return: QDF STATUS 2986 */ 2987 static QDF_STATUS wlan_ipa_set_peer_id(struct wlan_ipa_priv * ipa_ctx,qdf_ipa_msg_meta_t * meta,qdf_netdev_t net_dev,qdf_ipa_wlan_event type,const uint8_t * mac_addr)2988 wlan_ipa_set_peer_id(struct wlan_ipa_priv *ipa_ctx, 2989 qdf_ipa_msg_meta_t *meta, 2990 qdf_netdev_t net_dev, 2991 qdf_ipa_wlan_event type, 2992 const uint8_t *mac_addr) 2993 { 2994 uint8_t ta_peer_id; 2995 struct cdp_ast_entry_info peer_ast_info = {0}; 2996 struct cdp_soc_t *cdp_soc; 2997 qdf_ipa_wlan_msg_ex_t *msg_ex; 2998 bool status; 2999 3000 QDF_IPA_MSG_META_MSG_LEN(meta) = 3001 (sizeof(qdf_ipa_wlan_msg_ex_t) + 3002 sizeof(qdf_ipa_wlan_hdr_attrib_val_t) * 3003 IPA_TA_PEER_ID_ATTRI); 3004 3005 msg_ex = qdf_mem_malloc(QDF_IPA_MSG_META_MSG_LEN(meta)); 3006 if (!msg_ex) 3007 return QDF_STATUS_E_NOMEM; 3008 3009 strlcpy(msg_ex->name, net_dev->name, IPA_RESOURCE_NAME_MAX); 3010 msg_ex->num_of_attribs = IPA_TA_PEER_ID_ATTRI; 3011 ipa_info("Num of attribute set to: %d", IPA_TA_PEER_ID_ATTRI); 3012 3013 msg_ex->attribs[0].attrib_type = WLAN_HDR_ATTRIB_MAC_ADDR; 3014 if (wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 3015 msg_ex->attribs[0].offset = 3016 WLAN_IPA_UC_WLAN_HDR_DES_MAC_OFFSET; 3017 } else { 3018 msg_ex->attribs[0].offset = 3019 WLAN_IPA_WLAN_HDR_DES_MAC_OFFSET; 3020 } 3021 memcpy(msg_ex->attribs[0].u.mac_addr, mac_addr, IPA_MAC_ADDR_SIZE); 3022 3023 msg_ex->attribs[1].attrib_type = WLAN_HDR_ATTRIB_TA_PEER_ID; 3024 cdp_soc = (struct cdp_soc_t *)ipa_ctx->dp_soc; 3025 status = cdp_peer_get_ast_info_by_soc(cdp_soc, 3026 msg_ex->attribs[0].u.mac_addr, 3027 &peer_ast_info); 3028 3029 if (!status) { 3030 qdf_mem_free(msg_ex); 3031 return QDF_STATUS_E_FAILURE; 3032 } 3033 3034 ta_peer_id = peer_ast_info.peer_id; 3035 ipa_info("ta_peer_id set to: %d", ta_peer_id); 3036 msg_ex->attribs[1].u.ta_peer_id = ta_peer_id; 3037 3038 if (qdf_ipa_send_msg(meta, msg_ex, wlan_ipa_msg_free_fn)) { 3039 ipa_info("%s: Evt: %d send ipa msg fail", 3040 net_dev->name, type); 3041 qdf_mem_free(msg_ex); 3042 return QDF_STATUS_E_FAILURE; 3043 } 3044 ipa_ctx->stats.num_send_msg++; 3045 3046 return QDF_STATUS_SUCCESS; 3047 } 3048 #else 3049 static QDF_STATUS wlan_ipa_set_peer_id(struct wlan_ipa_priv * ipa_ctx,qdf_ipa_msg_meta_t * meta,qdf_netdev_t net_dev,qdf_ipa_wlan_event type,const uint8_t * mac_addr)3050 wlan_ipa_set_peer_id(struct wlan_ipa_priv *ipa_ctx, 3051 qdf_ipa_msg_meta_t *meta, 3052 qdf_netdev_t net_dev, 3053 qdf_ipa_wlan_event type, 3054 const uint8_t *mac_addr) 3055 { 3056 qdf_ipa_wlan_msg_ex_t *msg_ex; 3057 3058 QDF_IPA_MSG_META_MSG_LEN(meta) = 3059 (sizeof(qdf_ipa_wlan_msg_ex_t) + 3060 sizeof(qdf_ipa_wlan_hdr_attrib_val_t)); 3061 3062 msg_ex = qdf_mem_malloc(QDF_IPA_MSG_META_MSG_LEN(meta)); 3063 if (!msg_ex) 3064 return QDF_STATUS_E_NOMEM; 3065 3066 strlcpy(msg_ex->name, net_dev->name, IPA_RESOURCE_NAME_MAX); 3067 msg_ex->num_of_attribs = 1; 3068 msg_ex->attribs[0].attrib_type = WLAN_HDR_ATTRIB_MAC_ADDR; 3069 3070 if (wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 3071 msg_ex->attribs[0].offset = 3072 WLAN_IPA_UC_WLAN_HDR_DES_MAC_OFFSET; 3073 } else { 3074 msg_ex->attribs[0].offset = WLAN_IPA_WLAN_HDR_DES_MAC_OFFSET; 3075 } 3076 memcpy(msg_ex->attribs[0].u.mac_addr, mac_addr, IPA_MAC_ADDR_SIZE); 3077 3078 if (qdf_ipa_send_msg(meta, msg_ex, wlan_ipa_msg_free_fn)) { 3079 ipa_info("%s: Evt: %d send ipa msg fail", 3080 net_dev->name, type); 3081 qdf_mem_free(msg_ex); 3082 return QDF_STATUS_E_FAILURE; 3083 } 3084 ipa_ctx->stats.num_send_msg++; 3085 3086 return QDF_STATUS_SUCCESS; 3087 } 3088 #endif 3089 3090 /** 3091 * __wlan_ipa_wlan_evt() - IPA event handler 3092 * @net_dev: Interface net device 3093 * @device_mode: Net interface device mode 3094 * @session_id: session id for the event 3095 * @type: event enum of type ipa_wlan_event 3096 * @mac_addr: MAC address associated with the event 3097 * @is_2g_iface: @net_dev is 2G or not for QDF_IPA_STA_CONNECT and 3098 * QDF_IPA_AP_CONNECT 3099 * @ipa_obj: IPA object 3100 * 3101 * This function is meant to be called from within wlan_ipa_ctx.c 3102 * 3103 * Return: QDF STATUS 3104 */ __wlan_ipa_wlan_evt(qdf_netdev_t net_dev,uint8_t device_mode,uint8_t session_id,qdf_ipa_wlan_event type,const uint8_t * mac_addr,bool is_2g_iface,struct wlan_ipa_priv * ipa_obj)3105 static QDF_STATUS __wlan_ipa_wlan_evt(qdf_netdev_t net_dev, uint8_t device_mode, 3106 uint8_t session_id, 3107 qdf_ipa_wlan_event type, 3108 const uint8_t *mac_addr, bool is_2g_iface, 3109 struct wlan_ipa_priv *ipa_obj) 3110 { 3111 struct wlan_ipa_priv *ipa_ctx; 3112 struct wlan_ipa_iface_context *iface_ctx = NULL; 3113 qdf_ipa_msg_meta_t meta; 3114 qdf_ipa_wlan_msg_t *msg; 3115 qdf_ipa_wlan_msg_ex_t *msg_ex = NULL; 3116 int i; 3117 QDF_STATUS status; 3118 uint8_t sta_session_id = WLAN_IPA_MAX_SESSION; 3119 struct wlan_objmgr_pdev *pdev; 3120 struct wlan_objmgr_psoc *psoc; 3121 struct wlan_objmgr_vdev *vdev; 3122 bool ipa_wds = false; 3123 3124 ipa_debug("%s: EVT: %d, MAC: "QDF_MAC_ADDR_FMT", session_id: %u is_2g_iface %u", 3125 net_dev->name, type, QDF_MAC_ADDR_REF(mac_addr), session_id, 3126 is_2g_iface); 3127 3128 if (type >= QDF_IPA_WLAN_EVENT_MAX) 3129 return QDF_STATUS_E_INVAL; 3130 3131 ipa_ctx = ipa_obj; 3132 if (wlan_ipa_uc_is_enabled(ipa_ctx->config) && 3133 !wlan_ipa_uc_sta_is_enabled(ipa_ctx->config) && 3134 (device_mode != QDF_SAP_MODE)) { 3135 return QDF_STATUS_SUCCESS; 3136 } 3137 3138 pdev = ipa_ctx->pdev; 3139 psoc = wlan_pdev_get_psoc(pdev); 3140 vdev = wlan_objmgr_get_vdev_by_id_from_psoc(psoc, session_id, 3141 WLAN_IPA_ID); 3142 QDF_BUG(session_id < WLAN_IPA_MAX_SESSION); 3143 3144 if (vdev) 3145 wlan_objmgr_vdev_release_ref(vdev, WLAN_IPA_ID); 3146 else 3147 ipa_err("vdev is NULL, session_id: %u", session_id); 3148 3149 if (ipa_ctx->sta_connected) { 3150 iface_ctx = wlan_ipa_get_iface(ipa_ctx, QDF_STA_MODE); 3151 if (iface_ctx) 3152 sta_session_id = iface_ctx->session_id; 3153 else 3154 ipa_err("sta iface_ctx is NULL"); 3155 } 3156 3157 /* 3158 * During IPA UC resource loading/unloading new events can be issued. 3159 */ 3160 if (wlan_ipa_uc_is_enabled(ipa_ctx->config) && 3161 (ipa_ctx->resource_loading || ipa_ctx->resource_unloading)) { 3162 unsigned int pending_event_count; 3163 struct wlan_ipa_uc_pending_event *pending_event = NULL; 3164 3165 ipa_info("Event:%d IPA resource %s inprogress", type, 3166 ipa_ctx->resource_loading ? 3167 "load" : "unload"); 3168 3169 /* Wait until completion of the loading/unloading */ 3170 status = qdf_wait_for_event_completion( 3171 &ipa_ctx->ipa_resource_comp, 3172 IPA_RESOURCE_COMP_WAIT_TIME); 3173 if (status != QDF_STATUS_SUCCESS) { 3174 /* 3175 * If timed out, store the events separately and 3176 * handle them later. 3177 */ 3178 ipa_info("IPA resource %s timed out", 3179 ipa_ctx->resource_loading ? 3180 "load" : "unload"); 3181 3182 if (type == QDF_IPA_AP_DISCONNECT) { 3183 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 3184 WMI_AP_RX_DATA_OFFLOAD, 3185 session_id, false); 3186 } else if (type == QDF_IPA_CLIENT_CONNECT_EX && 3187 wlan_sap_no_client_connected(ipa_ctx)) { 3188 if (wlan_sta_is_connected(ipa_ctx) && 3189 wlan_ipa_uc_is_loaded(ipa_ctx) && 3190 wlan_ipa_uc_sta_is_enabled(ipa_ctx-> 3191 config) && 3192 !wlan_ipa_is_sta_only_offload_enabled()) { 3193 wlan_ipa_uc_offload_enable_disable( 3194 ipa_ctx, 3195 WMI_STA_RX_DATA_OFFLOAD, 3196 sta_session_id, true); 3197 } 3198 } 3199 3200 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 3201 3202 pending_event_count = 3203 qdf_list_size(&ipa_ctx->pending_event); 3204 if (pending_event_count >= 3205 WLAN_IPA_MAX_PENDING_EVENT_COUNT) { 3206 ipa_info("Reached max pending evt count"); 3207 qdf_list_remove_front( 3208 &ipa_ctx->pending_event, 3209 (qdf_list_node_t **)&pending_event); 3210 } else { 3211 pending_event = 3212 (struct wlan_ipa_uc_pending_event *) 3213 qdf_mem_malloc(sizeof( 3214 struct wlan_ipa_uc_pending_event)); 3215 } 3216 3217 if (!pending_event) { 3218 qdf_mutex_release(&ipa_ctx->ipa_lock); 3219 return QDF_STATUS_E_NOMEM; 3220 } 3221 3222 pending_event->net_dev = net_dev; 3223 pending_event->device_mode = device_mode; 3224 pending_event->session_id = session_id; 3225 pending_event->type = type; 3226 pending_event->is_loading = ipa_ctx->resource_loading; 3227 qdf_mem_copy(pending_event->mac_addr, 3228 mac_addr, QDF_MAC_ADDR_SIZE); 3229 pending_event->is_2g_iface = is_2g_iface; 3230 qdf_list_insert_back(&ipa_ctx->pending_event, 3231 &pending_event->node); 3232 3233 qdf_mutex_release(&ipa_ctx->ipa_lock); 3234 3235 /* Cleanup interface */ 3236 if (type == QDF_IPA_STA_DISCONNECT || 3237 type == QDF_IPA_AP_DISCONNECT) { 3238 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 3239 iface_ctx = &ipa_ctx->iface_context[i]; 3240 if (wlan_ipa_check_iface_netdev_sessid( 3241 iface_ctx, net_dev, 3242 session_id)) { 3243 wlan_ipa_cleanup_iface( 3244 iface_ctx, 3245 mac_addr); 3246 break; 3247 } 3248 } 3249 3250 if (qdf_ipa_get_lan_rx_napi() && 3251 ipa_ctx->num_sap_connected == 1) { 3252 wlan_ipa_handle_multiple_sap_evt(ipa_ctx, 3253 type, session_id); 3254 } 3255 } 3256 3257 return QDF_STATUS_SUCCESS; 3258 } 3259 ipa_info("IPA resource %s completed", 3260 ipa_ctx->resource_loading ? 3261 "load" : "unload"); 3262 } 3263 3264 ipa_ctx->stats.event[type]++; 3265 3266 QDF_IPA_SET_META_MSG_TYPE(&meta, type); 3267 switch (type) { 3268 case QDF_IPA_STA_CONNECT: 3269 qdf_mutex_acquire(&ipa_ctx->event_lock); 3270 3271 /* STA already connected and without disconnect, connect again 3272 * This is Roaming scenario, clean up ipa iface first, then add 3273 * ipa iface later, sta_connected-- first, sta_connected++ 3274 * later to reflect real sta number on DUT. 3275 */ 3276 if (ipa_ctx->sta_connected) { 3277 iface_ctx = wlan_ipa_get_iface_by_mode_netdev( 3278 ipa_ctx, net_dev, QDF_STA_MODE, 3279 session_id); 3280 if (iface_ctx) { 3281 ipa_ctx->sta_connected--; 3282 wlan_ipa_cleanup_iface(iface_ctx, NULL); 3283 } 3284 status = wlan_ipa_send_msg(net_dev, 3285 QDF_IPA_STA_DISCONNECT, 3286 mac_addr); 3287 if (status != QDF_STATUS_SUCCESS) { 3288 ipa_err("QDF_IPA_STA_DISCONNECT send failed %u", 3289 status); 3290 qdf_mutex_release(&ipa_ctx->event_lock); 3291 goto end; 3292 } 3293 } 3294 3295 status = wlan_ipa_setup_iface(ipa_ctx, net_dev, device_mode, 3296 session_id, mac_addr, 3297 is_2g_iface); 3298 if (status != QDF_STATUS_SUCCESS) { 3299 ipa_err("wlan_ipa_setup_iface failed %u", status); 3300 qdf_mutex_release(&ipa_ctx->event_lock); 3301 goto end; 3302 } 3303 3304 ipa_ctx->vdev_to_iface[session_id] = 3305 wlan_ipa_get_ifaceid(ipa_ctx, session_id); 3306 3307 wlan_ipa_save_bssid_iface_ctx(ipa_ctx, 3308 ipa_ctx->vdev_to_iface[session_id], 3309 mac_addr); 3310 3311 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config) && 3312 (ipa_ctx->sap_num_connected_sta > 0 || 3313 wlan_ipa_is_sta_only_offload_enabled()) && 3314 !ipa_ctx->sta_connected) { 3315 qdf_mutex_release(&ipa_ctx->event_lock); 3316 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 3317 WMI_STA_RX_DATA_OFFLOAD, session_id, 3318 true); 3319 qdf_mutex_acquire(&ipa_ctx->event_lock); 3320 qdf_atomic_set(&ipa_ctx->stats_quota, 1); 3321 } 3322 3323 if (!wlan_ipa_is_sta_only_offload_enabled()) { 3324 ipa_debug("IPA STA only offload not enabled"); 3325 } else if (ipa_ctx->uc_loaded && 3326 !ipa_ctx->sap_num_connected_sta && 3327 !ipa_ctx->sta_connected) { 3328 status = wlan_ipa_uc_handle_first_con(ipa_ctx); 3329 if (status) { 3330 qdf_mutex_release(&ipa_ctx->event_lock); 3331 ipa_info("handle 1st conn failed %d", status); 3332 wlan_ipa_uc_offload_enable_disable( 3333 ipa_ctx, 3334 WMI_STA_RX_DATA_OFFLOAD, 3335 session_id, 3336 false); 3337 ipa_ctx->vdev_to_iface[session_id] = 3338 WLAN_IPA_MAX_SESSION; 3339 goto end; 3340 } 3341 } 3342 3343 ipa_ctx->sta_connected++; 3344 3345 if (qdf_ipa_get_lan_rx_napi() && ipa_ctx->sap_num_connected_sta) 3346 ipa_set_rps_per_vdev(ipa_ctx, session_id, true); 3347 3348 qdf_mutex_release(&ipa_ctx->event_lock); 3349 3350 ipa_debug("sta_connected=%d vdev_to_iface[%u] %u", 3351 ipa_ctx->sta_connected, 3352 session_id, 3353 ipa_ctx->vdev_to_iface[session_id]); 3354 break; 3355 3356 case QDF_IPA_AP_CONNECT: 3357 qdf_mutex_acquire(&ipa_ctx->event_lock); 3358 3359 /* For DFS channel we get two start_bss event (before and after 3360 * CAC). Also when ACS range includes both DFS and non DFS 3361 * channels, we could possibly change channel many times due to 3362 * RADAR detection and chosen channel may not be a DFS channels. 3363 * So dont return error here. Just discard the event. 3364 */ 3365 if (ipa_ctx->vdev_to_iface[session_id] != 3366 WLAN_IPA_MAX_SESSION) { 3367 qdf_mutex_release(&ipa_ctx->event_lock); 3368 return 0; 3369 } 3370 3371 status = wlan_ipa_setup_iface(ipa_ctx, net_dev, device_mode, 3372 session_id, mac_addr, 3373 is_2g_iface); 3374 if (status != QDF_STATUS_SUCCESS) { 3375 qdf_mutex_release(&ipa_ctx->event_lock); 3376 ipa_err("%s: Evt: %d, Interface setup failed", 3377 msg_ex->name, QDF_IPA_MSG_META_MSG_TYPE(&meta)); 3378 goto end; 3379 } 3380 3381 if (wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 3382 qdf_mutex_release(&ipa_ctx->event_lock); 3383 if (qdf_ipa_get_lan_rx_napi() && 3384 (ipa_ctx->num_sap_connected > 1)) { 3385 wlan_ipa_handle_multiple_sap_evt(ipa_ctx, type, 3386 session_id); 3387 } else { 3388 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 3389 WMI_AP_RX_DATA_OFFLOAD, 3390 session_id, true); 3391 } 3392 qdf_mutex_acquire(&ipa_ctx->event_lock); 3393 } 3394 3395 ipa_ctx->vdev_to_iface[session_id] = 3396 wlan_ipa_get_ifaceid(ipa_ctx, session_id); 3397 ipa_debug("vdev_to_iface[%u]=%u", 3398 session_id, 3399 ipa_ctx->vdev_to_iface[session_id]); 3400 ipa_wds = ipa_ctx->config->ipa_wds; 3401 qdf_mutex_release(&ipa_ctx->event_lock); 3402 break; 3403 3404 case QDF_IPA_STA_DISCONNECT: 3405 qdf_mutex_acquire(&ipa_ctx->event_lock); 3406 3407 if (!ipa_ctx->sta_connected) { 3408 struct wlan_ipa_iface_context *iface; 3409 3410 qdf_mutex_release(&ipa_ctx->event_lock); 3411 ipa_info("%s: Evt: %d, STA already disconnected", 3412 msg_ex->name, 3413 QDF_IPA_MSG_META_MSG_TYPE(&meta)); 3414 3415 iface = wlan_ipa_get_iface_by_mode_netdev(ipa_ctx, 3416 net_dev, 3417 QDF_STA_MODE, 3418 session_id); 3419 if (iface) 3420 wlan_ipa_cleanup_iface(iface, mac_addr); 3421 3422 return QDF_STATUS_E_INVAL; 3423 } 3424 3425 ipa_ctx->sta_connected--; 3426 3427 if (!wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 3428 ipa_debug("%s: IPA UC OFFLOAD NOT ENABLED", 3429 msg_ex->name); 3430 } else { 3431 /* 3432 * Disable IPA pipes when 3433 * 1. STA is the last interface or 3434 * 2. STA only offload enabled and no clients connected 3435 * to SAP 3436 */ 3437 if ((ipa_ctx->num_iface == 1 || 3438 (wlan_ipa_is_sta_only_offload_enabled() && 3439 !ipa_ctx->sap_num_connected_sta)) && 3440 wlan_ipa_is_fw_wdi_activated(ipa_ctx) && 3441 !ipa_ctx->ipa_pipes_down && 3442 (ipa_ctx->resource_unloading == false)) { 3443 if (wlan_ipa_is_driver_unloading(ipa_ctx)) { 3444 /* 3445 * We disable WDI pipes directly here 3446 * since IPA_OPCODE_TX/RX_SUSPEND 3447 * message will not be processed when 3448 * unloading WLAN driver is in progress 3449 */ 3450 wlan_ipa_uc_disable_pipes(ipa_ctx, 3451 true); 3452 } else { 3453 wlan_ipa_uc_handle_last_discon(ipa_ctx, 3454 true); 3455 } 3456 } 3457 } 3458 3459 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config) && 3460 (ipa_ctx->sap_num_connected_sta > 0 || 3461 wlan_ipa_is_sta_only_offload_enabled())) { 3462 qdf_atomic_set(&ipa_ctx->stats_quota, 0); 3463 qdf_mutex_release(&ipa_ctx->event_lock); 3464 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 3465 WMI_STA_RX_DATA_OFFLOAD, session_id, false); 3466 qdf_mutex_acquire(&ipa_ctx->event_lock); 3467 } 3468 3469 ipa_ctx->vdev_to_iface[session_id] = WLAN_IPA_MAX_SESSION; 3470 ipa_debug("vdev_to_iface[%u]=%u", session_id, 3471 ipa_ctx->vdev_to_iface[session_id]); 3472 3473 iface_ctx = wlan_ipa_get_iface_by_mode_netdev(ipa_ctx, 3474 net_dev, 3475 QDF_STA_MODE, 3476 session_id); 3477 if (iface_ctx) 3478 wlan_ipa_cleanup_iface(iface_ctx, mac_addr); 3479 3480 if (qdf_ipa_get_lan_rx_napi() && ipa_ctx->sap_num_connected_sta) 3481 ipa_set_rps_per_vdev(ipa_ctx, session_id, false); 3482 3483 qdf_mutex_release(&ipa_ctx->event_lock); 3484 3485 ipa_debug("sta_connected=%d", ipa_ctx->sta_connected); 3486 break; 3487 3488 case QDF_IPA_AP_DISCONNECT: 3489 qdf_mutex_acquire(&ipa_ctx->event_lock); 3490 3491 if ((ipa_ctx->num_iface == 1) && 3492 wlan_ipa_is_fw_wdi_activated(ipa_ctx) && 3493 !ipa_ctx->ipa_pipes_down && 3494 (ipa_ctx->resource_unloading == false)) { 3495 if (wlan_ipa_is_driver_unloading(ipa_ctx)) { 3496 /* 3497 * We disable WDI pipes directly here since 3498 * IPA_OPCODE_TX/RX_SUSPEND message will not be 3499 * processed when unloading WLAN driver is in 3500 * progress 3501 */ 3502 wlan_ipa_uc_disable_pipes(ipa_ctx, true); 3503 } else { 3504 /* 3505 * This shouldn't happen : 3506 * No interface left but WDI pipes are still 3507 * active - force close WDI pipes 3508 */ 3509 ipa_err("No interface left but WDI pipes are still active"); 3510 wlan_ipa_uc_handle_last_discon(ipa_ctx, true); 3511 } 3512 } 3513 3514 if (wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 3515 qdf_mutex_release(&ipa_ctx->event_lock); 3516 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 3517 WMI_AP_RX_DATA_OFFLOAD, session_id, false); 3518 qdf_mutex_acquire(&ipa_ctx->event_lock); 3519 ipa_ctx->vdev_to_iface[session_id] = 3520 WLAN_IPA_MAX_SESSION; 3521 ipa_debug("vdev_to_iface[%u]=%u", 3522 session_id, 3523 ipa_ctx->vdev_to_iface[session_id]); 3524 } 3525 3526 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 3527 iface_ctx = &ipa_ctx->iface_context[i]; 3528 if (wlan_ipa_check_iface_netdev_sessid(iface_ctx, 3529 net_dev, session_id)) { 3530 wlan_ipa_cleanup_iface(iface_ctx, mac_addr); 3531 break; 3532 } 3533 } 3534 3535 if (qdf_ipa_get_lan_rx_napi() && 3536 (ipa_ctx->num_sap_connected == 1)) 3537 wlan_ipa_handle_multiple_sap_evt(ipa_ctx, type, 3538 session_id); 3539 3540 qdf_mutex_release(&ipa_ctx->event_lock); 3541 break; 3542 3543 case QDF_IPA_CLIENT_CONNECT_EX: 3544 if (!wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 3545 ipa_debug("%s: Evt: %d, IPA UC OFFLOAD NOT ENABLED", 3546 net_dev->name, type); 3547 return QDF_STATUS_SUCCESS; 3548 } 3549 3550 qdf_mutex_acquire(&ipa_ctx->event_lock); 3551 if (wlan_ipa_uc_find_add_assoc_sta(ipa_ctx, true, 3552 mac_addr)) { 3553 qdf_mutex_release(&ipa_ctx->event_lock); 3554 ipa_err("%s: STA found, addr: " QDF_MAC_ADDR_FMT, 3555 net_dev->name, 3556 QDF_MAC_ADDR_REF(mac_addr)); 3557 return QDF_STATUS_SUCCESS; 3558 } 3559 3560 /* Enable IPA UC Data PIPEs when first STA connected */ 3561 if (ipa_ctx->sap_num_connected_sta == 0 && 3562 ipa_ctx->uc_loaded == true) { 3563 3564 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config) && 3565 ipa_ctx->sta_connected && 3566 !wlan_ipa_is_sta_only_offload_enabled()) { 3567 qdf_mutex_release(&ipa_ctx->event_lock); 3568 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 3569 WMI_STA_RX_DATA_OFFLOAD, 3570 sta_session_id, true); 3571 qdf_mutex_acquire(&ipa_ctx->event_lock); 3572 qdf_atomic_set(&ipa_ctx->stats_quota, 1); 3573 } 3574 3575 /* 3576 * IPA pipes already enabled if STA only offload 3577 * is enabled and STA is connected to remote AP. 3578 */ 3579 if (wlan_ipa_is_sta_only_offload_enabled() && 3580 ipa_ctx->sta_connected) { 3581 ipa_debug("IPA pipes already enabled"); 3582 } else if (wlan_ipa_uc_handle_first_con(ipa_ctx)) { 3583 ipa_info("%s: handle 1st con fail", 3584 net_dev->name); 3585 3586 if (wlan_ipa_uc_sta_is_enabled( 3587 ipa_ctx->config) && 3588 ipa_ctx->sta_connected && 3589 !wlan_ipa_is_sta_only_offload_enabled()) { 3590 qdf_atomic_set(&ipa_ctx->stats_quota, 3591 0); 3592 qdf_mutex_release(&ipa_ctx->event_lock); 3593 wlan_ipa_uc_offload_enable_disable( 3594 ipa_ctx, 3595 WMI_STA_RX_DATA_OFFLOAD, 3596 sta_session_id, false); 3597 } else { 3598 qdf_mutex_release(&ipa_ctx->event_lock); 3599 } 3600 3601 return QDF_STATUS_E_BUSY; 3602 } 3603 wlan_ipa_uc_bw_monitor(ipa_ctx, false); 3604 ipa_info("first sap client connected"); 3605 } 3606 3607 ipa_ctx->sap_num_connected_sta++; 3608 3609 qdf_mutex_release(&ipa_ctx->event_lock); 3610 3611 QDF_IPA_SET_META_MSG_TYPE(&meta, type); 3612 3613 status = wlan_ipa_set_peer_id(ipa_ctx, &meta, net_dev, 3614 type, mac_addr); 3615 if (QDF_IS_STATUS_ERROR(status)) 3616 return QDF_STATUS_E_FAILURE; 3617 3618 ipa_debug("sap_num_connected_sta=%d", 3619 ipa_ctx->sap_num_connected_sta); 3620 3621 return QDF_STATUS_SUCCESS; 3622 3623 case WLAN_CLIENT_DISCONNECT: 3624 if (!wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 3625 ipa_debug("%s: IPA UC OFFLOAD NOT ENABLED", 3626 msg_ex->name); 3627 return QDF_STATUS_SUCCESS; 3628 } 3629 3630 qdf_mutex_acquire(&ipa_ctx->event_lock); 3631 wlan_ipa_set_sap_client_auth(ipa_ctx, mac_addr, false); 3632 if (!ipa_ctx->sap_num_connected_sta) { 3633 qdf_mutex_release(&ipa_ctx->event_lock); 3634 ipa_debug("%s: Evt: %d, Client already disconnected", 3635 msg_ex->name, 3636 QDF_IPA_MSG_META_MSG_TYPE(&meta)); 3637 3638 return QDF_STATUS_SUCCESS; 3639 } 3640 if (!wlan_ipa_uc_find_add_assoc_sta(ipa_ctx, false, 3641 mac_addr)) { 3642 qdf_mutex_release(&ipa_ctx->event_lock); 3643 ipa_debug("%s: STA NOT found, not valid: " 3644 QDF_MAC_ADDR_FMT, 3645 msg_ex->name, QDF_MAC_ADDR_REF(mac_addr)); 3646 3647 return QDF_STATUS_SUCCESS; 3648 } 3649 ipa_ctx->sap_num_connected_sta--; 3650 3651 /* 3652 * Disable IPA pipes when 3653 * 1. last client disconnected and 3654 * 2. STA is not connected if STA only offload is enabled 3655 */ 3656 if (!ipa_ctx->sap_num_connected_sta && 3657 ipa_ctx->uc_loaded && 3658 !(wlan_ipa_is_sta_only_offload_enabled() && 3659 ipa_ctx->sta_connected)) { 3660 if ((false == ipa_ctx->resource_unloading) && 3661 wlan_ipa_is_fw_wdi_activated(ipa_ctx) && 3662 !ipa_ctx->ipa_pipes_down) { 3663 if (wlan_ipa_is_driver_unloading(ipa_ctx)) { 3664 /* 3665 * We disable WDI pipes directly here 3666 * since IPA_OPCODE_TX/RX_SUSPEND 3667 * message will not be processed when 3668 * unloading WLAN driver is in progress 3669 */ 3670 3671 wlan_ipa_uc_bw_monitor(ipa_ctx, true); 3672 wlan_ipa_uc_disable_pipes(ipa_ctx, 3673 true); 3674 } else { 3675 /* 3676 * If STA is connected, wait for IPA TX 3677 * completions before disabling 3678 * IPA pipes 3679 */ 3680 wlan_ipa_uc_handle_last_discon(ipa_ctx, 3681 !ipa_ctx->sta_connected); 3682 wlan_ipa_uc_bw_monitor(ipa_ctx, true); 3683 } 3684 ipa_info("last sap client disconnected"); 3685 } 3686 3687 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config) && 3688 ipa_ctx->sta_connected && 3689 !wlan_ipa_is_sta_only_offload_enabled()) { 3690 qdf_atomic_set(&ipa_ctx->stats_quota, 0); 3691 qdf_mutex_release(&ipa_ctx->event_lock); 3692 wlan_ipa_uc_offload_enable_disable(ipa_ctx, 3693 WMI_STA_RX_DATA_OFFLOAD, 3694 sta_session_id, false); 3695 } else { 3696 qdf_mutex_release(&ipa_ctx->event_lock); 3697 } 3698 } else { 3699 qdf_mutex_release(&ipa_ctx->event_lock); 3700 } 3701 3702 ipa_debug("sap_num_connected_sta=%d", 3703 ipa_ctx->sap_num_connected_sta); 3704 break; 3705 3706 default: 3707 return QDF_STATUS_SUCCESS; 3708 } 3709 3710 QDF_IPA_MSG_META_MSG_LEN(&meta) = sizeof(qdf_ipa_wlan_msg_t); 3711 msg = qdf_mem_malloc(QDF_IPA_MSG_META_MSG_LEN(&meta)); 3712 if (!msg) 3713 return QDF_STATUS_E_NOMEM; 3714 3715 QDF_IPA_SET_META_MSG_TYPE(&meta, type); 3716 strlcpy(QDF_IPA_WLAN_MSG_NAME(msg), net_dev->name, 3717 IPA_RESOURCE_NAME_MAX); 3718 qdf_mem_copy(QDF_IPA_WLAN_MSG_MAC_ADDR(msg), mac_addr, QDF_NET_ETH_LEN); 3719 QDF_IPA_WLAN_MSG_NETDEV_IF_ID(msg) = net_dev->ifindex; 3720 3721 wlan_ipa_msg_wds_update(ipa_wds, msg); 3722 3723 ipa_debug("%s: Evt: %d", QDF_IPA_WLAN_MSG_NAME(msg), 3724 QDF_IPA_MSG_META_MSG_TYPE(&meta)); 3725 3726 if (qdf_ipa_send_msg(&meta, msg, wlan_ipa_msg_free_fn)) { 3727 3728 ipa_err("%s: Evt: %d fail", 3729 QDF_IPA_WLAN_MSG_NAME(msg), 3730 QDF_IPA_MSG_META_MSG_TYPE(&meta)); 3731 qdf_mem_free(msg); 3732 3733 return QDF_STATUS_E_FAILURE; 3734 } 3735 3736 ipa_ctx->stats.num_send_msg++; 3737 3738 end: 3739 return QDF_STATUS_SUCCESS; 3740 } 3741 3742 /** 3743 * wlan_host_to_ipa_wlan_event() - convert wlan_ipa_wlan_event to ipa_wlan_event 3744 * @wlan_ipa_event_type: event to be converted to an ipa_wlan_event 3745 * 3746 * Return: qdf_ipa_wlan_event representing the wlan_ipa_wlan_event 3747 */ 3748 static qdf_ipa_wlan_event wlan_host_to_ipa_wlan_event(enum wlan_ipa_wlan_event wlan_ipa_event_type)3749 wlan_host_to_ipa_wlan_event(enum wlan_ipa_wlan_event wlan_ipa_event_type) 3750 { 3751 qdf_ipa_wlan_event ipa_event; 3752 3753 switch (wlan_ipa_event_type) { 3754 case WLAN_IPA_CLIENT_CONNECT: 3755 ipa_event = QDF_IPA_CLIENT_CONNECT; 3756 break; 3757 case WLAN_IPA_CLIENT_DISCONNECT: 3758 ipa_event = QDF_IPA_CLIENT_DISCONNECT; 3759 break; 3760 case WLAN_IPA_AP_CONNECT: 3761 ipa_event = QDF_IPA_AP_CONNECT; 3762 break; 3763 case WLAN_IPA_AP_DISCONNECT: 3764 ipa_event = QDF_IPA_AP_DISCONNECT; 3765 break; 3766 case WLAN_IPA_STA_CONNECT: 3767 ipa_event = QDF_IPA_STA_CONNECT; 3768 break; 3769 case WLAN_IPA_STA_DISCONNECT: 3770 ipa_event = QDF_IPA_STA_DISCONNECT; 3771 break; 3772 case WLAN_IPA_CLIENT_CONNECT_EX: 3773 ipa_event = QDF_IPA_CLIENT_CONNECT_EX; 3774 break; 3775 case WLAN_IPA_WLAN_EVENT_MAX: 3776 default: 3777 ipa_event = QDF_IPA_WLAN_EVENT_MAX; 3778 break; 3779 } 3780 3781 return ipa_event; 3782 } 3783 3784 #ifdef IPA_P2P_SUPPORT 3785 /** 3786 * wlan_ipa_device_mode_switch() - Switch P2p GO/CLI to SAP/STA mode 3787 * @device_mode: device mode 3788 * 3789 * Return: New device mode after switching 3790 */ wlan_ipa_device_mode_switch(uint8_t device_mode)3791 static uint8_t wlan_ipa_device_mode_switch(uint8_t device_mode) 3792 { 3793 switch (device_mode) { 3794 case QDF_P2P_CLIENT_MODE: 3795 return QDF_STA_MODE; 3796 case QDF_P2P_GO_MODE: 3797 return QDF_SAP_MODE; 3798 default: 3799 break; 3800 } 3801 3802 return device_mode; 3803 } 3804 #else wlan_ipa_device_mode_switch(uint8_t device_mode)3805 static uint8_t wlan_ipa_device_mode_switch(uint8_t device_mode) 3806 { 3807 return device_mode; 3808 } 3809 #endif 3810 3811 /** 3812 * wlan_ipa_wlan_evt() - SSR wrapper for __wlan_ipa_wlan_evt 3813 * @net_dev: Interface net device 3814 * @device_mode: Net interface device mode 3815 * @session_id: session id for the event 3816 * @ipa_event_type: event enum of type wlan_ipa_wlan_event 3817 * @mac_addr: MAC address associated with the event 3818 * @is_2g_iface: @net_dev is 2g interface or not 3819 * @ipa_obj: IPA object 3820 * 3821 * Return: QDF_STATUS 3822 */ wlan_ipa_wlan_evt(qdf_netdev_t net_dev,uint8_t device_mode,uint8_t session_id,enum wlan_ipa_wlan_event ipa_event_type,const uint8_t * mac_addr,bool is_2g_iface,struct wlan_ipa_priv * ipa_obj)3823 QDF_STATUS wlan_ipa_wlan_evt(qdf_netdev_t net_dev, uint8_t device_mode, 3824 uint8_t session_id, 3825 enum wlan_ipa_wlan_event ipa_event_type, 3826 const uint8_t *mac_addr, bool is_2g_iface, 3827 struct wlan_ipa_priv *ipa_obj) 3828 { 3829 qdf_ipa_wlan_event type = wlan_host_to_ipa_wlan_event(ipa_event_type); 3830 QDF_STATUS status = QDF_STATUS_SUCCESS; 3831 3832 device_mode = wlan_ipa_device_mode_switch(device_mode); 3833 3834 /* Data path offload only support for STA and SAP mode */ 3835 if ((device_mode == QDF_STA_MODE) || 3836 (device_mode == QDF_SAP_MODE)) 3837 status = __wlan_ipa_wlan_evt(net_dev, device_mode, 3838 session_id, type, mac_addr, 3839 is_2g_iface, ipa_obj); 3840 3841 return status; 3842 } 3843 3844 /** 3845 * wlan_ipa_uc_proc_pending_event() - Process IPA uC pending events 3846 * @ipa_ctx: Global IPA IPA context 3847 * @is_loading: Indicate if invoked during loading 3848 * 3849 * Return: None 3850 */ 3851 static void wlan_ipa_uc_proc_pending_event(struct wlan_ipa_priv * ipa_ctx,bool is_loading)3852 wlan_ipa_uc_proc_pending_event(struct wlan_ipa_priv *ipa_ctx, bool is_loading) 3853 { 3854 unsigned int pending_event_count; 3855 struct wlan_ipa_uc_pending_event *pending_event = NULL; 3856 3857 pending_event_count = qdf_list_size(&ipa_ctx->pending_event); 3858 ipa_debug("Pending Event Count %d", pending_event_count); 3859 if (!pending_event_count) { 3860 ipa_debug("No Pending Event"); 3861 return; 3862 } 3863 3864 qdf_list_remove_front(&ipa_ctx->pending_event, 3865 (qdf_list_node_t **)&pending_event); 3866 while (pending_event) { 3867 struct wlan_objmgr_pdev *pdev = ipa_ctx->pdev; 3868 struct wlan_objmgr_psoc *psoc = wlan_pdev_get_psoc(pdev); 3869 struct wlan_objmgr_vdev *vdev = 3870 wlan_objmgr_get_vdev_by_id_from_psoc(psoc, 3871 pending_event->session_id, 3872 WLAN_IPA_ID); 3873 if (pending_event->is_loading == is_loading && vdev) { 3874 __wlan_ipa_wlan_evt(pending_event->net_dev, 3875 pending_event->device_mode, 3876 pending_event->session_id, 3877 pending_event->type, 3878 pending_event->mac_addr, 3879 pending_event->is_2g_iface, ipa_ctx); 3880 } 3881 3882 if (vdev) 3883 wlan_objmgr_vdev_release_ref(vdev, WLAN_IPA_ID); 3884 qdf_mem_free(pending_event); 3885 pending_event = NULL; 3886 qdf_list_remove_front(&ipa_ctx->pending_event, 3887 (qdf_list_node_t **)&pending_event); 3888 } 3889 } 3890 3891 #if !defined(QCA_LL_TX_FLOW_CONTROL_V2) && !defined(QCA_IPA_LL_TX_FLOW_CONTROL) 3892 3893 /** 3894 * wlan_ipa_free_tx_desc_list() - Free IPA Tx desc list 3895 * @ipa_ctx: IPA context 3896 * 3897 * Return: None 3898 */ wlan_ipa_free_tx_desc_list(struct wlan_ipa_priv * ipa_ctx)3899 static inline void wlan_ipa_free_tx_desc_list(struct wlan_ipa_priv *ipa_ctx) 3900 { 3901 int i; 3902 qdf_ipa_rx_data_t *ipa_tx_desc; 3903 uint32_t pool_size; 3904 3905 if (!ipa_ctx->tx_desc_pool) 3906 return; 3907 3908 qdf_spin_lock_bh(&ipa_ctx->q_lock); 3909 pool_size = ipa_ctx->tx_desc_free_list.max_size; 3910 for (i = 0; i < pool_size; i++) { 3911 ipa_tx_desc = ipa_ctx->tx_desc_pool[i].ipa_tx_desc_ptr; 3912 if (ipa_tx_desc) 3913 qdf_ipa_free_skb(ipa_tx_desc); 3914 3915 if (ipa_ctx->tx_desc_free_list.count && 3916 qdf_list_remove_node(&ipa_ctx->tx_desc_free_list, 3917 &ipa_ctx->tx_desc_pool[i].node) != 3918 QDF_STATUS_SUCCESS) 3919 ipa_err("Failed to remove node from tx desc freelist"); 3920 } 3921 qdf_spin_unlock_bh(&ipa_ctx->q_lock); 3922 3923 qdf_list_destroy(&ipa_ctx->tx_desc_free_list); 3924 qdf_mem_free(ipa_ctx->tx_desc_pool); 3925 ipa_ctx->tx_desc_pool = NULL; 3926 3927 ipa_ctx->stats.num_tx_desc_q_cnt = 0; 3928 ipa_ctx->stats.num_tx_desc_error = 0; 3929 } 3930 3931 /** 3932 * wlan_ipa_alloc_tx_desc_free_list() - Allocate IPA Tx desc list 3933 * @ipa_ctx: IPA context 3934 * 3935 * Return: QDF_STATUS 3936 */ 3937 static QDF_STATUS wlan_ipa_alloc_tx_desc_free_list(struct wlan_ipa_priv * ipa_ctx)3938 wlan_ipa_alloc_tx_desc_free_list(struct wlan_ipa_priv *ipa_ctx) 3939 { 3940 int i; 3941 uint32_t max_desc_cnt; 3942 3943 max_desc_cnt = ipa_ctx->config->txbuf_count; 3944 3945 ipa_ctx->tx_desc_pool = qdf_mem_malloc(sizeof(struct wlan_ipa_tx_desc) * 3946 max_desc_cnt); 3947 if (!ipa_ctx->tx_desc_pool) 3948 return QDF_STATUS_E_NOMEM; 3949 3950 qdf_list_create(&ipa_ctx->tx_desc_free_list, max_desc_cnt); 3951 3952 qdf_spin_lock_bh(&ipa_ctx->q_lock); 3953 for (i = 0; i < max_desc_cnt; i++) { 3954 ipa_ctx->tx_desc_pool[i].id = i; 3955 ipa_ctx->tx_desc_pool[i].ipa_tx_desc_ptr = NULL; 3956 qdf_list_insert_back(&ipa_ctx->tx_desc_free_list, 3957 &ipa_ctx->tx_desc_pool[i].node); 3958 } 3959 3960 ipa_ctx->stats.num_tx_desc_q_cnt = 0; 3961 ipa_ctx->stats.num_tx_desc_error = 0; 3962 3963 qdf_spin_unlock_bh(&ipa_ctx->q_lock); 3964 3965 return QDF_STATUS_SUCCESS; 3966 } 3967 3968 /** 3969 * wlan_ipa_setup_tx_sys_pipe() - Setup IPA Tx system pipes 3970 * @ipa_ctx: Global IPA IPA context 3971 * @desc_fifo_sz: Number of descriptors 3972 * 3973 * Return: 0 on success, negative errno on error 3974 */ wlan_ipa_setup_tx_sys_pipe(struct wlan_ipa_priv * ipa_ctx,int32_t desc_fifo_sz)3975 static int wlan_ipa_setup_tx_sys_pipe(struct wlan_ipa_priv *ipa_ctx, 3976 int32_t desc_fifo_sz) 3977 { 3978 int i, ret = 0; 3979 qdf_ipa_sys_connect_params_t *ipa; 3980 3981 /*setup TX pipes */ 3982 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 3983 ipa = &ipa_ctx->sys_pipe[i].ipa_sys_params; 3984 3985 ipa->client = wlan_ipa_iface_2_client[i].cons_client; 3986 ipa->desc_fifo_sz = desc_fifo_sz; 3987 ipa->priv = &ipa_ctx->iface_context[i]; 3988 ipa->notify = wlan_ipa_i2w_cb; 3989 3990 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 3991 ipa->ipa_ep_cfg.hdr.hdr_len = 3992 WLAN_IPA_UC_WLAN_TX_HDR_LEN; 3993 ipa->ipa_ep_cfg.nat.nat_en = IPA_BYPASS_NAT; 3994 ipa->ipa_ep_cfg.hdr.hdr_ofst_pkt_size_valid = 1; 3995 ipa->ipa_ep_cfg.hdr.hdr_ofst_pkt_size = 0; 3996 ipa->ipa_ep_cfg.hdr.hdr_additional_const_len = 3997 WLAN_IPA_UC_WLAN_8023_HDR_SIZE; 3998 ipa->ipa_ep_cfg.hdr_ext.hdr_little_endian = true; 3999 } else { 4000 ipa->ipa_ep_cfg.hdr.hdr_len = WLAN_IPA_WLAN_TX_HDR_LEN; 4001 } 4002 ipa->ipa_ep_cfg.mode.mode = IPA_BASIC; 4003 4004 ret = wlan_ipa_wdi_setup_sys_pipe(ipa_ctx, ipa, 4005 &ipa_ctx->sys_pipe[i].conn_hdl); 4006 if (ret) { 4007 ipa_err("Failed for pipe %d ret: %d", i, ret); 4008 return ret; 4009 } 4010 ipa_ctx->sys_pipe[i].conn_hdl_valid = 1; 4011 } 4012 4013 return ret; 4014 } 4015 #else /* QCA_LL_TX_FLOW_CONTROL_V2 */ 4016 4017 /** 4018 * wlan_ipa_free_tx_desc_list() - Free IPA Tx desc list 4019 * @ipa_ctx: IPA context 4020 * 4021 * Return: None 4022 */ wlan_ipa_free_tx_desc_list(struct wlan_ipa_priv * ipa_ctx)4023 static inline void wlan_ipa_free_tx_desc_list(struct wlan_ipa_priv *ipa_ctx) 4024 { 4025 } 4026 4027 /** 4028 * wlan_ipa_alloc_tx_desc_free_list() - Allocate IPA Tx desc list 4029 * @ipa_ctx: IPA context 4030 * 4031 * Return: QDF_STATUS 4032 */ 4033 static QDF_STATUS wlan_ipa_alloc_tx_desc_free_list(struct wlan_ipa_priv * ipa_ctx)4034 wlan_ipa_alloc_tx_desc_free_list(struct wlan_ipa_priv *ipa_ctx) 4035 { 4036 return QDF_STATUS_SUCCESS; 4037 } 4038 4039 /** 4040 * wlan_ipa_setup_tx_sys_pipe() - Setup IPA Tx system pipes 4041 * @ipa_ctx: IPA context 4042 * @desc_fifo_sz: Number of descriptors 4043 * 4044 * Return: 0 on success, negative errno on error 4045 */ wlan_ipa_setup_tx_sys_pipe(struct wlan_ipa_priv * ipa_ctx,int32_t desc_fifo_sz)4046 static int wlan_ipa_setup_tx_sys_pipe(struct wlan_ipa_priv *ipa_ctx, 4047 int32_t desc_fifo_sz) 4048 { 4049 /* 4050 * The Tx system pipes are not needed for MCC when TX_FLOW_CONTROL_V2 4051 * is enabled, where per vdev descriptors are supported in firmware. 4052 */ 4053 return 0; 4054 } 4055 #endif /* QCA_LL_TX_FLOW_CONTROL_V2 */ 4056 4057 #if defined(CONFIG_IPA_WDI_UNIFIED_API) && defined(IPA_WDI3_GSI) 4058 /** 4059 * wlan_ipa_get_rx_ipa_client() - Get IPA RX ipa client 4060 * @ipa_ctx: IPA context 4061 * 4062 * Return: rx ipa sys client 4063 */ wlan_ipa_get_rx_ipa_client(struct wlan_ipa_priv * ipa_ctx)4064 static inline uint8_t wlan_ipa_get_rx_ipa_client(struct wlan_ipa_priv *ipa_ctx) 4065 { 4066 if (ipa_ctx->over_gsi) 4067 return IPA_CLIENT_WLAN2_PROD; 4068 else 4069 return IPA_CLIENT_WLAN1_PROD; 4070 } 4071 4072 /** 4073 * wlan_ipa_uc_send_wdi_control_msg() - Set WDI control message 4074 * @ipa_ctx: IPA context 4075 * @ctrl: WDI control value 4076 * 4077 * Send WLAN_WDI_ENABLE for ctrl = true and WLAN_WDI_DISABLE otherwise. 4078 * 4079 * Return: QDF_STATUS 4080 */ wlan_ipa_uc_send_wdi_control_msg(struct wlan_ipa_priv * ipa_ctx,bool ctrl)4081 static QDF_STATUS wlan_ipa_uc_send_wdi_control_msg(struct wlan_ipa_priv *ipa_ctx, 4082 bool ctrl) 4083 { 4084 return QDF_STATUS_SUCCESS; 4085 } 4086 4087 #else wlan_ipa_get_rx_ipa_client(struct wlan_ipa_priv * ipa_ctx)4088 static inline uint8_t wlan_ipa_get_rx_ipa_client(struct wlan_ipa_priv *ipa_ctx) 4089 { 4090 return IPA_CLIENT_WLAN1_PROD; 4091 } 4092 wlan_ipa_uc_send_wdi_control_msg(struct wlan_ipa_priv * ipa_ctx,bool ctrl)4093 static QDF_STATUS wlan_ipa_uc_send_wdi_control_msg(struct wlan_ipa_priv *ipa_ctx, 4094 bool ctrl) 4095 { 4096 struct wlan_ipa_priv *ipa_obj = ipa_ctx; 4097 qdf_ipa_msg_meta_t meta; 4098 qdf_ipa_wlan_msg_t *ipa_msg; 4099 int ret = 0; 4100 4101 /* WDI enable message to IPA */ 4102 QDF_IPA_MSG_META_MSG_LEN(&meta) = sizeof(*ipa_msg); 4103 ipa_msg = qdf_mem_malloc(QDF_IPA_MSG_META_MSG_LEN(&meta)); 4104 if (!ipa_msg) 4105 return QDF_STATUS_E_NOMEM; 4106 4107 if (ctrl) { 4108 QDF_IPA_SET_META_MSG_TYPE(&meta, QDF_WDI_ENABLE); 4109 ipa_obj->stats.event[QDF_WDI_ENABLE]++; 4110 } else { 4111 QDF_IPA_SET_META_MSG_TYPE(&meta, QDF_WDI_DISABLE); 4112 ipa_obj->stats.event[QDF_WDI_DISABLE]++; 4113 } 4114 4115 ipa_debug("ipa_send_msg(Evt:%d)", QDF_IPA_MSG_META_MSG_TYPE(&meta)); 4116 ret = qdf_ipa_send_msg(&meta, ipa_msg, wlan_ipa_msg_free_fn); 4117 if (ret) { 4118 ipa_err("ipa_send_msg(Evt:%d)-fail=%d", 4119 QDF_IPA_MSG_META_MSG_TYPE(&meta), ret); 4120 qdf_mem_free(ipa_msg); 4121 return QDF_STATUS_E_FAILURE; 4122 } 4123 4124 return QDF_STATUS_SUCCESS; 4125 } 4126 #endif 4127 4128 /** 4129 * wlan_ipa_setup_rx_sys_pipe() - Setup IPA Rx system pipes 4130 * @ipa_ctx: Global IPA IPA context 4131 * @desc_fifo_sz: Number of descriptors 4132 * 4133 * Return: 0 on success, negative errno on error 4134 */ wlan_ipa_setup_rx_sys_pipe(struct wlan_ipa_priv * ipa_ctx,int32_t desc_fifo_sz)4135 static int wlan_ipa_setup_rx_sys_pipe(struct wlan_ipa_priv *ipa_ctx, 4136 int32_t desc_fifo_sz) 4137 { 4138 int ret = 0; 4139 qdf_ipa_sys_connect_params_t *ipa; 4140 4141 /* 4142 * Hard code it here, this can be extended if in case 4143 * PROD pipe is also per interface. 4144 * Right now there is no advantage of doing this. 4145 */ 4146 ipa = &ipa_ctx->sys_pipe[WLAN_IPA_RX_PIPE].ipa_sys_params; 4147 4148 ipa->client = wlan_ipa_get_rx_ipa_client(ipa_ctx); 4149 ipa->desc_fifo_sz = desc_fifo_sz; 4150 ipa->priv = ipa_ctx; 4151 ipa->notify = wlan_ipa_w2i_cb; 4152 4153 ipa->ipa_ep_cfg.nat.nat_en = IPA_BYPASS_NAT; 4154 ipa->ipa_ep_cfg.hdr.hdr_len = WLAN_IPA_WLAN_RX_HDR_LEN; 4155 ipa->ipa_ep_cfg.hdr.hdr_ofst_metadata_valid = 1; 4156 ipa->ipa_ep_cfg.mode.mode = IPA_BASIC; 4157 4158 ret = qdf_ipa_setup_sys_pipe(ipa, 4159 &ipa_ctx->sys_pipe[WLAN_IPA_RX_PIPE].conn_hdl); 4160 if (ret) { 4161 ipa_err("Failed for RX pipe: %d", ret); 4162 return ret; 4163 } 4164 ipa_ctx->sys_pipe[WLAN_IPA_RX_PIPE].conn_hdl_valid = 1; 4165 4166 return ret; 4167 } 4168 4169 /** 4170 * wlan_ipa_teardown_sys_pipe() - Tear down all IPA Sys pipes 4171 * @ipa_ctx: Global IPA IPA context 4172 * 4173 * Return: None 4174 */ wlan_ipa_teardown_sys_pipe(struct wlan_ipa_priv * ipa_ctx)4175 static void wlan_ipa_teardown_sys_pipe(struct wlan_ipa_priv *ipa_ctx) 4176 { 4177 int ret, i; 4178 4179 if (!ipa_ctx) 4180 return; 4181 4182 for (i = 0; i < WLAN_IPA_MAX_SYSBAM_PIPE; i++) { 4183 if (ipa_ctx->sys_pipe[i].conn_hdl_valid) { 4184 ret = wlan_ipa_wdi_teardown_sys_pipe(ipa_ctx, 4185 ipa_ctx->sys_pipe[i].conn_hdl); 4186 if (ret) 4187 ipa_err("Failed:%d", ret); 4188 4189 ipa_ctx->sys_pipe[i].conn_hdl_valid = 0; 4190 } 4191 } 4192 4193 wlan_ipa_free_tx_desc_list(ipa_ctx); 4194 } 4195 4196 /** 4197 * wlan_ipa_setup_sys_pipe() - Setup all IPA system pipes 4198 * @ipa_ctx: Global IPA IPA context 4199 * 4200 * Return: 0 on success, negative errno on error 4201 */ wlan_ipa_setup_sys_pipe(struct wlan_ipa_priv * ipa_ctx)4202 static int wlan_ipa_setup_sys_pipe(struct wlan_ipa_priv *ipa_ctx) 4203 { 4204 int ret = 0; 4205 uint32_t desc_fifo_sz; 4206 4207 /* The maximum number of descriptors that can be provided to a BAM at 4208 * once is one less than the total number of descriptors that the buffer 4209 * can contain. 4210 * If max_num_of_descriptors = (BAM_PIPE_DESCRIPTOR_FIFO_SIZE / sizeof 4211 * (SPS_DESCRIPTOR)), then (max_num_of_descriptors - 1) descriptors can 4212 * be provided at once. 4213 * Because of above requirement, one extra descriptor will be added to 4214 * make sure hardware always has one descriptor. 4215 */ 4216 desc_fifo_sz = ipa_ctx->config->desc_size + IPA_SPS_DESC_SIZE; 4217 4218 ret = wlan_ipa_setup_tx_sys_pipe(ipa_ctx, desc_fifo_sz); 4219 if (ret) { 4220 ipa_err("Failed for TX pipe: %d", ret); 4221 goto setup_sys_pipe_fail; 4222 } 4223 4224 if (!wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 4225 ret = wlan_ipa_setup_rx_sys_pipe(ipa_ctx, desc_fifo_sz); 4226 if (ret) { 4227 ipa_err("Failed for RX pipe: %d", ret); 4228 goto setup_sys_pipe_fail; 4229 } 4230 } 4231 4232 /* Allocate free Tx desc list */ 4233 ret = wlan_ipa_alloc_tx_desc_free_list(ipa_ctx); 4234 if (ret) 4235 goto setup_sys_pipe_fail; 4236 4237 return ret; 4238 4239 setup_sys_pipe_fail: 4240 wlan_ipa_teardown_sys_pipe(ipa_ctx); 4241 4242 return ret; 4243 } 4244 4245 #if !defined(QCA_LL_TX_FLOW_CONTROL_V2) && !defined(QCA_IPA_LL_TX_FLOW_CONTROL) wlan_ipa_send_mcc_scc_msg(struct wlan_ipa_priv * ipa_ctx,bool mcc_mode)4246 QDF_STATUS wlan_ipa_send_mcc_scc_msg(struct wlan_ipa_priv *ipa_ctx, 4247 bool mcc_mode) 4248 { 4249 qdf_ipa_msg_meta_t meta; 4250 qdf_ipa_wlan_msg_t *msg; 4251 int ret; 4252 4253 if (!wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) 4254 return QDF_STATUS_SUCCESS; 4255 4256 /* Send SCC/MCC Switching event to IPA */ 4257 QDF_IPA_MSG_META_MSG_LEN(&meta) = sizeof(*msg); 4258 msg = qdf_mem_malloc(QDF_IPA_MSG_META_MSG_LEN(&meta)); 4259 if (!msg) 4260 return QDF_STATUS_E_NOMEM; 4261 4262 if (mcc_mode) { 4263 QDF_IPA_SET_META_MSG_TYPE(&meta, QDF_SWITCH_TO_MCC); 4264 ipa_ctx->stats.event[QDF_SWITCH_TO_MCC]++; 4265 } else { 4266 QDF_IPA_SET_META_MSG_TYPE(&meta, QDF_SWITCH_TO_SCC); 4267 ipa_ctx->stats.event[QDF_SWITCH_TO_SCC]++; 4268 } 4269 4270 WLAN_IPA_LOG(QDF_TRACE_LEVEL_DEBUG, 4271 "ipa_send_msg(Evt:%d)", 4272 QDF_IPA_MSG_META_MSG_TYPE(&meta)); 4273 4274 ret = qdf_ipa_send_msg(&meta, msg, wlan_ipa_msg_free_fn); 4275 4276 if (ret) { 4277 ipa_err("ipa_send_msg(Evt:%d) - fail=%d", 4278 QDF_IPA_MSG_META_MSG_TYPE(&meta), ret); 4279 qdf_mem_free(msg); 4280 return QDF_STATUS_E_FAILURE; 4281 } 4282 4283 return QDF_STATUS_SUCCESS; 4284 } 4285 wlan_ipa_mcc_work_handler(void * data)4286 static void wlan_ipa_mcc_work_handler(void *data) 4287 { 4288 struct wlan_ipa_priv *ipa_ctx = (struct wlan_ipa_priv *)data; 4289 4290 wlan_ipa_send_mcc_scc_msg(ipa_ctx, ipa_ctx->mcc_mode); 4291 } 4292 #endif 4293 4294 #ifdef IPA_OPT_WIFI_DP 4295 /** 4296 * wlan_ipa_reg_flt_cbs() - register filter cbs with IPA to set up Rx CCE filter 4297 * rules for optional wifi datapath 4298 * @ipa_ctx: IPA context 4299 * 4300 * 4301 * Return: QDF_STATUS enumeration 4302 */ wlan_ipa_reg_flt_cbs(struct wlan_ipa_priv * ipa_ctx)4303 static inline QDF_STATUS wlan_ipa_reg_flt_cbs(struct wlan_ipa_priv *ipa_ctx) 4304 { 4305 QDF_STATUS status; 4306 4307 ipa_wdi_opt_dpath_flt_rsrv_cb flt_rsrv_cb = 4308 &wlan_ipa_wdi_opt_dpath_flt_rsrv_cb; 4309 ipa_wdi_opt_dpath_flt_rsrv_rel_cb 4310 flt_rsrv_rel_cb = &wlan_ipa_wdi_opt_dpath_flt_rsrv_rel_cb; 4311 ipa_wdi_opt_dpath_flt_rem_cb flt_rem_cb = 4312 &wlan_ipa_wdi_opt_dpath_flt_rem_cb; 4313 ipa_wdi_opt_dpath_flt_add_cb flt_add_cb = 4314 &wlan_ipa_wdi_opt_dpath_flt_add_cb; 4315 4316 status = qdf_ipa_wdi_register_flt_cb(ipa_ctx->hdl, flt_rsrv_cb, 4317 flt_rsrv_rel_cb, 4318 flt_add_cb, 4319 flt_rem_cb); 4320 return status; 4321 } 4322 4323 /** 4324 * wlan_ipa_opt_dp_init() - Check if OPT_WIFI_DP enabled from both IPA 4325 * and WLAN, and perform required init steps 4326 * @ipa_ctx: IPA context 4327 * 4328 * 4329 * Return: QDF_STATUS enumeration 4330 */ 4331 static inline wlan_ipa_opt_dp_init(struct wlan_ipa_priv * ipa_ctx)4332 QDF_STATUS wlan_ipa_opt_dp_init(struct wlan_ipa_priv *ipa_ctx) 4333 { 4334 QDF_STATUS status = QDF_STATUS_SUCCESS; 4335 4336 /* Register call backs for opt wifi dp */ 4337 if (ipa_ctx->opt_wifi_datapath) { 4338 if (ipa_config_is_opt_wifi_dp_enabled()) { 4339 status = wlan_ipa_reg_flt_cbs(ipa_ctx); 4340 ipa_debug("opt_dp: Register flt cb. status %d", status); 4341 qdf_wake_lock_create(&ipa_ctx->opt_dp_wake_lock, 4342 "opt_dp"); 4343 } else { 4344 ipa_debug("opt_dp: Disabled from WLAN INI"); 4345 } 4346 } else { 4347 ipa_debug("opt_dp: Disabled from IPA"); 4348 } 4349 4350 return status; 4351 } 4352 4353 /** 4354 * wlan_ipa_destroy_opt_wifi_flt_cb_event - destroy filter cb event 4355 * @ipa_ctx: IPA context 4356 * 4357 *Return: void 4358 */ 4359 static inline wlan_ipa_destroy_opt_wifi_flt_cb_event(struct wlan_ipa_priv * ipa_ctx)4360 void wlan_ipa_destroy_opt_wifi_flt_cb_event(struct wlan_ipa_priv *ipa_ctx) 4361 { 4362 qdf_event_destroy(&ipa_ctx->ipa_flt_evnt); 4363 } 4364 4365 /** 4366 * wlan_ipa_opt_dp_deinit() - Perform opt_wifi_dp deinit steps 4367 * @ipa_ctx: IPA context 4368 * 4369 * Return: None 4370 */ 4371 static inline wlan_ipa_opt_dp_deinit(struct wlan_ipa_priv * ipa_ctx)4372 void wlan_ipa_opt_dp_deinit(struct wlan_ipa_priv *ipa_ctx) 4373 { 4374 if (ipa_ctx->uc_loaded) 4375 wlan_ipa_destroy_opt_wifi_flt_cb_event(ipa_ctx); 4376 4377 if (ipa_ctx->opt_wifi_datapath && ipa_config_is_opt_wifi_dp_enabled()) 4378 qdf_wake_lock_destroy(&ipa_ctx->opt_dp_wake_lock); 4379 4380 if (cdp_ipa_get_smmu_mapped(ipa_ctx->dp_soc)) { 4381 cdp_ipa_set_smmu_mapped(ipa_ctx->dp_soc, 0); 4382 cdp_ipa_rx_buf_smmu_pool_mapping(ipa_ctx->dp_soc, 4383 ipa_ctx->dp_pdev_id, 4384 false, __func__, __LINE__); 4385 } 4386 } 4387 4388 #else wlan_ipa_reg_flt_cbs(struct wlan_ipa_priv * ipa_ctx)4389 static inline QDF_STATUS wlan_ipa_reg_flt_cbs(struct wlan_ipa_priv *ipa_ctx) 4390 { 4391 return QDF_STATUS_SUCCESS; 4392 } 4393 4394 static inline wlan_ipa_opt_dp_init(struct wlan_ipa_priv * ipa_ctx)4395 QDF_STATUS wlan_ipa_opt_dp_init(struct wlan_ipa_priv *ipa_ctx) 4396 { 4397 return QDF_STATUS_SUCCESS; 4398 } 4399 4400 static inline wlan_ipa_destroy_opt_wifi_flt_cb_event(struct wlan_ipa_priv * ipa_ctx)4401 void wlan_ipa_destroy_opt_wifi_flt_cb_event(struct wlan_ipa_priv *ipa_ctx) 4402 { 4403 } 4404 4405 static inline wlan_ipa_opt_dp_deinit(struct wlan_ipa_priv * ipa_ctx)4406 void wlan_ipa_opt_dp_deinit(struct wlan_ipa_priv *ipa_ctx) 4407 { 4408 } 4409 #endif 4410 4411 /** 4412 * wlan_ipa_setup() - IPA initialization function 4413 * @ipa_ctx: IPA context 4414 * @ipa_cfg: IPA config 4415 * 4416 * Allocate ipa_ctx resources, ipa pipe resource and register 4417 * wlan interface with IPA module. 4418 * 4419 * Return: QDF_STATUS enumeration 4420 */ wlan_ipa_setup(struct wlan_ipa_priv * ipa_ctx,struct wlan_ipa_config * ipa_cfg)4421 QDF_STATUS wlan_ipa_setup(struct wlan_ipa_priv *ipa_ctx, 4422 struct wlan_ipa_config *ipa_cfg) 4423 { 4424 int ret, i; 4425 struct wlan_ipa_iface_context *iface_context = NULL; 4426 QDF_STATUS status; 4427 4428 ipa_debug("enter"); 4429 4430 gp_ipa = ipa_ctx; 4431 ipa_ctx->num_iface = 0; 4432 ipa_ctx->config = ipa_cfg; 4433 4434 wlan_ipa_wdi_get_wdi_version(ipa_ctx); 4435 4436 /* Create the interface context */ 4437 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 4438 iface_context = &ipa_ctx->iface_context[i]; 4439 iface_context->ipa_ctx = ipa_ctx; 4440 iface_context->cons_client = 4441 wlan_ipa_iface_2_client[i].cons_client; 4442 iface_context->prod_client = 4443 wlan_ipa_iface_2_client[i].prod_client; 4444 iface_context->iface_id = i; 4445 iface_context->dev = NULL; 4446 iface_context->device_mode = QDF_MAX_NO_OF_MODE; 4447 iface_context->session_id = WLAN_IPA_MAX_SESSION; 4448 qdf_atomic_init(&iface_context->conn_count); 4449 qdf_atomic_init(&iface_context->disconn_count); 4450 qdf_spinlock_create(&iface_context->interface_lock); 4451 } 4452 4453 qdf_create_work(0, &ipa_ctx->pm_work, wlan_ipa_pm_flush, ipa_ctx); 4454 qdf_spinlock_create(&ipa_ctx->pm_lock); 4455 qdf_spinlock_create(&ipa_ctx->q_lock); 4456 qdf_spinlock_create(&ipa_ctx->enable_disable_lock); 4457 ipa_ctx->pipes_down_in_progress = false; 4458 ipa_ctx->pipes_enable_in_progress = false; 4459 qdf_nbuf_queue_init(&ipa_ctx->pm_queue_head); 4460 qdf_list_create(&ipa_ctx->pending_event, 1000); 4461 qdf_mutex_create(&ipa_ctx->event_lock); 4462 qdf_mutex_create(&ipa_ctx->ipa_lock); 4463 qdf_atomic_init(&ipa_ctx->deinit_in_prog); 4464 4465 cdp_ipa_set_smmu_mapped(ipa_ctx->dp_soc, 0); 4466 4467 status = wlan_ipa_wdi_setup_rm(ipa_ctx); 4468 if (status != QDF_STATUS_SUCCESS) 4469 goto fail_setup_rm; 4470 4471 for (i = 0; i < WLAN_IPA_MAX_SYSBAM_PIPE; i++) 4472 qdf_mem_zero(&ipa_ctx->sys_pipe[i], 4473 sizeof(struct wlan_ipa_sys_pipe)); 4474 4475 if (wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 4476 qdf_mem_zero(&ipa_ctx->stats, sizeof(ipa_ctx->stats)); 4477 ipa_ctx->sap_num_connected_sta = 0; 4478 ipa_ctx->ipa_tx_packets_diff = 0; 4479 ipa_ctx->ipa_rx_packets_diff = 0; 4480 ipa_ctx->ipa_p_tx_packets = 0; 4481 ipa_ctx->ipa_p_rx_packets = 0; 4482 ipa_ctx->resource_loading = false; 4483 ipa_ctx->resource_unloading = false; 4484 ipa_ctx->num_sap_connected = 0; 4485 ipa_ctx->sta_connected = 0; 4486 ipa_ctx->ipa_pipes_down = true; 4487 qdf_atomic_set(&ipa_ctx->pipes_disabled, 1); 4488 qdf_atomic_set(&ipa_ctx->autonomy_disabled, 1); 4489 ipa_ctx->wdi_enabled = false; 4490 4491 status = wlan_ipa_wdi_init(ipa_ctx); 4492 4493 if (status == QDF_STATUS_SUCCESS) { 4494 /* Setup IPA system pipes */ 4495 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 4496 ret = wlan_ipa_setup_sys_pipe(ipa_ctx); 4497 if (ret) 4498 goto ipa_wdi_destroy; 4499 4500 qdf_create_work(0, &ipa_ctx->mcc_work, 4501 wlan_ipa_mcc_work_handler, 4502 ipa_ctx); 4503 } 4504 } else if (status == QDF_STATUS_E_BUSY) { 4505 ret = wlan_ipa_uc_send_wdi_control_msg(ipa_ctx, false); 4506 if (ret) { 4507 ipa_err("IPA WDI msg send failed: ret=%d", ret); 4508 goto ipa_wdi_destroy; 4509 } 4510 } else { 4511 ipa_err("IPA WDI init failed: ret=%d", status); 4512 goto ipa_wdi_destroy; 4513 } 4514 } else { 4515 ret = wlan_ipa_setup_sys_pipe(ipa_ctx); 4516 if (ret) 4517 goto ipa_wdi_destroy; 4518 } 4519 4520 status = wlan_ipa_opt_dp_init(ipa_ctx); 4521 4522 qdf_event_create(&ipa_ctx->ipa_resource_comp); 4523 4524 ipa_debug("exit: success"); 4525 4526 return QDF_STATUS_SUCCESS; 4527 4528 ipa_wdi_destroy: 4529 wlan_ipa_wdi_destroy_rm(ipa_ctx); 4530 4531 fail_setup_rm: 4532 qdf_spinlock_destroy(&ipa_ctx->pm_lock); 4533 qdf_spinlock_destroy(&ipa_ctx->q_lock); 4534 qdf_spinlock_destroy(&ipa_ctx->enable_disable_lock); 4535 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 4536 iface_context = &ipa_ctx->iface_context[i]; 4537 qdf_spinlock_destroy(&iface_context->interface_lock); 4538 } 4539 qdf_mutex_destroy(&ipa_ctx->event_lock); 4540 qdf_mutex_destroy(&ipa_ctx->ipa_lock); 4541 qdf_list_destroy(&ipa_ctx->pending_event); 4542 gp_ipa = NULL; 4543 ipa_debug("exit: fail"); 4544 4545 return QDF_STATUS_E_FAILURE; 4546 } 4547 wlan_ipa_flush(struct wlan_ipa_priv * ipa_ctx)4548 void wlan_ipa_flush(struct wlan_ipa_priv *ipa_ctx) 4549 { 4550 qdf_nbuf_t skb; 4551 struct wlan_ipa_pm_tx_cb *pm_tx_cb; 4552 4553 if (!wlan_ipa_is_enabled(ipa_ctx->config)) 4554 return; 4555 4556 qdf_cancel_work(&ipa_ctx->pm_work); 4557 4558 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 4559 4560 while (((skb = qdf_nbuf_queue_remove(&ipa_ctx->pm_queue_head)) 4561 != NULL)) { 4562 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 4563 4564 pm_tx_cb = (struct wlan_ipa_pm_tx_cb *)skb->cb; 4565 4566 if (pm_tx_cb->exception || pm_tx_cb->send_to_nw) { 4567 dev_kfree_skb_any(skb); 4568 } else { 4569 if (pm_tx_cb->ipa_tx_desc) 4570 ipa_free_skb(pm_tx_cb->ipa_tx_desc); 4571 } 4572 4573 qdf_spin_lock_bh(&ipa_ctx->pm_lock); 4574 } 4575 qdf_spin_unlock_bh(&ipa_ctx->pm_lock); 4576 } 4577 wlan_ipa_cleanup(struct wlan_ipa_priv * ipa_ctx)4578 QDF_STATUS wlan_ipa_cleanup(struct wlan_ipa_priv *ipa_ctx) 4579 { 4580 struct wlan_ipa_iface_context *iface_context; 4581 int i; 4582 4583 if (!ipa_cb_is_ready()) 4584 return QDF_STATUS_SUCCESS; 4585 qdf_event_destroy(&ipa_ctx->ipa_resource_comp); 4586 if (!wlan_ipa_uc_is_enabled(ipa_ctx->config)) 4587 wlan_ipa_teardown_sys_pipe(ipa_ctx); 4588 4589 wlan_ipa_opt_dp_deinit(ipa_ctx); 4590 4591 /* Teardown IPA sys_pipe for MCC */ 4592 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 4593 wlan_ipa_teardown_sys_pipe(ipa_ctx); 4594 if (ipa_ctx->uc_loaded) 4595 qdf_cancel_work(&ipa_ctx->mcc_work); 4596 } 4597 4598 wlan_ipa_wdi_destroy_rm(ipa_ctx); 4599 4600 wlan_ipa_flush(ipa_ctx); 4601 4602 qdf_spinlock_destroy(&ipa_ctx->pm_lock); 4603 qdf_spinlock_destroy(&ipa_ctx->q_lock); 4604 qdf_spinlock_destroy(&ipa_ctx->enable_disable_lock); 4605 qdf_destroy_work(0, &ipa_ctx->pm_work); 4606 4607 /* destroy the interface lock */ 4608 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 4609 iface_context = &ipa_ctx->iface_context[i]; 4610 qdf_spinlock_destroy(&iface_context->interface_lock); 4611 } 4612 4613 if (wlan_ipa_uc_is_enabled(ipa_ctx->config)) { 4614 wlan_ipa_wdi_cleanup(ipa_ctx->hdl); 4615 qdf_mutex_destroy(&ipa_ctx->event_lock); 4616 qdf_mutex_destroy(&ipa_ctx->ipa_lock); 4617 qdf_list_destroy(&ipa_ctx->pending_event); 4618 4619 } 4620 4621 gp_ipa = NULL; 4622 4623 ipa_ctx->handle_initialized = false; 4624 4625 return QDF_STATUS_SUCCESS; 4626 } 4627 4628 struct wlan_ipa_iface_context wlan_ipa_get_iface(struct wlan_ipa_priv * ipa_ctx,uint8_t mode)4629 *wlan_ipa_get_iface(struct wlan_ipa_priv *ipa_ctx, uint8_t mode) 4630 { 4631 struct wlan_ipa_iface_context *iface_ctx = NULL; 4632 int i; 4633 4634 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 4635 iface_ctx = &ipa_ctx->iface_context[i]; 4636 4637 if (iface_ctx->device_mode == mode) 4638 return iface_ctx; 4639 } 4640 4641 return NULL; 4642 } 4643 wlan_ipa_check_iface_netdev_sessid(struct wlan_ipa_iface_context * iface_ctx,qdf_netdev_t net_dev,uint8_t session_id)4644 int wlan_ipa_check_iface_netdev_sessid(struct wlan_ipa_iface_context *iface_ctx, 4645 qdf_netdev_t net_dev, uint8_t session_id) 4646 { 4647 if (iface_ctx->dev == net_dev && iface_ctx->session_id == session_id) 4648 return 1; 4649 4650 return 0; 4651 } 4652 4653 struct wlan_ipa_iface_context * wlan_ipa_get_iface_by_mode_netdev(struct wlan_ipa_priv * ipa_ctx,qdf_netdev_t ndev,uint8_t mode,uint8_t session_id)4654 wlan_ipa_get_iface_by_mode_netdev(struct wlan_ipa_priv *ipa_ctx, 4655 qdf_netdev_t ndev, uint8_t mode, 4656 uint8_t session_id) 4657 { 4658 struct wlan_ipa_iface_context *iface_ctx = NULL; 4659 int i; 4660 4661 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 4662 iface_ctx = &ipa_ctx->iface_context[i]; 4663 4664 if (iface_ctx->device_mode == mode && 4665 wlan_ipa_check_iface_netdev_sessid(iface_ctx, ndev, 4666 session_id)) 4667 return iface_ctx; 4668 } 4669 4670 return NULL; 4671 } 4672 wlan_ipa_set_mcc_mode(struct wlan_ipa_priv * ipa_ctx,bool mcc_mode)4673 void wlan_ipa_set_mcc_mode(struct wlan_ipa_priv *ipa_ctx, bool mcc_mode) 4674 { 4675 if (!wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) 4676 return; 4677 4678 if (ipa_ctx->mcc_mode == mcc_mode) 4679 return; 4680 4681 ipa_ctx->mcc_mode = mcc_mode; 4682 qdf_sched_work(0, &ipa_ctx->mcc_work); 4683 } 4684 4685 /** 4686 * wlan_ipa_uc_loaded_handler() - Process IPA uC loaded indication 4687 * @ipa_ctx: ipa ipa local context 4688 * 4689 * Will handle IPA UC image loaded indication comes from IPA kernel 4690 * 4691 * Return: None 4692 */ wlan_ipa_uc_loaded_handler(struct wlan_ipa_priv * ipa_ctx)4693 static void wlan_ipa_uc_loaded_handler(struct wlan_ipa_priv *ipa_ctx) 4694 { 4695 struct wlan_objmgr_pdev *pdev = ipa_ctx->pdev; 4696 struct wlan_objmgr_psoc *psoc = wlan_pdev_get_psoc(pdev); 4697 qdf_device_t qdf_dev = wlan_psoc_get_qdf_dev(psoc); 4698 QDF_STATUS status; 4699 4700 ipa_info("UC READY"); 4701 4702 if (true == ipa_ctx->uc_loaded) { 4703 ipa_info("UC already loaded"); 4704 return; 4705 } 4706 4707 if (!qdf_dev) { 4708 ipa_err("qdf_dev is null"); 4709 return; 4710 } 4711 4712 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 4713 /* Setup IPA system pipes */ 4714 status = wlan_ipa_setup_sys_pipe(ipa_ctx); 4715 if (status) { 4716 ipa_err("Fail to setup sys pipes (status=%d)", status); 4717 return; 4718 } 4719 qdf_create_work(0, &ipa_ctx->mcc_work, 4720 wlan_ipa_mcc_work_handler, ipa_ctx); 4721 } 4722 4723 /* Connect pipe */ 4724 status = wlan_ipa_wdi_setup(ipa_ctx, qdf_dev); 4725 if (status) { 4726 ipa_err("Failure to setup IPA pipes (status=%d)", 4727 status); 4728 goto connect_pipe_fail; 4729 } 4730 /* Setup the Tx buffer SMMU mappings */ 4731 status = cdp_ipa_tx_buf_smmu_mapping(ipa_ctx->dp_soc, 4732 ipa_ctx->dp_pdev_id, 4733 __func__, __LINE__); 4734 if (status) { 4735 ipa_err("Failure to map Tx buffers for IPA(status=%d)", 4736 status); 4737 goto smmu_map_fail; 4738 } 4739 ipa_info("TX buffers mapped to IPA"); 4740 cdp_ipa_set_doorbell_paddr(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id); 4741 wlan_ipa_init_metering(ipa_ctx); 4742 wlan_ipa_add_rem_flt_cb_event(ipa_ctx); 4743 if (QDF_IS_STATUS_ERROR(wlan_ipa_init_perf_level(ipa_ctx))) 4744 ipa_err("Failed to init perf level"); 4745 4746 /* 4747 * Enable IPA/FW PIPEs if 4748 * 1. any clients connected to SAP or 4749 * 2. STA connected to remote AP if STA only offload is enabled 4750 */ 4751 if (ipa_ctx->sap_num_connected_sta || 4752 (wlan_ipa_is_sta_only_offload_enabled() && 4753 ipa_ctx->sta_connected)) { 4754 ipa_debug("Client already connected, enable IPA/FW PIPEs"); 4755 wlan_ipa_uc_handle_first_con(ipa_ctx); 4756 } 4757 4758 ipa_ctx->uc_loaded = true; 4759 4760 return; 4761 4762 smmu_map_fail: 4763 qdf_ipa_wdi_disconn_pipes(ipa_ctx->hdl); 4764 4765 connect_pipe_fail: 4766 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 4767 qdf_cancel_work(&ipa_ctx->mcc_work); 4768 wlan_ipa_teardown_sys_pipe(ipa_ctx); 4769 } 4770 } 4771 4772 /** 4773 * wlan_ipa_uc_op_cb() - IPA uC operation callback 4774 * @op_msg: operation message received from firmware 4775 * @ipa_ctx: IPA context 4776 * 4777 * Return: None 4778 */ wlan_ipa_uc_op_cb(struct op_msg_type * op_msg,struct wlan_ipa_priv * ipa_ctx)4779 static void wlan_ipa_uc_op_cb(struct op_msg_type *op_msg, 4780 struct wlan_ipa_priv *ipa_ctx) 4781 { 4782 struct op_msg_type *msg = op_msg; 4783 struct ipa_uc_fw_stats *uc_fw_stat; 4784 4785 if (!ipa_ctx || !op_msg) { 4786 ipa_err("INVALID ARG"); 4787 return; 4788 } 4789 4790 if (msg->op_code >= WLAN_IPA_UC_OPCODE_MAX) { 4791 ipa_err("INVALID OPCODE %d", msg->op_code); 4792 qdf_mem_free(op_msg); 4793 return; 4794 } 4795 4796 ipa_debug("OPCODE=%d", msg->op_code); 4797 4798 if ((msg->op_code == WLAN_IPA_UC_OPCODE_TX_RESUME) || 4799 (msg->op_code == WLAN_IPA_UC_OPCODE_RX_RESUME)) { 4800 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4801 ipa_ctx->activated_fw_pipe++; 4802 if (wlan_ipa_is_fw_wdi_activated(ipa_ctx)) { 4803 ipa_ctx->resource_loading = false; 4804 qdf_event_set(&ipa_ctx->ipa_resource_comp); 4805 if (ipa_ctx->wdi_enabled == false) { 4806 ipa_ctx->wdi_enabled = true; 4807 if (wlan_ipa_uc_send_wdi_control_msg(ipa_ctx, true) == 0) 4808 wlan_ipa_send_mcc_scc_msg(ipa_ctx, 4809 ipa_ctx->mcc_mode); 4810 } 4811 wlan_ipa_uc_proc_pending_event(ipa_ctx, true); 4812 if (ipa_ctx->pending_cons_req) 4813 wlan_ipa_wdi_rm_notify_completion( 4814 QDF_IPA_RM_RESOURCE_GRANTED, 4815 QDF_IPA_RM_RESOURCE_WLAN_CONS); 4816 ipa_ctx->pending_cons_req = false; 4817 } 4818 qdf_mutex_release(&ipa_ctx->ipa_lock); 4819 } else if ((msg->op_code == WLAN_IPA_UC_OPCODE_TX_SUSPEND) || 4820 (msg->op_code == WLAN_IPA_UC_OPCODE_RX_SUSPEND)) { 4821 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4822 4823 if (msg->op_code == WLAN_IPA_UC_OPCODE_RX_SUSPEND) { 4824 wlan_ipa_uc_disable_pipes(ipa_ctx, true); 4825 ipa_info("Disable FW TX PIPE"); 4826 cdp_ipa_set_active(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id, 4827 false, true); 4828 } 4829 4830 ipa_ctx->activated_fw_pipe--; 4831 if (!ipa_ctx->activated_fw_pipe) { 4832 /* 4833 * Async return success from FW 4834 * Disable/suspend all the PIPEs 4835 */ 4836 ipa_ctx->resource_unloading = false; 4837 qdf_event_set(&ipa_ctx->ipa_resource_comp); 4838 if (wlan_ipa_is_rm_enabled(ipa_ctx->config)) 4839 wlan_ipa_wdi_rm_release_resource(ipa_ctx, 4840 QDF_IPA_RM_RESOURCE_WLAN_PROD); 4841 wlan_ipa_uc_proc_pending_event(ipa_ctx, false); 4842 ipa_ctx->pending_cons_req = false; 4843 } 4844 qdf_mutex_release(&ipa_ctx->ipa_lock); 4845 } else if ((msg->op_code == WLAN_IPA_UC_OPCODE_STATS) && 4846 (ipa_ctx->stat_req_reason == WLAN_IPA_UC_STAT_REASON_DEBUG)) { 4847 uc_fw_stat = (struct ipa_uc_fw_stats *) 4848 ((uint8_t *)op_msg + sizeof(struct op_msg_type)); 4849 4850 /* WLAN FW WDI stats */ 4851 wlan_ipa_print_fw_wdi_stats(ipa_ctx, uc_fw_stat); 4852 } else if ((msg->op_code == WLAN_IPA_UC_OPCODE_STATS) && 4853 (ipa_ctx->stat_req_reason == WLAN_IPA_UC_STAT_REASON_BW_CAL)) { 4854 /* STATs from FW */ 4855 uc_fw_stat = (struct ipa_uc_fw_stats *) 4856 ((uint8_t *)op_msg + sizeof(struct op_msg_type)); 4857 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4858 ipa_ctx->ipa_tx_packets_diff = BW_GET_DIFF( 4859 uc_fw_stat->tx_pkts_completed, 4860 ipa_ctx->ipa_p_tx_packets); 4861 ipa_ctx->ipa_rx_packets_diff = BW_GET_DIFF( 4862 (uc_fw_stat->rx_num_ind_drop_no_space + 4863 uc_fw_stat->rx_num_ind_drop_no_buf + 4864 uc_fw_stat->rx_num_pkts_indicated), 4865 ipa_ctx->ipa_p_rx_packets); 4866 4867 ipa_ctx->ipa_p_tx_packets = uc_fw_stat->tx_pkts_completed; 4868 ipa_ctx->ipa_p_rx_packets = 4869 (uc_fw_stat->rx_num_ind_drop_no_space + 4870 uc_fw_stat->rx_num_ind_drop_no_buf + 4871 uc_fw_stat->rx_num_pkts_indicated); 4872 qdf_mutex_release(&ipa_ctx->ipa_lock); 4873 } else if (msg->op_code == WLAN_IPA_UC_OPCODE_UC_READY) { 4874 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4875 wlan_ipa_uc_loaded_handler(ipa_ctx); 4876 qdf_mutex_release(&ipa_ctx->ipa_lock); 4877 } else if (msg->op_code == WLAN_IPA_FILTER_RSV_NOTIFY) { 4878 ipa_info("opt_dp: IPA notify filter resrv response: %d", 4879 msg->rsvd); 4880 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4881 qdf_ipa_wdi_opt_dpath_notify_flt_rsvd_per_inst(ipa_ctx->hdl, 4882 msg->rsvd); 4883 qdf_mutex_release(&ipa_ctx->ipa_lock); 4884 } else if (msg->op_code == WLAN_IPA_FILTER_REL_NOTIFY) { 4885 ipa_info("opt_dp: IPA notify filter rel_response: %d", 4886 msg->rsvd); 4887 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4888 qdf_ipa_wdi_opt_dpath_notify_flt_rlsd_per_inst(ipa_ctx->hdl, 4889 msg->rsvd); 4890 qdf_mutex_release(&ipa_ctx->ipa_lock); 4891 } else if (msg->op_code == WLAN_IPA_SMMU_MAP) { 4892 ipa_info("opt_dp: IPA smmu pool map"); 4893 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4894 cdp_ipa_rx_buf_smmu_pool_mapping(ipa_ctx->dp_soc, 4895 ipa_ctx->dp_pdev_id, true, 4896 __func__, __LINE__); 4897 qdf_mutex_release(&ipa_ctx->ipa_lock); 4898 } else if (msg->op_code == WLAN_IPA_SMMU_UNMAP) { 4899 ipa_info("opt_dp: IPA smmu pool unmap"); 4900 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 4901 cdp_ipa_rx_buf_smmu_pool_mapping(ipa_ctx->dp_soc, 4902 ipa_ctx->dp_pdev_id, 4903 false, __func__, __LINE__); 4904 qdf_mutex_release(&ipa_ctx->ipa_lock); 4905 } else if (wlan_ipa_uc_op_metering(ipa_ctx, op_msg)) { 4906 ipa_err("Invalid message: op_code=%d, reason=%d", 4907 msg->op_code, ipa_ctx->stat_req_reason); 4908 } 4909 4910 qdf_mem_free(op_msg); 4911 } 4912 4913 /** 4914 * __wlan_ipa_uc_fw_op_event_handler - IPA uC FW OPvent handler 4915 * @data: uC OP work 4916 * 4917 * Return: None 4918 */ __wlan_ipa_uc_fw_op_event_handler(void * data)4919 static void __wlan_ipa_uc_fw_op_event_handler(void *data) 4920 { 4921 struct op_msg_type *msg; 4922 struct uc_op_work_struct *uc_op_work = 4923 (struct uc_op_work_struct *)data; 4924 struct wlan_ipa_priv *ipa_ctx = uc_op_work->ipa_priv_bp; 4925 4926 msg = uc_op_work->msg; 4927 uc_op_work->msg = NULL; 4928 ipa_debug("posted msg %d", msg->op_code); 4929 4930 wlan_ipa_uc_op_cb(msg, ipa_ctx); 4931 } 4932 4933 /** 4934 * wlan_ipa_uc_fw_op_event_handler - SSR wrapper for 4935 * __wlan_ipa_uc_fw_op_event_handler 4936 * @data: uC OP work 4937 * 4938 * Return: None 4939 */ wlan_ipa_uc_fw_op_event_handler(void * data)4940 static void wlan_ipa_uc_fw_op_event_handler(void *data) 4941 { 4942 if (qdf_is_recovering()) { 4943 ipa_err("in recovering"); 4944 return; 4945 } 4946 4947 __wlan_ipa_uc_fw_op_event_handler(data); 4948 } 4949 4950 /** 4951 * wlan_ipa_uc_op_event_handler() - IPA UC OP event handler 4952 * @op_msg: operation message received from firmware 4953 * @ctx: Global IPA context 4954 * 4955 * Return: None 4956 */ wlan_ipa_uc_op_event_handler(uint8_t * op_msg,void * ctx)4957 static void wlan_ipa_uc_op_event_handler(uint8_t *op_msg, void *ctx) 4958 { 4959 struct wlan_ipa_priv *ipa_ctx = (struct wlan_ipa_priv *)ctx; 4960 struct op_msg_type *msg; 4961 struct uc_op_work_struct *uc_op_work; 4962 4963 if (!ipa_ctx) 4964 goto end; 4965 4966 msg = (struct op_msg_type *)op_msg; 4967 4968 if (msg->op_code >= WLAN_IPA_UC_OPCODE_MAX) { 4969 ipa_err("Invalid OP Code (%d)", msg->op_code); 4970 goto end; 4971 } 4972 4973 uc_op_work = &ipa_ctx->uc_op_work[msg->op_code]; 4974 if (uc_op_work->msg) { 4975 /* When the same uC OPCODE is already pended, just return */ 4976 goto end; 4977 } 4978 4979 uc_op_work->msg = msg; 4980 qdf_sched_work(0, &uc_op_work->work); 4981 return; 4982 4983 end: 4984 qdf_mem_free(op_msg); 4985 } 4986 wlan_ipa_uc_ol_init(struct wlan_ipa_priv * ipa_ctx,qdf_device_t osdev)4987 QDF_STATUS wlan_ipa_uc_ol_init(struct wlan_ipa_priv *ipa_ctx, 4988 qdf_device_t osdev) 4989 { 4990 uint8_t i; 4991 QDF_STATUS status = QDF_STATUS_SUCCESS; 4992 4993 if (!wlan_ipa_uc_is_enabled(ipa_ctx->config)) 4994 return QDF_STATUS_SUCCESS; 4995 4996 ipa_debug("enter"); 4997 4998 if (!osdev) { 4999 ipa_err("osdev null"); 5000 status = QDF_STATUS_E_FAILURE; 5001 goto fail_return; 5002 } 5003 5004 for (i = 0; i < WLAN_IPA_MAX_SESSION; i++) { 5005 ipa_ctx->vdev_to_iface[i] = WLAN_IPA_MAX_SESSION; 5006 ipa_ctx->vdev_offload_enabled[i] = false; 5007 ipa_ctx->disable_intrabss_fwd[i] = false; 5008 } 5009 5010 if (cdp_ipa_get_resource(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id)) { 5011 ipa_err("IPA UC resource alloc fail"); 5012 status = QDF_STATUS_E_FAILURE; 5013 goto fail_return; 5014 } 5015 5016 for (i = 0; i < WLAN_IPA_UC_OPCODE_MAX; i++) { 5017 ipa_ctx->uc_op_work[i].osdev = osdev; 5018 ipa_ctx->uc_op_work[i].msg = NULL; 5019 ipa_ctx->uc_op_work[i].ipa_priv_bp = ipa_ctx; 5020 qdf_create_work(0, &ipa_ctx->uc_op_work[i].work, 5021 wlan_ipa_uc_fw_op_event_handler, 5022 &ipa_ctx->uc_op_work[i]); 5023 } 5024 5025 if (true == ipa_ctx->uc_loaded) { 5026 status = wlan_ipa_wdi_setup(ipa_ctx, osdev); 5027 if (status) { 5028 ipa_err("Failure to setup IPA pipes (status=%d)", 5029 status); 5030 status = QDF_STATUS_E_FAILURE; 5031 5032 if (wlan_ipa_uc_sta_is_enabled(ipa_ctx->config)) { 5033 qdf_cancel_work(&ipa_ctx->mcc_work); 5034 wlan_ipa_teardown_sys_pipe(ipa_ctx); 5035 } 5036 ipa_ctx->uc_loaded = false; 5037 5038 goto fail_return; 5039 } 5040 5041 /* Setup the Tx buffer SMMU mappings */ 5042 status = cdp_ipa_tx_buf_smmu_mapping(ipa_ctx->dp_soc, 5043 ipa_ctx->dp_pdev_id, 5044 __func__, __LINE__); 5045 if (status) { 5046 ipa_err("Failure to map Tx buffers for IPA(status=%d)", 5047 status); 5048 return status; 5049 } 5050 ipa_info("TX buffers mapped to IPA"); 5051 cdp_ipa_set_doorbell_paddr(ipa_ctx->dp_soc, 5052 ipa_ctx->dp_pdev_id); 5053 wlan_ipa_init_metering(ipa_ctx); 5054 wlan_ipa_add_rem_flt_cb_event(ipa_ctx); 5055 if (wlan_ipa_init_perf_level(ipa_ctx) != QDF_STATUS_SUCCESS) 5056 ipa_err("Failed to init perf level"); 5057 } 5058 5059 cdp_ipa_register_op_cb(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id, 5060 wlan_ipa_uc_op_event_handler, (void *)ipa_ctx); 5061 fail_return: 5062 ipa_debug("exit: status=%d", status); 5063 return status; 5064 } 5065 5066 /** 5067 * wlan_ipa_cleanup_pending_event() - Cleanup IPA pending event list 5068 * @ipa_ctx: pointer to IPA IPA struct 5069 * 5070 * Return: none 5071 */ wlan_ipa_cleanup_pending_event(struct wlan_ipa_priv * ipa_ctx)5072 static void wlan_ipa_cleanup_pending_event(struct wlan_ipa_priv *ipa_ctx) 5073 { 5074 struct wlan_ipa_uc_pending_event *pending_event = NULL; 5075 5076 while (qdf_list_remove_front(&ipa_ctx->pending_event, 5077 (qdf_list_node_t **)&pending_event) == QDF_STATUS_SUCCESS) 5078 qdf_mem_free(pending_event); 5079 } 5080 wlan_ipa_uc_ol_deinit(struct wlan_ipa_priv * ipa_ctx)5081 QDF_STATUS wlan_ipa_uc_ol_deinit(struct wlan_ipa_priv *ipa_ctx) 5082 { 5083 QDF_STATUS status = QDF_STATUS_SUCCESS; 5084 int i; 5085 5086 ipa_debug("enter"); 5087 5088 if (!wlan_ipa_uc_is_enabled(ipa_ctx->config)) 5089 return status; 5090 5091 wlan_ipa_uc_disable_pipes(ipa_ctx, true); 5092 5093 cdp_ipa_deregister_op_cb(ipa_ctx->dp_soc, ipa_ctx->dp_pdev_id); 5094 qdf_atomic_set(&ipa_ctx->deinit_in_prog, 1); 5095 5096 for (i = 0; i < WLAN_IPA_UC_OPCODE_MAX; i++) { 5097 qdf_cancel_work(&ipa_ctx->uc_op_work[i].work); 5098 qdf_mem_free(ipa_ctx->uc_op_work[i].msg); 5099 ipa_ctx->uc_op_work[i].msg = NULL; 5100 } 5101 5102 cdp_ipa_iounmap_doorbell_vaddr(ipa_ctx->dp_soc, 5103 ipa_ctx->dp_pdev_id); 5104 5105 if (true == ipa_ctx->uc_loaded) { 5106 status = cdp_ipa_tx_buf_smmu_unmapping(ipa_ctx->dp_soc, 5107 ipa_ctx->dp_pdev_id, 5108 __func__, __LINE__); 5109 if (status) 5110 ipa_err("Failure to unmap IPA Tx buffers (status=%d)", 5111 status); 5112 else 5113 ipa_info("TX buffers unmapped from IPA"); 5114 status = cdp_ipa_cleanup(ipa_ctx->dp_soc, 5115 ipa_ctx->dp_pdev_id, 5116 ipa_ctx->tx_pipe_handle, 5117 ipa_ctx->rx_pipe_handle, ipa_ctx->hdl); 5118 if (status) 5119 ipa_err("Failure to cleanup IPA pipes (status=%d)", 5120 status); 5121 } 5122 5123 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 5124 wlan_ipa_cleanup_pending_event(ipa_ctx); 5125 qdf_mutex_release(&ipa_ctx->ipa_lock); 5126 5127 ipa_debug("exit: ret=%d", status); 5128 return status; 5129 } 5130 5131 /** 5132 * wlan_ipa_uc_send_evt() - send event to ipa 5133 * @net_dev: Interface net device 5134 * @type: event type 5135 * @mac_addr: pointer to mac address 5136 * @ipa_priv: IPA private context 5137 * 5138 * Send event to IPA driver 5139 * 5140 * Return: QDF_STATUS 5141 */ wlan_ipa_uc_send_evt(qdf_netdev_t net_dev,qdf_ipa_wlan_event type,uint8_t * mac_addr,struct wlan_ipa_priv * ipa_priv)5142 static QDF_STATUS wlan_ipa_uc_send_evt(qdf_netdev_t net_dev, 5143 qdf_ipa_wlan_event type, 5144 uint8_t *mac_addr, 5145 struct wlan_ipa_priv *ipa_priv) 5146 { 5147 struct wlan_ipa_priv *ipa_ctx; 5148 qdf_ipa_msg_meta_t meta; 5149 qdf_ipa_wlan_msg_t *msg; 5150 5151 if (!ipa_priv) 5152 return QDF_STATUS_E_INVAL; 5153 5154 ipa_ctx = ipa_priv; 5155 5156 QDF_IPA_MSG_META_MSG_LEN(&meta) = sizeof(qdf_ipa_wlan_msg_t); 5157 msg = qdf_mem_malloc(QDF_IPA_MSG_META_MSG_LEN(&meta)); 5158 if (!msg) 5159 return QDF_STATUS_E_NOMEM; 5160 5161 QDF_IPA_SET_META_MSG_TYPE(&meta, type); 5162 qdf_str_lcopy(QDF_IPA_WLAN_MSG_NAME(msg), net_dev->name, 5163 IPA_RESOURCE_NAME_MAX); 5164 qdf_mem_copy(QDF_IPA_WLAN_MSG_MAC_ADDR(msg), mac_addr, QDF_NET_ETH_LEN); 5165 QDF_IPA_WLAN_MSG_NETDEV_IF_ID(msg) = net_dev->ifindex; 5166 5167 if (qdf_ipa_send_msg(&meta, msg, wlan_ipa_msg_free_fn)) { 5168 ipa_err("%s: Evt: %d fail", 5169 QDF_IPA_WLAN_MSG_NAME(msg), 5170 QDF_IPA_MSG_META_MSG_TYPE(&meta)); 5171 qdf_mem_free(msg); 5172 5173 return QDF_STATUS_E_FAILURE; 5174 } 5175 5176 ipa_ctx->stats.num_send_msg++; 5177 5178 return QDF_STATUS_SUCCESS; 5179 } 5180 wlan_ipa_uc_cleanup_sta(struct wlan_ipa_priv * ipa_ctx,qdf_netdev_t net_dev,uint8_t session_id)5181 void wlan_ipa_uc_cleanup_sta(struct wlan_ipa_priv *ipa_ctx, 5182 qdf_netdev_t net_dev, uint8_t session_id) 5183 { 5184 struct wlan_ipa_iface_context *iface_ctx; 5185 int i; 5186 5187 ipa_debug("enter"); 5188 5189 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 5190 iface_ctx = &ipa_ctx->iface_context[i]; 5191 if (iface_ctx && iface_ctx->device_mode == QDF_STA_MODE && 5192 wlan_ipa_check_iface_netdev_sessid(iface_ctx, net_dev, 5193 session_id)) { 5194 wlan_ipa_uc_send_evt(net_dev, QDF_IPA_STA_DISCONNECT, 5195 (uint8_t *)net_dev->dev_addr, 5196 ipa_ctx); 5197 wlan_ipa_cleanup_iface(iface_ctx, NULL); 5198 } 5199 } 5200 5201 ipa_debug("exit"); 5202 } 5203 wlan_ipa_uc_disconnect_ap(struct wlan_ipa_priv * ipa_ctx,qdf_netdev_t net_dev)5204 QDF_STATUS wlan_ipa_uc_disconnect_ap(struct wlan_ipa_priv *ipa_ctx, 5205 qdf_netdev_t net_dev) 5206 { 5207 struct wlan_ipa_iface_context *iface_ctx; 5208 QDF_STATUS status; 5209 5210 ipa_debug("enter"); 5211 5212 iface_ctx = wlan_ipa_get_iface(ipa_ctx, QDF_SAP_MODE); 5213 if (iface_ctx) 5214 status = wlan_ipa_uc_send_evt(net_dev, QDF_IPA_AP_DISCONNECT, 5215 (uint8_t *)net_dev->dev_addr, 5216 ipa_ctx); 5217 else 5218 return QDF_STATUS_E_INVAL; 5219 5220 ipa_debug("exit :%d", status); 5221 5222 return status; 5223 } 5224 wlan_ipa_cleanup_dev_iface(struct wlan_ipa_priv * ipa_ctx,qdf_netdev_t net_dev,uint8_t session_id)5225 void wlan_ipa_cleanup_dev_iface(struct wlan_ipa_priv *ipa_ctx, 5226 qdf_netdev_t net_dev, uint8_t session_id) 5227 { 5228 struct wlan_ipa_iface_context *iface_ctx; 5229 int i; 5230 5231 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 5232 iface_ctx = &ipa_ctx->iface_context[i]; 5233 if (wlan_ipa_check_iface_netdev_sessid(iface_ctx, net_dev, 5234 session_id)) { 5235 wlan_ipa_cleanup_iface(iface_ctx, NULL); 5236 break; 5237 } 5238 } 5239 } 5240 wlan_ipa_uc_ssr_cleanup(struct wlan_ipa_priv * ipa_ctx)5241 void wlan_ipa_uc_ssr_cleanup(struct wlan_ipa_priv *ipa_ctx) 5242 { 5243 struct wlan_ipa_iface_context *iface; 5244 int i; 5245 5246 ipa_info("enter"); 5247 5248 for (i = 0; i < WLAN_IPA_MAX_IFACE; i++) { 5249 iface = &ipa_ctx->iface_context[i]; 5250 if (iface->dev) { 5251 if (iface->device_mode == QDF_SAP_MODE) 5252 wlan_ipa_uc_send_evt(iface->dev, 5253 QDF_IPA_AP_DISCONNECT, 5254 (uint8_t *)iface->dev->dev_addr, 5255 ipa_ctx); 5256 else if (iface->device_mode == QDF_STA_MODE) 5257 wlan_ipa_uc_send_evt(iface->dev, 5258 QDF_IPA_STA_DISCONNECT, 5259 (uint8_t *)iface->dev->dev_addr, 5260 ipa_ctx); 5261 wlan_ipa_cleanup_iface(iface, NULL); 5262 } 5263 } 5264 } 5265 wlan_ipa_fw_rejuvenate_send_msg(struct wlan_ipa_priv * ipa_ctx)5266 void wlan_ipa_fw_rejuvenate_send_msg(struct wlan_ipa_priv *ipa_ctx) 5267 { 5268 qdf_ipa_msg_meta_t meta; 5269 qdf_ipa_wlan_msg_t *msg; 5270 int ret; 5271 5272 meta.msg_len = sizeof(*msg); 5273 msg = qdf_mem_malloc(meta.msg_len); 5274 if (!msg) 5275 return; 5276 5277 QDF_IPA_SET_META_MSG_TYPE(&meta, QDF_FWR_SSR_BEFORE_SHUTDOWN); 5278 ipa_debug("ipa_send_msg(Evt:%d)", 5279 meta.msg_type); 5280 ret = qdf_ipa_send_msg(&meta, msg, wlan_ipa_msg_free_fn); 5281 5282 if (ret) { 5283 ipa_err("ipa_send_msg(Evt:%d)-fail=%d", 5284 meta.msg_type, ret); 5285 qdf_mem_free(msg); 5286 } 5287 ipa_ctx->stats.num_send_msg++; 5288 } 5289 wlan_ipa_flush_pending_vdev_events(struct wlan_ipa_priv * ipa_ctx,uint8_t vdev_id)5290 void wlan_ipa_flush_pending_vdev_events(struct wlan_ipa_priv *ipa_ctx, 5291 uint8_t vdev_id) 5292 { 5293 struct wlan_ipa_uc_pending_event *event; 5294 struct wlan_ipa_uc_pending_event *next_event; 5295 5296 qdf_mutex_acquire(&ipa_ctx->ipa_lock); 5297 5298 qdf_list_for_each_del(&ipa_ctx->pending_event, event, next_event, 5299 node) { 5300 if (event->session_id == vdev_id) { 5301 qdf_list_remove_node(&ipa_ctx->pending_event, 5302 &event->node); 5303 qdf_mem_free(event); 5304 } 5305 } 5306 5307 qdf_mutex_release(&ipa_ctx->ipa_lock); 5308 } 5309 5310 #ifdef IPA_OPT_WIFI_DP wlan_ipa_wdi_opt_dpath_notify_flt_rsvd(bool response)5311 void wlan_ipa_wdi_opt_dpath_notify_flt_rsvd(bool response) 5312 { 5313 struct wlan_ipa_priv *ipa_ctx = gp_ipa; 5314 struct op_msg_type *smmu_msg; 5315 struct op_msg_type *notify_msg; 5316 struct uc_op_work_struct *uc_op_work; 5317 5318 smmu_msg = qdf_mem_malloc(sizeof(*smmu_msg)); 5319 if (!smmu_msg) 5320 return; 5321 5322 if (response) { 5323 smmu_msg->op_code = WLAN_IPA_SMMU_MAP; 5324 uc_op_work = &ipa_ctx->uc_op_work[WLAN_IPA_SMMU_MAP]; 5325 uc_op_work->msg = smmu_msg; 5326 cdp_ipa_set_smmu_mapped(ipa_ctx->dp_soc, 1); 5327 qdf_sched_work(0, &uc_op_work->work); 5328 } 5329 5330 notify_msg = qdf_mem_malloc(sizeof(*notify_msg)); 5331 if (!notify_msg) 5332 return; 5333 5334 notify_msg->op_code = WLAN_IPA_FILTER_RSV_NOTIFY; 5335 notify_msg->rsvd = response; 5336 uc_op_work = &ipa_ctx->uc_op_work[WLAN_IPA_FILTER_RSV_NOTIFY]; 5337 uc_op_work->msg = notify_msg; 5338 qdf_sched_work(0, &uc_op_work->work); 5339 } 5340 wlan_ipa_wdi_opt_dpath_flt_rsrv_cb(void * ipa_ctx,struct ipa_wdi_opt_dpath_flt_rsrv_cb_params * out_params)5341 int wlan_ipa_wdi_opt_dpath_flt_rsrv_cb( 5342 void *ipa_ctx, 5343 struct ipa_wdi_opt_dpath_flt_rsrv_cb_params *out_params) 5344 { 5345 struct wifi_dp_flt_setup *dp_flt_params = NULL; 5346 struct wlan_ipa_priv *ipa_obj = (struct wlan_ipa_priv *)ipa_ctx; 5347 int i, pdev_id, param_val; 5348 struct wlan_objmgr_pdev *pdev; 5349 struct wlan_objmgr_psoc *psoc; 5350 wmi_unified_t wmi_handle; 5351 int response = 0; 5352 int wait_cnt = 0; 5353 5354 if (ipa_obj->ipa_pipes_down || ipa_obj->pipes_down_in_progress) { 5355 ipa_err("Pipes are going down. Reject flt rsrv request"); 5356 return QDF_STATUS_FILT_REQ_ERROR; 5357 } 5358 5359 pdev = ipa_obj->pdev; 5360 pdev_id = ipa_obj->dp_pdev_id; 5361 psoc = wlan_pdev_get_psoc(pdev); 5362 wmi_handle = get_wmi_unified_hdl_from_psoc(psoc); 5363 if (!wmi_handle) { 5364 ipa_err("Unable to get wmi handle"); 5365 return QDF_STATUS_FILT_REQ_ERROR; 5366 } 5367 5368 /* Hold wakelock */ 5369 qdf_wake_lock_acquire(&ipa_obj->opt_dp_wake_lock, 5370 WIFI_POWER_EVENT_WAKELOCK_OPT_WIFI_DP); 5371 ipa_debug("opt_dp: Wakelock acquired"); 5372 qdf_pm_system_wakeup(); 5373 5374 response = cdp_ipa_pcie_link_up(ipa_obj->dp_soc); 5375 if (response) { 5376 ipa_err("opt_dp: Pcie link up fail %d", response); 5377 goto error_pcie_link_up; 5378 } 5379 5380 ipa_debug("opt_dp :Target suspend state %d", 5381 qdf_atomic_read(&wmi_handle->is_target_suspended)); 5382 while (qdf_atomic_read(&wmi_handle->is_target_suspended) && 5383 wait_cnt < OPT_DP_TARGET_RESUME_WAIT_COUNT) { 5384 qdf_sleep(OPT_DP_TARGET_RESUME_WAIT_TIMEOUT_MS); 5385 wait_cnt++; 5386 } 5387 5388 if (qdf_atomic_read(&wmi_handle->is_target_suspended)) { 5389 ipa_err("Wifi is suspended. Reject request"); 5390 goto error; 5391 } 5392 5393 /* Disable Low power features before filter reservation */ 5394 ipa_debug("opt_dp: Disable low power features to reserve filter"); 5395 param_val = 0; 5396 response = cdp_ipa_opt_dp_enable_disable_low_power_mode(pdev, pdev_id, 5397 param_val); 5398 if (response) { 5399 ipa_err("Low power feature disable failed. status %d", 5400 response); 5401 goto error; 5402 } 5403 5404 ipa_debug("opt_dp: Send filter reserve req"); 5405 dp_flt_params = &(ipa_obj->dp_cce_super_rule_flt_param); 5406 dp_flt_params->op = HTT_RX_CCE_SUPER_RULE_SETUP_REQUEST; 5407 dp_flt_params->pdev_id = ipa_obj->dp_pdev_id; 5408 for (i = 0; i < IPA_WDI_MAX_FILTER; i++) { 5409 dp_flt_params->flt_addr_params[i].ipa_flt_evnt_required = 0; 5410 dp_flt_params->flt_addr_params[i].ipa_flt_in_use = false; 5411 } 5412 return cdp_ipa_rx_cce_super_rule_setup(ipa_obj->dp_soc, dp_flt_params); 5413 5414 error: 5415 cdp_ipa_pcie_link_down(ipa_obj->dp_soc); 5416 error_pcie_link_up: 5417 qdf_wake_lock_release(&ipa_obj->opt_dp_wake_lock, 5418 WIFI_POWER_EVENT_WAKELOCK_OPT_WIFI_DP); 5419 return QDF_STATUS_FILT_REQ_ERROR; 5420 } 5421 wlan_ipa_wdi_opt_dpath_flt_add_cb(void * ipa_ctx,struct ipa_wdi_opt_dpath_flt_add_cb_params * in_out)5422 int wlan_ipa_wdi_opt_dpath_flt_add_cb( 5423 void *ipa_ctx, 5424 struct ipa_wdi_opt_dpath_flt_add_cb_params *in_out) 5425 { 5426 struct ipa_wdi_opt_dpath_flt_add_cb_params *ipa_flt = 5427 (struct ipa_wdi_opt_dpath_flt_add_cb_params *)(in_out); 5428 struct wlan_ipa_priv *ipa_obj = (struct wlan_ipa_priv *)ipa_ctx; 5429 int i, j, flt, response = 0; 5430 uint8_t num_flts; 5431 uint32_t src_ip_addr, dst_ip_addr; 5432 uint32_t *host_ipv6; 5433 struct wlan_objmgr_pdev *pdev; 5434 struct wlan_objmgr_psoc *psoc; 5435 struct wifi_dp_flt_setup *dp_flt_param = NULL; 5436 void *htc_handle; 5437 5438 if (ipa_obj->ipa_pipes_down || ipa_obj->pipes_down_in_progress) { 5439 ipa_err("Pipes are going down. Reject flt add request"); 5440 return QDF_STATUS_FILT_REQ_ERROR; 5441 } 5442 5443 pdev = ipa_obj->pdev; 5444 psoc = wlan_pdev_get_psoc(pdev); 5445 num_flts = ipa_flt->num_tuples; 5446 htc_handle = lmac_get_htc_hdl(psoc); 5447 if (!htc_handle) { 5448 ipa_err("HTC Handle is null"); 5449 return QDF_STATUS_FILT_REQ_ERROR; 5450 } 5451 5452 dp_flt_param = &(ipa_obj->dp_cce_super_rule_flt_param); 5453 5454 if (num_flts > IPA_WDI_MAX_FILTER) { 5455 ipa_err("Wrong IPA flt count %d", num_flts); 5456 return QDF_STATUS_FILT_REQ_ERROR; 5457 } 5458 5459 for (flt = 0; flt < num_flts; flt++) { 5460 for (i = 0; i < IPA_WDI_MAX_FILTER; i++) 5461 if (!dp_flt_param->flt_addr_params[i].ipa_flt_in_use) 5462 break; 5463 5464 if (i >= IPA_WDI_MAX_FILTER) { 5465 ipa_err("Wrong IPA flt count %d, i=%d", num_flts, i); 5466 return QDF_STATUS_FILT_REQ_ERROR; 5467 } 5468 5469 ipa_flt->flt_info[flt].out_hdl = (WLAN_HDL_FILTER1 + i); 5470 dp_flt_param->flt_addr_params[i].valid = 1; 5471 dp_flt_param->flt_addr_params[i].flt_hdl = 5472 ipa_flt->flt_info[flt].out_hdl; 5473 dp_flt_param->flt_addr_params[i].ipa_flt_evnt_required = 1; 5474 dp_flt_param->flt_addr_params[i].ipa_flt_in_use = true; 5475 5476 if (ipa_flt->flt_info[flt].version == 0) { 5477 dp_flt_param->flt_addr_params[i].l3_type = IPV4; 5478 } else if (ipa_flt->flt_info[flt].version == 1) { 5479 dp_flt_param->flt_addr_params[i].l3_type = IPV6; 5480 } else { 5481 ipa_err("Wrong IPA version %d", 5482 ipa_flt->flt_info[flt].version); 5483 return QDF_STATUS_FILT_REQ_ERROR; 5484 } 5485 5486 if (dp_flt_param->flt_addr_params[i].l3_type == IPV4) { 5487 src_ip_addr = qdf_ntohl(ipa_flt->flt_info[flt]. 5488 ipv4_addr.ipv4_saddr); 5489 dst_ip_addr = qdf_ntohl(ipa_flt->flt_info[flt]. 5490 ipv4_addr.ipv4_daddr); 5491 qdf_mem_copy( 5492 dp_flt_param->flt_addr_params[i].src_ipv4_addr, 5493 (&src_ip_addr), 5494 IPV4BYTES); 5495 qdf_mem_copy( 5496 dp_flt_param->flt_addr_params[i].dst_ipv4_addr, 5497 (&dst_ip_addr), 5498 IPV4BYTES); 5499 ipa_debug("ipv4 sent to FW 0x%x", src_ip_addr); 5500 } else if (dp_flt_param->flt_addr_params[i].l3_type == IPV6) { 5501 host_ipv6 = (uint32_t *)dp_flt_param->flt_addr_params[i]. 5502 src_ipv6_addr; 5503 5504 for (j = 0; j < IPV6ARRAY; j++) { 5505 src_ip_addr = qdf_ntohl(ipa_flt->flt_info[flt]. 5506 ipv6_addr.ipv6_saddr[j]); 5507 qdf_mem_copy(host_ipv6, 5508 &src_ip_addr, 5509 IPV6ARRAY); 5510 host_ipv6++; 5511 } 5512 for (j = 0; j < IPV6ARRAY; j++) { 5513 ipa_debug("ipv6 src addr rxed from ipa 0x%x", 5514 ipa_flt->flt_info[flt].ipv6_addr. 5515 ipv6_saddr[j]); 5516 } 5517 for (j = 0; j < IPV6ARRAY; j++) 5518 ipa_debug("ipv6 sent to FW 0x%x", 5519 *((uint32_t *)dp_flt_param->flt_addr_params[i]. 5520 src_ipv6_addr + j)); 5521 /* Dest addr is currently not used in filter */ 5522 } 5523 } 5524 5525 dp_flt_param->op = HTT_RX_CCE_SUPER_RULE_INSTALL; 5526 dp_flt_param->pdev_id = ipa_obj->dp_pdev_id; 5527 dp_flt_param->num_filters = num_flts; 5528 qdf_event_reset(&ipa_obj->ipa_flt_evnt); 5529 5530 ipa_debug("opt_dp: op %d, pdev_id %d. num_flts %d", 5531 dp_flt_param->op, dp_flt_param->pdev_id, num_flts); 5532 5533 cdp_ipa_rx_cce_super_rule_setup(ipa_obj->dp_soc, dp_flt_param); 5534 5535 qdf_wait_single_event(&ipa_obj->ipa_flt_evnt, 5536 DP_MAX_SLEEP_TIME); 5537 5538 for (i = 0; i < num_flts; i++) 5539 dp_flt_param->flt_addr_params[i].ipa_flt_evnt_required = 0; 5540 5541 response = dp_flt_param->ipa_flt_evnt_response; 5542 if (response != QDF_STATUS_SUCCESS) { 5543 if (response == QDF_STATUS_E_TIMEOUT) 5544 qdf_err("TIMEOUT_OCCURS"); 5545 else 5546 qdf_err("Error on event wait for filter add cb"); 5547 } 5548 return response; 5549 } 5550 wlan_ipa_wdi_opt_dpath_flt_rem_cb(void * ipa_ctx,struct ipa_wdi_opt_dpath_flt_rem_cb_params * in)5551 int wlan_ipa_wdi_opt_dpath_flt_rem_cb( 5552 void *ipa_ctx, 5553 struct ipa_wdi_opt_dpath_flt_rem_cb_params *in) 5554 { 5555 struct ipa_wdi_opt_dpath_flt_rem_cb_params *rem_flt = 5556 (struct ipa_wdi_opt_dpath_flt_rem_cb_params *)(in); 5557 struct wifi_dp_flt_setup *dp_flt_params = NULL; 5558 struct wlan_ipa_priv *ipa_obj = (struct wlan_ipa_priv *)ipa_ctx; 5559 struct wlan_objmgr_pdev *pdev; 5560 struct wlan_objmgr_psoc *psoc; 5561 uint8_t num_flts; 5562 uint32_t i, j, response = 0; 5563 void *htc_handle; 5564 5565 pdev = ipa_obj->pdev; 5566 psoc = wlan_pdev_get_psoc(pdev); 5567 num_flts = rem_flt->num_tuples; 5568 5569 htc_handle = lmac_get_htc_hdl(psoc); 5570 if (!htc_handle) { 5571 ipa_err("HTC Handle is null"); 5572 return QDF_STATUS_FILT_REQ_ERROR; 5573 } 5574 5575 dp_flt_params = &(ipa_obj->dp_cce_super_rule_flt_param); 5576 for (i = 0; i < num_flts; i++) { 5577 for (j = 0; j < IPA_WDI_MAX_FILTER; j++) { 5578 if (rem_flt->hdl_info[i] == 5579 dp_flt_params->flt_addr_params[j].flt_hdl) { 5580 dp_flt_params->flt_addr_params[i].valid = 0; 5581 qdf_mem_zero(dp_flt_params->flt_addr_params[i]. 5582 src_ipv4_addr, 5583 IPV4BYTES); 5584 qdf_mem_zero(dp_flt_params->flt_addr_params[i]. 5585 src_ipv6_addr, 5586 IPV6BYTES); 5587 dp_flt_params->flt_addr_params[i]. 5588 ipa_flt_evnt_required = 1; 5589 dp_flt_params->flt_addr_params[i].ipa_flt_in_use 5590 = false; 5591 } 5592 } 5593 } 5594 dp_flt_params->op = HTT_RX_CCE_SUPER_RULE_INSTALL; 5595 dp_flt_params->pdev_id = ipa_obj->dp_pdev_id; 5596 dp_flt_params->num_filters = num_flts; 5597 qdf_event_reset(&ipa_obj->ipa_flt_evnt); 5598 5599 ipa_debug("opt_dp: op %d, pdev_id %d. num_flts %d", 5600 dp_flt_params->op, dp_flt_params->pdev_id, num_flts); 5601 5602 cdp_ipa_rx_cce_super_rule_setup(ipa_obj->dp_soc, dp_flt_params); 5603 5604 qdf_wait_single_event(&ipa_obj->ipa_flt_evnt, 5605 DP_MAX_SLEEP_TIME); 5606 5607 for (i = 0; i < num_flts; i++) 5608 dp_flt_params->flt_addr_params[i].ipa_flt_evnt_required = 0; 5609 5610 response = dp_flt_params->ipa_flt_evnt_response; 5611 if (response != QDF_STATUS_SUCCESS) { 5612 if (response == QDF_STATUS_E_TIMEOUT) 5613 qdf_err("TIMEOUT_OCCURS"); 5614 else 5615 qdf_err("Error on event wait for filter rem cb"); 5616 } 5617 return response; 5618 } 5619 wlan_ipa_wdi_opt_dpath_flt_rsrv_rel_cb(void * ipa_ctx)5620 int wlan_ipa_wdi_opt_dpath_flt_rsrv_rel_cb(void *ipa_ctx) 5621 { 5622 struct wifi_dp_flt_setup *dp_flt_params = NULL; 5623 struct wlan_ipa_priv *ipa_obj = (struct wlan_ipa_priv *)ipa_ctx; 5624 int i, param_val = 0; 5625 struct wlan_objmgr_pdev *pdev; 5626 int pdev_id; 5627 int response = 0; 5628 5629 pdev = ipa_obj->pdev; 5630 pdev_id = ipa_obj->dp_pdev_id; 5631 /* Enable Low power features before filter release */ 5632 ipa_debug("opt_dp: Enable low power features to release filter"); 5633 param_val = 1; 5634 response = cdp_ipa_opt_dp_enable_disable_low_power_mode(pdev, pdev_id, 5635 param_val); 5636 if (response) { 5637 ipa_err("Low power feature enable failed. status %d", response); 5638 } 5639 5640 response = cdp_ipa_pcie_link_down(ipa_obj->dp_soc); 5641 ipa_debug("opt_dp: Vote for PCIe link down"); 5642 5643 dp_flt_params = &(ipa_obj->dp_cce_super_rule_flt_param); 5644 for (i = 0; i < IPA_WDI_MAX_FILTER; i++) 5645 dp_flt_params->flt_addr_params[i].valid = 0; 5646 dp_flt_params->op = HTT_RX_CCE_SUPER_RULE_RELEASE; 5647 dp_flt_params->pdev_id = ipa_obj->dp_pdev_id; 5648 dp_flt_params->num_filters = IPA_WDI_MAX_FILTER; 5649 return cdp_ipa_rx_cce_super_rule_setup(ipa_obj->dp_soc, dp_flt_params); 5650 } 5651 wlan_ipa_wdi_opt_dpath_notify_flt_rlsd(int flt0_rslt,int flt1_rslt)5652 void wlan_ipa_wdi_opt_dpath_notify_flt_rlsd(int flt0_rslt, int flt1_rslt) 5653 { 5654 struct wifi_dp_flt_setup *dp_flt_params = NULL; 5655 struct wlan_ipa_priv *ipa_ctx = gp_ipa; 5656 struct wlan_objmgr_pdev *pdev; 5657 struct op_msg_type *smmu_msg; 5658 struct op_msg_type *notify_msg; 5659 struct uc_op_work_struct *uc_op_work; 5660 bool result = false; 5661 bool val = false; 5662 5663 pdev = ipa_ctx->pdev; 5664 dp_flt_params = &(ipa_ctx->dp_cce_super_rule_flt_param); 5665 5666 if ((dp_flt_params->flt_addr_params[0].ipa_flt_in_use == true && 5667 flt0_rslt == 0) || 5668 (dp_flt_params->flt_addr_params[1].ipa_flt_in_use == true && 5669 flt1_rslt == 0)) 5670 result = false; 5671 else { 5672 dp_flt_params->flt_addr_params[0].ipa_flt_in_use = false; 5673 dp_flt_params->flt_addr_params[1].ipa_flt_in_use = false; 5674 result = true; 5675 } 5676 5677 smmu_msg = qdf_mem_malloc(sizeof(*smmu_msg)); 5678 if (!smmu_msg) 5679 return; 5680 5681 val = cdp_ipa_get_smmu_mapped(ipa_ctx->dp_soc); 5682 if (val) { 5683 smmu_msg->op_code = WLAN_IPA_SMMU_UNMAP; 5684 uc_op_work = &ipa_ctx->uc_op_work[WLAN_IPA_SMMU_UNMAP]; 5685 uc_op_work->msg = smmu_msg; 5686 cdp_ipa_set_smmu_mapped(ipa_ctx->dp_soc, 0); 5687 qdf_sched_work(0, &uc_op_work->work); 5688 } else { 5689 ipa_err("IPA SMMU not mapped!!"); 5690 } 5691 5692 notify_msg = qdf_mem_malloc(sizeof(*notify_msg)); 5693 if (!notify_msg) 5694 return; 5695 5696 notify_msg->op_code = WLAN_IPA_FILTER_REL_NOTIFY; 5697 notify_msg->rsvd = result; 5698 uc_op_work = &ipa_ctx->uc_op_work[WLAN_IPA_FILTER_REL_NOTIFY]; 5699 uc_op_work->msg = notify_msg; 5700 qdf_sched_work(0, &uc_op_work->work); 5701 5702 qdf_wake_lock_release(&ipa_ctx->opt_dp_wake_lock, 5703 WIFI_POWER_EVENT_WAKELOCK_OPT_WIFI_DP); 5704 ipa_debug("opt_dp: Wakelock released"); 5705 } 5706 wlan_ipa_wdi_opt_dpath_notify_flt_add_rem_cb(int flt0_rslt,int flt1_rslt)5707 void wlan_ipa_wdi_opt_dpath_notify_flt_add_rem_cb(int flt0_rslt, int flt1_rslt) 5708 { 5709 struct wifi_dp_flt_setup *dp_flt_params = NULL; 5710 struct wlan_ipa_priv *ipa_obj = gp_ipa; 5711 5712 dp_flt_params = &(ipa_obj->dp_cce_super_rule_flt_param); 5713 5714 if ((dp_flt_params->flt_addr_params[0].ipa_flt_evnt_required == 1 && 5715 flt0_rslt == 0) || 5716 (dp_flt_params->flt_addr_params[1].ipa_flt_evnt_required == 1 && 5717 flt1_rslt == 0)) 5718 dp_flt_params->ipa_flt_evnt_response = 5719 QDF_STATUS_FILT_REQ_ERROR; 5720 else 5721 dp_flt_params->ipa_flt_evnt_response = 5722 QDF_STATUS_SUCCESS; 5723 ipa_debug("opt_dp: ipa_flt_event_response set status: %d", 5724 dp_flt_params->ipa_flt_evnt_response); 5725 qdf_event_set(&ipa_obj->ipa_flt_evnt); 5726 } 5727 #endif /* IPA_OPT_WIFI_DP */ 5728 5729 #ifdef IPA_WDI3_TX_TWO_PIPES wlan_ipa_get_alt_pipe(struct wlan_ipa_priv * ipa_ctx,uint8_t vdev_id,bool * alt_pipe)5730 QDF_STATUS wlan_ipa_get_alt_pipe(struct wlan_ipa_priv *ipa_ctx, 5731 uint8_t vdev_id, 5732 bool *alt_pipe) 5733 { 5734 struct wlan_ipa_iface_context *ctxt; 5735 uint8_t iface_id; 5736 5737 if (qdf_unlikely(!ipa_ctx || !alt_pipe)) 5738 return QDF_STATUS_E_INVAL; 5739 5740 iface_id = ipa_ctx->vdev_to_iface[vdev_id]; 5741 if (qdf_unlikely(iface_id >= WLAN_IPA_MAX_IFACE)) { 5742 ipa_err("Invalid iface_id %u from vdev_id %d", iface_id, 5743 vdev_id); 5744 return QDF_STATUS_E_INVAL; 5745 } 5746 5747 ctxt = &ipa_ctx->iface_context[iface_id]; 5748 if (qdf_unlikely(ctxt->session_id >= WLAN_IPA_MAX_SESSION)) { 5749 ipa_err("Invalid session_id %u from iface_id %d", 5750 ctxt->session_id, iface_id); 5751 return QDF_STATUS_E_INVAL; 5752 } 5753 5754 *alt_pipe = ctxt->alt_pipe; 5755 ipa_info("vdev_id %d alt_pipe %d", vdev_id, *alt_pipe); 5756 5757 return QDF_STATUS_SUCCESS; 5758 } 5759 #endif /* IPA_WDI3_TX_TWO_PIPES */ 5760 5761