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