1 /* 2 * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved. 3 * 4 * Permission to use, copy, modify, and/or distribute this software for 5 * any purpose with or without fee is hereby granted, provided that the 6 * above copyright notice and this permission notice appear in all 7 * copies. 8 * 9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL 10 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED 11 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE 12 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL 13 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 14 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER 15 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 16 * PERFORMANCE OF THIS SOFTWARE. 17 */ 18 #ifndef _HAL_GENERIC_API_H_ 19 #define _HAL_GENERIC_API_H_ 20 21 #include <hal_rx.h> 22 23 /** 24 * hal_tx_comp_get_status() - TQM Release reason 25 * @hal_desc: completion ring Tx status 26 * 27 * This function will parse the WBM completion descriptor and populate in 28 * HAL structure 29 * 30 * Return: none 31 */ 32 static inline 33 void hal_tx_comp_get_status_generic(void *desc, 34 void *ts1, 35 struct hal_soc *hal) 36 { 37 uint8_t rate_stats_valid = 0; 38 uint32_t rate_stats = 0; 39 struct hal_tx_completion_status *ts = 40 (struct hal_tx_completion_status *)ts1; 41 42 ts->ppdu_id = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_3, 43 TQM_STATUS_NUMBER); 44 ts->ack_frame_rssi = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_4, 45 ACK_FRAME_RSSI); 46 ts->first_msdu = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_4, FIRST_MSDU); 47 ts->last_msdu = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_4, LAST_MSDU); 48 ts->msdu_part_of_amsdu = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_4, 49 MSDU_PART_OF_AMSDU); 50 51 ts->peer_id = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_7, SW_PEER_ID); 52 ts->tid = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_7, TID); 53 ts->transmit_cnt = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_3, 54 TRANSMIT_COUNT); 55 56 rate_stats = HAL_TX_DESC_GET(desc, WBM_RELEASE_RING_5, 57 TX_RATE_STATS); 58 59 rate_stats_valid = HAL_TX_MS(TX_RATE_STATS_INFO_0, 60 TX_RATE_STATS_INFO_VALID, rate_stats); 61 62 ts->valid = rate_stats_valid; 63 64 if (rate_stats_valid) { 65 ts->bw = HAL_TX_MS(TX_RATE_STATS_INFO_0, TRANSMIT_BW, 66 rate_stats); 67 ts->pkt_type = HAL_TX_MS(TX_RATE_STATS_INFO_0, 68 TRANSMIT_PKT_TYPE, rate_stats); 69 ts->stbc = HAL_TX_MS(TX_RATE_STATS_INFO_0, 70 TRANSMIT_STBC, rate_stats); 71 ts->ldpc = HAL_TX_MS(TX_RATE_STATS_INFO_0, TRANSMIT_LDPC, 72 rate_stats); 73 ts->sgi = HAL_TX_MS(TX_RATE_STATS_INFO_0, TRANSMIT_SGI, 74 rate_stats); 75 ts->mcs = HAL_TX_MS(TX_RATE_STATS_INFO_0, TRANSMIT_MCS, 76 rate_stats); 77 ts->ofdma = HAL_TX_MS(TX_RATE_STATS_INFO_0, OFDMA_TRANSMISSION, 78 rate_stats); 79 ts->tones_in_ru = HAL_TX_MS(TX_RATE_STATS_INFO_0, TONES_IN_RU, 80 rate_stats); 81 } 82 83 ts->release_src = hal_tx_comp_get_buffer_source(desc); 84 ts->status = hal_tx_comp_get_release_reason( 85 desc, 86 hal_soc_to_hal_soc_handle(hal)); 87 88 ts->tsf = HAL_TX_DESC_GET(desc, UNIFIED_WBM_RELEASE_RING_6, 89 TX_RATE_STATS_INFO_TX_RATE_STATS); 90 } 91 92 /** 93 * hal_tx_desc_set_buf_addr - Fill Buffer Address information in Tx Descriptor 94 * @desc: Handle to Tx Descriptor 95 * @paddr: Physical Address 96 * @pool_id: Return Buffer Manager ID 97 * @desc_id: Descriptor ID 98 * @type: 0 - Address points to a MSDU buffer 99 * 1 - Address points to MSDU extension descriptor 100 * 101 * Return: void 102 */ 103 static inline void hal_tx_desc_set_buf_addr_generic(void *desc, 104 dma_addr_t paddr, uint8_t pool_id, 105 uint32_t desc_id, uint8_t type) 106 { 107 /* Set buffer_addr_info.buffer_addr_31_0 */ 108 HAL_SET_FLD(desc, UNIFIED_TCL_DATA_CMD_0, BUFFER_ADDR_INFO_BUF_ADDR_INFO) = 109 HAL_TX_SM(UNIFIED_BUFFER_ADDR_INFO_0, BUFFER_ADDR_31_0, paddr); 110 111 /* Set buffer_addr_info.buffer_addr_39_32 */ 112 HAL_SET_FLD(desc, UNIFIED_TCL_DATA_CMD_1, 113 BUFFER_ADDR_INFO_BUF_ADDR_INFO) |= 114 HAL_TX_SM(UNIFIED_BUFFER_ADDR_INFO_1, BUFFER_ADDR_39_32, 115 (((uint64_t) paddr) >> 32)); 116 117 /* Set buffer_addr_info.return_buffer_manager = pool id */ 118 HAL_SET_FLD(desc, UNIFIED_TCL_DATA_CMD_1, 119 BUFFER_ADDR_INFO_BUF_ADDR_INFO) |= 120 HAL_TX_SM(UNIFIED_BUFFER_ADDR_INFO_1, 121 RETURN_BUFFER_MANAGER, (pool_id + HAL_WBM_SW0_BM_ID)); 122 123 /* Set buffer_addr_info.sw_buffer_cookie = desc_id */ 124 HAL_SET_FLD(desc, UNIFIED_TCL_DATA_CMD_1, 125 BUFFER_ADDR_INFO_BUF_ADDR_INFO) |= 126 HAL_TX_SM(UNIFIED_BUFFER_ADDR_INFO_1, SW_BUFFER_COOKIE, desc_id); 127 128 /* Set Buffer or Ext Descriptor Type */ 129 HAL_SET_FLD(desc, UNIFIED_TCL_DATA_CMD_2, 130 BUF_OR_EXT_DESC_TYPE) |= 131 HAL_TX_SM(UNIFIED_TCL_DATA_CMD_2, BUF_OR_EXT_DESC_TYPE, type); 132 } 133 134 #if defined(QCA_WIFI_QCA6290_11AX_MU_UL) && defined(QCA_WIFI_QCA6290_11AX) 135 /** 136 * hal_rx_handle_other_tlvs() - handle special TLVs like MU_UL 137 * tlv_tag: Taf of the TLVs 138 * rx_tlv: the pointer to the TLVs 139 * @ppdu_info: pointer to ppdu_info 140 * 141 * Return: true if the tlv is handled, false if not 142 */ 143 static inline bool 144 hal_rx_handle_other_tlvs(uint32_t tlv_tag, void *rx_tlv, 145 struct hal_rx_ppdu_info *ppdu_info) 146 { 147 uint32_t value; 148 149 switch (tlv_tag) { 150 case WIFIPHYRX_HE_SIG_A_MU_UL_E: 151 { 152 uint8_t *he_sig_a_mu_ul_info = 153 (uint8_t *)rx_tlv + 154 HAL_RX_OFFSET(PHYRX_HE_SIG_A_MU_UL_0, 155 HE_SIG_A_MU_UL_INFO_PHYRX_HE_SIG_A_MU_UL_INFO_DETAILS); 156 ppdu_info->rx_status.he_flags = 1; 157 158 value = HAL_RX_GET(he_sig_a_mu_ul_info, HE_SIG_A_MU_UL_INFO_0, 159 FORMAT_INDICATION); 160 if (value == 0) { 161 ppdu_info->rx_status.he_data1 = 162 QDF_MON_STATUS_HE_TRIG_FORMAT_TYPE; 163 } else { 164 ppdu_info->rx_status.he_data1 = 165 QDF_MON_STATUS_HE_SU_FORMAT_TYPE; 166 } 167 168 /* data1 */ 169 ppdu_info->rx_status.he_data1 |= 170 QDF_MON_STATUS_HE_BSS_COLOR_KNOWN | 171 QDF_MON_STATUS_HE_DL_UL_KNOWN | 172 QDF_MON_STATUS_HE_DATA_BW_RU_KNOWN; 173 174 /* data2 */ 175 ppdu_info->rx_status.he_data2 |= 176 QDF_MON_STATUS_TXOP_KNOWN; 177 178 /*data3*/ 179 value = HAL_RX_GET(he_sig_a_mu_ul_info, 180 HE_SIG_A_MU_UL_INFO_0, BSS_COLOR_ID); 181 ppdu_info->rx_status.he_data3 = value; 182 /* 1 for UL and 0 for DL */ 183 value = 1; 184 value = value << QDF_MON_STATUS_DL_UL_SHIFT; 185 ppdu_info->rx_status.he_data3 |= value; 186 187 /*data4*/ 188 value = HAL_RX_GET(he_sig_a_mu_ul_info, HE_SIG_A_MU_UL_INFO_0, 189 SPATIAL_REUSE); 190 ppdu_info->rx_status.he_data4 = value; 191 192 /*data5*/ 193 value = HAL_RX_GET(he_sig_a_mu_ul_info, 194 HE_SIG_A_MU_UL_INFO_0, TRANSMIT_BW); 195 ppdu_info->rx_status.he_data5 = value; 196 ppdu_info->rx_status.bw = value; 197 198 /*data6*/ 199 value = HAL_RX_GET(he_sig_a_mu_ul_info, HE_SIG_A_MU_UL_INFO_1, 200 TXOP_DURATION); 201 value = value << QDF_MON_STATUS_TXOP_SHIFT; 202 ppdu_info->rx_status.he_data6 |= value; 203 return true; 204 } 205 default: 206 return false; 207 } 208 } 209 #else 210 static inline bool 211 hal_rx_handle_other_tlvs(uint32_t tlv_tag, void *rx_tlv, 212 struct hal_rx_ppdu_info *ppdu_info) 213 { 214 return false; 215 } 216 #endif /* QCA_WIFI_QCA6290_11AX_MU_UL && QCA_WIFI_QCA6290_11AX */ 217 218 #if defined(RX_PPDU_END_USER_STATS_1_OFDMA_INFO_VALID_OFFSET) && \ 219 defined(RX_PPDU_END_USER_STATS_22_SW_RESPONSE_REFERENCE_PTR_EXT_OFFSET) 220 221 static inline void 222 hal_rx_handle_mu_ul_info( 223 void *rx_tlv, 224 struct mon_rx_user_status *mon_rx_user_status) 225 { 226 mon_rx_user_status->mu_ul_user_v0_word0 = 227 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_11, 228 SW_RESPONSE_REFERENCE_PTR); 229 230 mon_rx_user_status->mu_ul_user_v0_word1 = 231 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_22, 232 SW_RESPONSE_REFERENCE_PTR_EXT); 233 } 234 235 static inline void 236 hal_rx_populate_byte_count(void *rx_tlv, void *ppduinfo, 237 struct mon_rx_user_status *mon_rx_user_status) 238 { 239 uint32_t mpdu_ok_byte_count; 240 uint32_t mpdu_err_byte_count; 241 242 mpdu_ok_byte_count = HAL_RX_GET(rx_tlv, 243 RX_PPDU_END_USER_STATS_17, 244 MPDU_OK_BYTE_COUNT); 245 mpdu_err_byte_count = HAL_RX_GET(rx_tlv, 246 RX_PPDU_END_USER_STATS_19, 247 MPDU_ERR_BYTE_COUNT); 248 249 mon_rx_user_status->mpdu_ok_byte_count = mpdu_ok_byte_count; 250 mon_rx_user_status->mpdu_err_byte_count = mpdu_err_byte_count; 251 } 252 #else 253 static inline void 254 hal_rx_handle_mu_ul_info(void *rx_tlv, 255 struct mon_rx_user_status *mon_rx_user_status) 256 { 257 } 258 259 static inline void 260 hal_rx_populate_byte_count(void *rx_tlv, void *ppduinfo, 261 struct mon_rx_user_status *mon_rx_user_status) 262 { 263 struct hal_rx_ppdu_info *ppdu_info = 264 (struct hal_rx_ppdu_info *)ppduinfo; 265 266 /* HKV1: doesn't support mpdu byte count */ 267 mon_rx_user_status->mpdu_ok_byte_count = ppdu_info->rx_status.ppdu_len; 268 mon_rx_user_status->mpdu_err_byte_count = 0; 269 } 270 #endif 271 272 static inline void 273 hal_rx_populate_mu_user_info(void *rx_tlv, void *ppduinfo, 274 struct mon_rx_user_status *mon_rx_user_status) 275 { 276 struct hal_rx_ppdu_info *ppdu_info = 277 (struct hal_rx_ppdu_info *)ppduinfo; 278 279 mon_rx_user_status->ast_index = ppdu_info->rx_status.ast_index; 280 mon_rx_user_status->tid = ppdu_info->rx_status.tid; 281 mon_rx_user_status->tcp_msdu_count = 282 ppdu_info->rx_status.tcp_msdu_count; 283 mon_rx_user_status->udp_msdu_count = 284 ppdu_info->rx_status.udp_msdu_count; 285 mon_rx_user_status->other_msdu_count = 286 ppdu_info->rx_status.other_msdu_count; 287 mon_rx_user_status->frame_control = ppdu_info->rx_status.frame_control; 288 mon_rx_user_status->frame_control_info_valid = 289 ppdu_info->rx_status.frame_control_info_valid; 290 mon_rx_user_status->data_sequence_control_info_valid = 291 ppdu_info->rx_status.data_sequence_control_info_valid; 292 mon_rx_user_status->first_data_seq_ctrl = 293 ppdu_info->rx_status.first_data_seq_ctrl; 294 mon_rx_user_status->preamble_type = ppdu_info->rx_status.preamble_type; 295 mon_rx_user_status->ht_flags = ppdu_info->rx_status.ht_flags; 296 mon_rx_user_status->rtap_flags = ppdu_info->rx_status.rtap_flags; 297 mon_rx_user_status->vht_flags = ppdu_info->rx_status.vht_flags; 298 mon_rx_user_status->he_flags = ppdu_info->rx_status.he_flags; 299 mon_rx_user_status->rs_flags = ppdu_info->rx_status.rs_flags; 300 301 mon_rx_user_status->mpdu_cnt_fcs_ok = 302 ppdu_info->com_info.mpdu_cnt_fcs_ok; 303 mon_rx_user_status->mpdu_cnt_fcs_err = 304 ppdu_info->com_info.mpdu_cnt_fcs_err; 305 qdf_mem_copy(&mon_rx_user_status->mpdu_fcs_ok_bitmap, 306 &ppdu_info->com_info.mpdu_fcs_ok_bitmap, 307 HAL_RX_NUM_WORDS_PER_PPDU_BITMAP * 308 sizeof(ppdu_info->com_info.mpdu_fcs_ok_bitmap[0])); 309 310 hal_rx_populate_byte_count(rx_tlv, ppdu_info, mon_rx_user_status); 311 } 312 313 #define HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(chain, word_1, word_2, \ 314 ppdu_info, rssi_info_tlv) \ 315 { \ 316 ppdu_info->rx_status.rssi_chain[chain][0] = \ 317 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_1,\ 318 RSSI_PRI20_CHAIN##chain); \ 319 ppdu_info->rx_status.rssi_chain[chain][1] = \ 320 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_1,\ 321 RSSI_EXT20_CHAIN##chain); \ 322 ppdu_info->rx_status.rssi_chain[chain][2] = \ 323 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_1,\ 324 RSSI_EXT40_LOW20_CHAIN##chain); \ 325 ppdu_info->rx_status.rssi_chain[chain][3] = \ 326 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_1,\ 327 RSSI_EXT40_HIGH20_CHAIN##chain); \ 328 ppdu_info->rx_status.rssi_chain[chain][4] = \ 329 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_2,\ 330 RSSI_EXT80_LOW20_CHAIN##chain); \ 331 ppdu_info->rx_status.rssi_chain[chain][5] = \ 332 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_2,\ 333 RSSI_EXT80_LOW_HIGH20_CHAIN##chain); \ 334 ppdu_info->rx_status.rssi_chain[chain][6] = \ 335 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_2,\ 336 RSSI_EXT80_HIGH_LOW20_CHAIN##chain); \ 337 ppdu_info->rx_status.rssi_chain[chain][7] = \ 338 HAL_RX_GET(rssi_info_tlv, RECEIVE_RSSI_INFO_##word_2,\ 339 RSSI_EXT80_HIGH20_CHAIN##chain); \ 340 } \ 341 342 #define HAL_RX_PPDU_UPDATE_RSSI(ppdu_info, rssi_info_tlv) \ 343 {HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(0, 0, 1, ppdu_info, rssi_info_tlv) \ 344 HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(1, 2, 3, ppdu_info, rssi_info_tlv) \ 345 HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(2, 4, 5, ppdu_info, rssi_info_tlv) \ 346 HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(3, 6, 7, ppdu_info, rssi_info_tlv) \ 347 HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(4, 8, 9, ppdu_info, rssi_info_tlv) \ 348 HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(5, 10, 11, ppdu_info, rssi_info_tlv) \ 349 HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(6, 12, 13, ppdu_info, rssi_info_tlv) \ 350 HAL_RX_UPDATE_RSSI_PER_CHAIN_BW(7, 14, 15, ppdu_info, rssi_info_tlv)} \ 351 352 static inline uint32_t 353 hal_rx_update_rssi_chain(struct hal_rx_ppdu_info *ppdu_info, 354 uint8_t *rssi_info_tlv) 355 { 356 HAL_RX_PPDU_UPDATE_RSSI(ppdu_info, rssi_info_tlv) 357 return 0; 358 } 359 360 /** 361 * hal_rx_status_get_tlv_info() - process receive info TLV 362 * @rx_tlv_hdr: pointer to TLV header 363 * @ppdu_info: pointer to ppdu_info 364 * 365 * Return: HAL_TLV_STATUS_PPDU_NOT_DONE or HAL_TLV_STATUS_PPDU_DONE from tlv 366 */ 367 static inline uint32_t 368 hal_rx_status_get_tlv_info_generic(void *rx_tlv_hdr, void *ppduinfo, 369 hal_soc_handle_t hal_soc_hdl, 370 qdf_nbuf_t nbuf) 371 { 372 struct hal_soc *hal = (struct hal_soc *)hal_soc_hdl; 373 uint32_t tlv_tag, user_id, tlv_len, value; 374 uint8_t group_id = 0; 375 uint8_t he_dcm = 0; 376 uint8_t he_stbc = 0; 377 uint16_t he_gi = 0; 378 uint16_t he_ltf = 0; 379 void *rx_tlv; 380 bool unhandled = false; 381 struct mon_rx_user_status *mon_rx_user_status; 382 struct hal_rx_ppdu_info *ppdu_info = 383 (struct hal_rx_ppdu_info *)ppduinfo; 384 385 tlv_tag = HAL_RX_GET_USER_TLV32_TYPE(rx_tlv_hdr); 386 user_id = HAL_RX_GET_USER_TLV32_USERID(rx_tlv_hdr); 387 tlv_len = HAL_RX_GET_USER_TLV32_LEN(rx_tlv_hdr); 388 389 rx_tlv = (uint8_t *)rx_tlv_hdr + HAL_RX_TLV32_HDR_SIZE; 390 391 qdf_trace_hex_dump(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 392 rx_tlv, tlv_len); 393 394 switch (tlv_tag) { 395 396 case WIFIRX_PPDU_START_E: 397 { 398 struct hal_rx_ppdu_common_info *com_info = &ppdu_info->com_info; 399 400 ppdu_info->com_info.ppdu_id = 401 HAL_RX_GET(rx_tlv, RX_PPDU_START_0, 402 PHY_PPDU_ID); 403 /* channel number is set in PHY meta data */ 404 ppdu_info->rx_status.chan_num = 405 HAL_RX_GET(rx_tlv, RX_PPDU_START_1, 406 SW_PHY_META_DATA); 407 ppdu_info->com_info.ppdu_timestamp = 408 HAL_RX_GET(rx_tlv, RX_PPDU_START_2, 409 PPDU_START_TIMESTAMP); 410 ppdu_info->rx_status.ppdu_timestamp = 411 ppdu_info->com_info.ppdu_timestamp; 412 ppdu_info->rx_state = HAL_RX_MON_PPDU_START; 413 414 /* If last ppdu_id doesn't match new ppdu_id, 415 * 1. reset mpdu_cnt 416 * 2. update last_ppdu_id with new 417 * 3. reset mpdu fcs bitmap 418 */ 419 if (com_info->ppdu_id != com_info->last_ppdu_id) { 420 com_info->mpdu_cnt = 0; 421 com_info->last_ppdu_id = 422 com_info->ppdu_id; 423 com_info->num_users = 0; 424 qdf_mem_zero(&com_info->mpdu_fcs_ok_bitmap, 425 HAL_RX_NUM_WORDS_PER_PPDU_BITMAP * 426 sizeof(com_info->mpdu_fcs_ok_bitmap[0])); 427 } 428 break; 429 } 430 431 case WIFIRX_PPDU_START_USER_INFO_E: 432 break; 433 434 case WIFIRX_PPDU_END_E: 435 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 436 "[%s][%d] ppdu_end_e len=%d", 437 __func__, __LINE__, tlv_len); 438 /* This is followed by sub-TLVs of PPDU_END */ 439 ppdu_info->rx_state = HAL_RX_MON_PPDU_END; 440 break; 441 442 case WIFIRXPCU_PPDU_END_INFO_E: 443 ppdu_info->rx_status.rx_antenna = 444 HAL_RX_GET(rx_tlv, RXPCU_PPDU_END_INFO_2, RX_ANTENNA); 445 ppdu_info->rx_status.tsft = 446 HAL_RX_GET(rx_tlv, RXPCU_PPDU_END_INFO_1, 447 WB_TIMESTAMP_UPPER_32); 448 ppdu_info->rx_status.tsft = (ppdu_info->rx_status.tsft << 32) | 449 HAL_RX_GET(rx_tlv, RXPCU_PPDU_END_INFO_0, 450 WB_TIMESTAMP_LOWER_32); 451 ppdu_info->rx_status.duration = 452 HAL_RX_GET(rx_tlv, UNIFIED_RXPCU_PPDU_END_INFO_8, 453 RX_PPDU_DURATION); 454 break; 455 456 /* 457 * WIFIRX_PPDU_END_USER_STATS_E comes for each user received. 458 * for MU, based on num users we see this tlv that many times. 459 */ 460 case WIFIRX_PPDU_END_USER_STATS_E: 461 { 462 unsigned long tid = 0; 463 uint16_t seq = 0; 464 465 ppdu_info->rx_status.ast_index = 466 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_4, 467 AST_INDEX); 468 469 tid = HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_12, 470 RECEIVED_QOS_DATA_TID_BITMAP); 471 ppdu_info->rx_status.tid = qdf_find_first_bit(&tid, sizeof(tid)*8); 472 473 if (ppdu_info->rx_status.tid == (sizeof(tid) * 8)) 474 ppdu_info->rx_status.tid = HAL_TID_INVALID; 475 476 ppdu_info->rx_status.tcp_msdu_count = 477 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_9, 478 TCP_MSDU_COUNT) + 479 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_10, 480 TCP_ACK_MSDU_COUNT); 481 ppdu_info->rx_status.udp_msdu_count = 482 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_9, 483 UDP_MSDU_COUNT); 484 ppdu_info->rx_status.other_msdu_count = 485 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_10, 486 OTHER_MSDU_COUNT); 487 488 if (ppdu_info->sw_frame_group_id 489 != HAL_MPDU_SW_FRAME_GROUP_NULL_DATA) { 490 ppdu_info->rx_status.frame_control_info_valid = 491 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_3, 492 FRAME_CONTROL_INFO_VALID); 493 494 if (ppdu_info->rx_status.frame_control_info_valid) 495 ppdu_info->rx_status.frame_control = 496 HAL_RX_GET(rx_tlv, 497 RX_PPDU_END_USER_STATS_4, 498 FRAME_CONTROL_FIELD); 499 } 500 501 ppdu_info->rx_status.data_sequence_control_info_valid = 502 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_3, 503 DATA_SEQUENCE_CONTROL_INFO_VALID); 504 505 seq = HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_5, 506 FIRST_DATA_SEQ_CTRL); 507 if (ppdu_info->rx_status.data_sequence_control_info_valid) 508 ppdu_info->rx_status.first_data_seq_ctrl = seq; 509 510 ppdu_info->rx_status.preamble_type = 511 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_3, 512 HT_CONTROL_FIELD_PKT_TYPE); 513 switch (ppdu_info->rx_status.preamble_type) { 514 case HAL_RX_PKT_TYPE_11N: 515 ppdu_info->rx_status.ht_flags = 1; 516 ppdu_info->rx_status.rtap_flags |= HT_SGI_PRESENT; 517 break; 518 case HAL_RX_PKT_TYPE_11AC: 519 ppdu_info->rx_status.vht_flags = 1; 520 break; 521 case HAL_RX_PKT_TYPE_11AX: 522 ppdu_info->rx_status.he_flags = 1; 523 break; 524 default: 525 break; 526 } 527 528 ppdu_info->com_info.mpdu_cnt_fcs_ok = 529 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_3, 530 MPDU_CNT_FCS_OK); 531 ppdu_info->com_info.mpdu_cnt_fcs_err = 532 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_2, 533 MPDU_CNT_FCS_ERR); 534 if ((ppdu_info->com_info.mpdu_cnt_fcs_ok | 535 ppdu_info->com_info.mpdu_cnt_fcs_err) > 1) 536 ppdu_info->rx_status.rs_flags |= IEEE80211_AMPDU_FLAG; 537 else 538 ppdu_info->rx_status.rs_flags &= 539 (~IEEE80211_AMPDU_FLAG); 540 541 ppdu_info->com_info.mpdu_fcs_ok_bitmap[0] = 542 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_7, 543 FCS_OK_BITMAP_31_0); 544 545 ppdu_info->com_info.mpdu_fcs_ok_bitmap[1] = 546 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_8, 547 FCS_OK_BITMAP_63_32); 548 549 if (user_id < HAL_MAX_UL_MU_USERS) { 550 mon_rx_user_status = 551 &ppdu_info->rx_user_status[user_id]; 552 553 hal_rx_handle_mu_ul_info(rx_tlv, mon_rx_user_status); 554 555 ppdu_info->com_info.num_users++; 556 557 hal_rx_populate_mu_user_info(rx_tlv, ppdu_info, 558 mon_rx_user_status); 559 } 560 break; 561 } 562 563 case WIFIRX_PPDU_END_USER_STATS_EXT_E: 564 ppdu_info->com_info.mpdu_fcs_ok_bitmap[2] = 565 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_EXT_1, 566 FCS_OK_BITMAP_95_64); 567 568 ppdu_info->com_info.mpdu_fcs_ok_bitmap[3] = 569 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_EXT_2, 570 FCS_OK_BITMAP_127_96); 571 572 ppdu_info->com_info.mpdu_fcs_ok_bitmap[4] = 573 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_EXT_3, 574 FCS_OK_BITMAP_159_128); 575 576 ppdu_info->com_info.mpdu_fcs_ok_bitmap[5] = 577 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_EXT_4, 578 FCS_OK_BITMAP_191_160); 579 580 ppdu_info->com_info.mpdu_fcs_ok_bitmap[6] = 581 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_EXT_5, 582 FCS_OK_BITMAP_223_192); 583 584 ppdu_info->com_info.mpdu_fcs_ok_bitmap[7] = 585 HAL_RX_GET(rx_tlv, RX_PPDU_END_USER_STATS_EXT_6, 586 FCS_OK_BITMAP_255_224); 587 break; 588 589 case WIFIRX_PPDU_END_STATUS_DONE_E: 590 return HAL_TLV_STATUS_PPDU_DONE; 591 592 case WIFIDUMMY_E: 593 return HAL_TLV_STATUS_BUF_DONE; 594 595 case WIFIPHYRX_HT_SIG_E: 596 { 597 uint8_t *ht_sig_info = (uint8_t *)rx_tlv + 598 HAL_RX_OFFSET(UNIFIED_PHYRX_HT_SIG_0, 599 HT_SIG_INFO_PHYRX_HT_SIG_INFO_DETAILS); 600 value = HAL_RX_GET(ht_sig_info, HT_SIG_INFO_1, 601 FEC_CODING); 602 ppdu_info->rx_status.ldpc = (value == HAL_SU_MU_CODING_LDPC) ? 603 1 : 0; 604 ppdu_info->rx_status.mcs = HAL_RX_GET(ht_sig_info, 605 HT_SIG_INFO_0, MCS); 606 ppdu_info->rx_status.ht_mcs = ppdu_info->rx_status.mcs; 607 ppdu_info->rx_status.bw = HAL_RX_GET(ht_sig_info, 608 HT_SIG_INFO_0, CBW); 609 ppdu_info->rx_status.sgi = HAL_RX_GET(ht_sig_info, 610 HT_SIG_INFO_1, SHORT_GI); 611 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_SU; 612 ppdu_info->rx_status.nss = ((ppdu_info->rx_status.mcs) >> 613 HT_SIG_SU_NSS_SHIFT) + 1; 614 ppdu_info->rx_status.mcs &= ((1 << HT_SIG_SU_NSS_SHIFT) - 1); 615 break; 616 } 617 618 case WIFIPHYRX_L_SIG_B_E: 619 { 620 uint8_t *l_sig_b_info = (uint8_t *)rx_tlv + 621 HAL_RX_OFFSET(UNIFIED_PHYRX_L_SIG_B_0, 622 L_SIG_B_INFO_PHYRX_L_SIG_B_INFO_DETAILS); 623 624 value = HAL_RX_GET(l_sig_b_info, L_SIG_B_INFO_0, RATE); 625 ppdu_info->rx_status.l_sig_b_info = *((uint32_t *)l_sig_b_info); 626 switch (value) { 627 case 1: 628 ppdu_info->rx_status.rate = HAL_11B_RATE_3MCS; 629 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS3; 630 break; 631 case 2: 632 ppdu_info->rx_status.rate = HAL_11B_RATE_2MCS; 633 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS2; 634 break; 635 case 3: 636 ppdu_info->rx_status.rate = HAL_11B_RATE_1MCS; 637 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS1; 638 break; 639 case 4: 640 ppdu_info->rx_status.rate = HAL_11B_RATE_0MCS; 641 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS0; 642 break; 643 case 5: 644 ppdu_info->rx_status.rate = HAL_11B_RATE_6MCS; 645 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS6; 646 break; 647 case 6: 648 ppdu_info->rx_status.rate = HAL_11B_RATE_5MCS; 649 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS5; 650 break; 651 case 7: 652 ppdu_info->rx_status.rate = HAL_11B_RATE_4MCS; 653 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS4; 654 break; 655 default: 656 break; 657 } 658 ppdu_info->rx_status.cck_flag = 1; 659 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_SU; 660 break; 661 } 662 663 case WIFIPHYRX_L_SIG_A_E: 664 { 665 uint8_t *l_sig_a_info = (uint8_t *)rx_tlv + 666 HAL_RX_OFFSET(UNIFIED_PHYRX_L_SIG_A_0, 667 L_SIG_A_INFO_PHYRX_L_SIG_A_INFO_DETAILS); 668 669 value = HAL_RX_GET(l_sig_a_info, L_SIG_A_INFO_0, RATE); 670 ppdu_info->rx_status.l_sig_a_info = *((uint32_t *)l_sig_a_info); 671 switch (value) { 672 case 8: 673 ppdu_info->rx_status.rate = HAL_11A_RATE_0MCS; 674 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS0; 675 break; 676 case 9: 677 ppdu_info->rx_status.rate = HAL_11A_RATE_1MCS; 678 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS1; 679 break; 680 case 10: 681 ppdu_info->rx_status.rate = HAL_11A_RATE_2MCS; 682 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS2; 683 break; 684 case 11: 685 ppdu_info->rx_status.rate = HAL_11A_RATE_3MCS; 686 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS3; 687 break; 688 case 12: 689 ppdu_info->rx_status.rate = HAL_11A_RATE_4MCS; 690 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS4; 691 break; 692 case 13: 693 ppdu_info->rx_status.rate = HAL_11A_RATE_5MCS; 694 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS5; 695 break; 696 case 14: 697 ppdu_info->rx_status.rate = HAL_11A_RATE_6MCS; 698 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS6; 699 break; 700 case 15: 701 ppdu_info->rx_status.rate = HAL_11A_RATE_7MCS; 702 ppdu_info->rx_status.mcs = HAL_LEGACY_MCS7; 703 break; 704 default: 705 break; 706 } 707 ppdu_info->rx_status.ofdm_flag = 1; 708 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_SU; 709 break; 710 } 711 712 case WIFIPHYRX_VHT_SIG_A_E: 713 { 714 uint8_t *vht_sig_a_info = (uint8_t *)rx_tlv + 715 HAL_RX_OFFSET(UNIFIED_PHYRX_VHT_SIG_A_0, 716 VHT_SIG_A_INFO_PHYRX_VHT_SIG_A_INFO_DETAILS); 717 718 value = HAL_RX_GET(vht_sig_a_info, VHT_SIG_A_INFO_1, 719 SU_MU_CODING); 720 ppdu_info->rx_status.ldpc = (value == HAL_SU_MU_CODING_LDPC) ? 721 1 : 0; 722 group_id = HAL_RX_GET(vht_sig_a_info, VHT_SIG_A_INFO_0, GROUP_ID); 723 ppdu_info->rx_status.vht_flag_values5 = group_id; 724 ppdu_info->rx_status.mcs = HAL_RX_GET(vht_sig_a_info, 725 VHT_SIG_A_INFO_1, MCS); 726 ppdu_info->rx_status.sgi = HAL_RX_GET(vht_sig_a_info, 727 VHT_SIG_A_INFO_1, GI_SETTING); 728 729 switch (hal->target_type) { 730 case TARGET_TYPE_QCA8074: 731 case TARGET_TYPE_QCA8074V2: 732 case TARGET_TYPE_QCA6018: 733 case TARGET_TYPE_QCN9000: 734 #ifdef QCA_WIFI_QCA6390 735 case TARGET_TYPE_QCA6390: 736 #endif 737 ppdu_info->rx_status.is_stbc = 738 HAL_RX_GET(vht_sig_a_info, 739 VHT_SIG_A_INFO_0, STBC); 740 value = HAL_RX_GET(vht_sig_a_info, 741 VHT_SIG_A_INFO_0, N_STS); 742 value = value & VHT_SIG_SU_NSS_MASK; 743 if (ppdu_info->rx_status.is_stbc && (value > 0)) 744 value = ((value + 1) >> 1) - 1; 745 ppdu_info->rx_status.nss = 746 ((value & VHT_SIG_SU_NSS_MASK) + 1); 747 748 break; 749 case TARGET_TYPE_QCA6290: 750 #if !defined(QCA_WIFI_QCA6290_11AX) 751 ppdu_info->rx_status.is_stbc = 752 HAL_RX_GET(vht_sig_a_info, 753 VHT_SIG_A_INFO_0, STBC); 754 value = HAL_RX_GET(vht_sig_a_info, 755 VHT_SIG_A_INFO_0, N_STS); 756 value = value & VHT_SIG_SU_NSS_MASK; 757 if (ppdu_info->rx_status.is_stbc && (value > 0)) 758 value = ((value + 1) >> 1) - 1; 759 ppdu_info->rx_status.nss = 760 ((value & VHT_SIG_SU_NSS_MASK) + 1); 761 #else 762 ppdu_info->rx_status.nss = 0; 763 #endif 764 break; 765 case TARGET_TYPE_QCA6490: 766 ppdu_info->rx_status.nss = 0; 767 break; 768 default: 769 break; 770 } 771 ppdu_info->rx_status.vht_flag_values3[0] = 772 (((ppdu_info->rx_status.mcs) << 4) 773 | ppdu_info->rx_status.nss); 774 ppdu_info->rx_status.bw = HAL_RX_GET(vht_sig_a_info, 775 VHT_SIG_A_INFO_0, BANDWIDTH); 776 ppdu_info->rx_status.vht_flag_values2 = 777 ppdu_info->rx_status.bw; 778 ppdu_info->rx_status.vht_flag_values4 = 779 HAL_RX_GET(vht_sig_a_info, 780 VHT_SIG_A_INFO_1, SU_MU_CODING); 781 782 ppdu_info->rx_status.beamformed = HAL_RX_GET(vht_sig_a_info, 783 VHT_SIG_A_INFO_1, BEAMFORMED); 784 if (group_id == 0 || group_id == 63) 785 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_SU; 786 else 787 ppdu_info->rx_status.reception_type = 788 HAL_RX_TYPE_MU_MIMO; 789 790 break; 791 } 792 case WIFIPHYRX_HE_SIG_A_SU_E: 793 { 794 uint8_t *he_sig_a_su_info = (uint8_t *)rx_tlv + 795 HAL_RX_OFFSET(UNIFIED_PHYRX_HE_SIG_A_SU_0, 796 HE_SIG_A_SU_INFO_PHYRX_HE_SIG_A_SU_INFO_DETAILS); 797 ppdu_info->rx_status.he_flags = 1; 798 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_0, 799 FORMAT_INDICATION); 800 if (value == 0) { 801 ppdu_info->rx_status.he_data1 = 802 QDF_MON_STATUS_HE_TRIG_FORMAT_TYPE; 803 } else { 804 ppdu_info->rx_status.he_data1 = 805 QDF_MON_STATUS_HE_SU_FORMAT_TYPE; 806 } 807 808 /* data1 */ 809 ppdu_info->rx_status.he_data1 |= 810 QDF_MON_STATUS_HE_BSS_COLOR_KNOWN | 811 QDF_MON_STATUS_HE_BEAM_CHANGE_KNOWN | 812 QDF_MON_STATUS_HE_DL_UL_KNOWN | 813 QDF_MON_STATUS_HE_MCS_KNOWN | 814 QDF_MON_STATUS_HE_DCM_KNOWN | 815 QDF_MON_STATUS_HE_CODING_KNOWN | 816 QDF_MON_STATUS_HE_LDPC_EXTRA_SYMBOL_KNOWN | 817 QDF_MON_STATUS_HE_STBC_KNOWN | 818 QDF_MON_STATUS_HE_DATA_BW_RU_KNOWN | 819 QDF_MON_STATUS_HE_DOPPLER_KNOWN; 820 821 /* data2 */ 822 ppdu_info->rx_status.he_data2 = 823 QDF_MON_STATUS_HE_GI_KNOWN; 824 ppdu_info->rx_status.he_data2 |= 825 QDF_MON_STATUS_TXBF_KNOWN | 826 QDF_MON_STATUS_PE_DISAMBIGUITY_KNOWN | 827 QDF_MON_STATUS_TXOP_KNOWN | 828 QDF_MON_STATUS_LTF_SYMBOLS_KNOWN | 829 QDF_MON_STATUS_PRE_FEC_PADDING_KNOWN | 830 QDF_MON_STATUS_MIDABLE_PERIODICITY_KNOWN; 831 832 /* data3 */ 833 value = HAL_RX_GET(he_sig_a_su_info, 834 HE_SIG_A_SU_INFO_0, BSS_COLOR_ID); 835 ppdu_info->rx_status.he_data3 = value; 836 value = HAL_RX_GET(he_sig_a_su_info, 837 HE_SIG_A_SU_INFO_0, BEAM_CHANGE); 838 value = value << QDF_MON_STATUS_BEAM_CHANGE_SHIFT; 839 ppdu_info->rx_status.he_data3 |= value; 840 value = HAL_RX_GET(he_sig_a_su_info, 841 HE_SIG_A_SU_INFO_0, DL_UL_FLAG); 842 value = value << QDF_MON_STATUS_DL_UL_SHIFT; 843 ppdu_info->rx_status.he_data3 |= value; 844 845 value = HAL_RX_GET(he_sig_a_su_info, 846 HE_SIG_A_SU_INFO_0, TRANSMIT_MCS); 847 ppdu_info->rx_status.mcs = value; 848 value = value << QDF_MON_STATUS_TRANSMIT_MCS_SHIFT; 849 ppdu_info->rx_status.he_data3 |= value; 850 851 value = HAL_RX_GET(he_sig_a_su_info, 852 HE_SIG_A_SU_INFO_0, DCM); 853 he_dcm = value; 854 value = value << QDF_MON_STATUS_DCM_SHIFT; 855 ppdu_info->rx_status.he_data3 |= value; 856 value = HAL_RX_GET(he_sig_a_su_info, 857 HE_SIG_A_SU_INFO_1, CODING); 858 ppdu_info->rx_status.ldpc = (value == HAL_SU_MU_CODING_LDPC) ? 859 1 : 0; 860 value = value << QDF_MON_STATUS_CODING_SHIFT; 861 ppdu_info->rx_status.he_data3 |= value; 862 value = HAL_RX_GET(he_sig_a_su_info, 863 HE_SIG_A_SU_INFO_1, 864 LDPC_EXTRA_SYMBOL); 865 value = value << QDF_MON_STATUS_LDPC_EXTRA_SYMBOL_SHIFT; 866 ppdu_info->rx_status.he_data3 |= value; 867 value = HAL_RX_GET(he_sig_a_su_info, 868 HE_SIG_A_SU_INFO_1, STBC); 869 he_stbc = value; 870 value = value << QDF_MON_STATUS_STBC_SHIFT; 871 ppdu_info->rx_status.he_data3 |= value; 872 873 /* data4 */ 874 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_0, 875 SPATIAL_REUSE); 876 ppdu_info->rx_status.he_data4 = value; 877 878 /* data5 */ 879 value = HAL_RX_GET(he_sig_a_su_info, 880 HE_SIG_A_SU_INFO_0, TRANSMIT_BW); 881 ppdu_info->rx_status.he_data5 = value; 882 ppdu_info->rx_status.bw = value; 883 value = HAL_RX_GET(he_sig_a_su_info, 884 HE_SIG_A_SU_INFO_0, CP_LTF_SIZE); 885 switch (value) { 886 case 0: 887 he_gi = HE_GI_0_8; 888 he_ltf = HE_LTF_1_X; 889 break; 890 case 1: 891 he_gi = HE_GI_0_8; 892 he_ltf = HE_LTF_2_X; 893 break; 894 case 2: 895 he_gi = HE_GI_1_6; 896 he_ltf = HE_LTF_2_X; 897 break; 898 case 3: 899 if (he_dcm && he_stbc) { 900 he_gi = HE_GI_0_8; 901 he_ltf = HE_LTF_4_X; 902 } else { 903 he_gi = HE_GI_3_2; 904 he_ltf = HE_LTF_4_X; 905 } 906 break; 907 } 908 ppdu_info->rx_status.sgi = he_gi; 909 value = he_gi << QDF_MON_STATUS_GI_SHIFT; 910 ppdu_info->rx_status.he_data5 |= value; 911 value = he_ltf << QDF_MON_STATUS_HE_LTF_SIZE_SHIFT; 912 ppdu_info->rx_status.ltf_size = he_ltf; 913 ppdu_info->rx_status.he_data5 |= value; 914 915 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_0, NSTS); 916 value = (value << QDF_MON_STATUS_HE_LTF_SYM_SHIFT); 917 ppdu_info->rx_status.he_data5 |= value; 918 919 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_1, 920 PACKET_EXTENSION_A_FACTOR); 921 value = value << QDF_MON_STATUS_PRE_FEC_PAD_SHIFT; 922 ppdu_info->rx_status.he_data5 |= value; 923 924 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_1, TXBF); 925 value = value << QDF_MON_STATUS_TXBF_SHIFT; 926 ppdu_info->rx_status.he_data5 |= value; 927 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_1, 928 PACKET_EXTENSION_PE_DISAMBIGUITY); 929 value = value << QDF_MON_STATUS_PE_DISAMBIGUITY_SHIFT; 930 ppdu_info->rx_status.he_data5 |= value; 931 932 /* data6 */ 933 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_0, NSTS); 934 value++; 935 ppdu_info->rx_status.nss = value; 936 ppdu_info->rx_status.he_data6 = value; 937 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_1, 938 DOPPLER_INDICATION); 939 value = value << QDF_MON_STATUS_DOPPLER_SHIFT; 940 ppdu_info->rx_status.he_data6 |= value; 941 value = HAL_RX_GET(he_sig_a_su_info, HE_SIG_A_SU_INFO_1, 942 TXOP_DURATION); 943 value = value << QDF_MON_STATUS_TXOP_SHIFT; 944 ppdu_info->rx_status.he_data6 |= value; 945 946 ppdu_info->rx_status.beamformed = HAL_RX_GET(he_sig_a_su_info, 947 HE_SIG_A_SU_INFO_1, TXBF); 948 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_SU; 949 break; 950 } 951 case WIFIPHYRX_HE_SIG_A_MU_DL_E: 952 { 953 uint8_t *he_sig_a_mu_dl_info = (uint8_t *)rx_tlv + 954 HAL_RX_OFFSET(UNIFIED_PHYRX_HE_SIG_A_MU_DL_0, 955 HE_SIG_A_MU_DL_INFO_PHYRX_HE_SIG_A_MU_DL_INFO_DETAILS); 956 957 ppdu_info->rx_status.he_mu_flags = 1; 958 959 /* HE Flags */ 960 /*data1*/ 961 ppdu_info->rx_status.he_data1 = 962 QDF_MON_STATUS_HE_MU_FORMAT_TYPE; 963 ppdu_info->rx_status.he_data1 |= 964 QDF_MON_STATUS_HE_BSS_COLOR_KNOWN | 965 QDF_MON_STATUS_HE_DL_UL_KNOWN | 966 QDF_MON_STATUS_HE_LDPC_EXTRA_SYMBOL_KNOWN | 967 QDF_MON_STATUS_HE_STBC_KNOWN | 968 QDF_MON_STATUS_HE_DATA_BW_RU_KNOWN | 969 QDF_MON_STATUS_HE_DOPPLER_KNOWN; 970 971 /* data2 */ 972 ppdu_info->rx_status.he_data2 = 973 QDF_MON_STATUS_HE_GI_KNOWN; 974 ppdu_info->rx_status.he_data2 |= 975 QDF_MON_STATUS_LTF_SYMBOLS_KNOWN | 976 QDF_MON_STATUS_PRE_FEC_PADDING_KNOWN | 977 QDF_MON_STATUS_PE_DISAMBIGUITY_KNOWN | 978 QDF_MON_STATUS_TXOP_KNOWN | 979 QDF_MON_STATUS_MIDABLE_PERIODICITY_KNOWN; 980 981 /*data3*/ 982 value = HAL_RX_GET(he_sig_a_mu_dl_info, 983 HE_SIG_A_MU_DL_INFO_0, BSS_COLOR_ID); 984 ppdu_info->rx_status.he_data3 = value; 985 986 value = HAL_RX_GET(he_sig_a_mu_dl_info, 987 HE_SIG_A_MU_DL_INFO_0, DL_UL_FLAG); 988 value = value << QDF_MON_STATUS_DL_UL_SHIFT; 989 ppdu_info->rx_status.he_data3 |= value; 990 991 value = HAL_RX_GET(he_sig_a_mu_dl_info, 992 HE_SIG_A_MU_DL_INFO_1, 993 LDPC_EXTRA_SYMBOL); 994 value = value << QDF_MON_STATUS_LDPC_EXTRA_SYMBOL_SHIFT; 995 ppdu_info->rx_status.he_data3 |= value; 996 997 value = HAL_RX_GET(he_sig_a_mu_dl_info, 998 HE_SIG_A_MU_DL_INFO_1, STBC); 999 he_stbc = value; 1000 value = value << QDF_MON_STATUS_STBC_SHIFT; 1001 ppdu_info->rx_status.he_data3 |= value; 1002 1003 /*data4*/ 1004 value = HAL_RX_GET(he_sig_a_mu_dl_info, HE_SIG_A_MU_DL_INFO_0, 1005 SPATIAL_REUSE); 1006 ppdu_info->rx_status.he_data4 = value; 1007 1008 /*data5*/ 1009 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1010 HE_SIG_A_MU_DL_INFO_0, TRANSMIT_BW); 1011 ppdu_info->rx_status.he_data5 = value; 1012 ppdu_info->rx_status.bw = value; 1013 1014 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1015 HE_SIG_A_MU_DL_INFO_0, CP_LTF_SIZE); 1016 switch (value) { 1017 case 0: 1018 he_gi = HE_GI_0_8; 1019 he_ltf = HE_LTF_4_X; 1020 break; 1021 case 1: 1022 he_gi = HE_GI_0_8; 1023 he_ltf = HE_LTF_2_X; 1024 break; 1025 case 2: 1026 he_gi = HE_GI_1_6; 1027 he_ltf = HE_LTF_2_X; 1028 break; 1029 case 3: 1030 he_gi = HE_GI_3_2; 1031 he_ltf = HE_LTF_4_X; 1032 break; 1033 } 1034 ppdu_info->rx_status.sgi = he_gi; 1035 value = he_gi << QDF_MON_STATUS_GI_SHIFT; 1036 ppdu_info->rx_status.he_data5 |= value; 1037 1038 value = he_ltf << QDF_MON_STATUS_HE_LTF_SIZE_SHIFT; 1039 ppdu_info->rx_status.he_data5 |= value; 1040 1041 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1042 HE_SIG_A_MU_DL_INFO_1, NUM_LTF_SYMBOLS); 1043 value = (value << QDF_MON_STATUS_HE_LTF_SYM_SHIFT); 1044 ppdu_info->rx_status.he_data5 |= value; 1045 1046 value = HAL_RX_GET(he_sig_a_mu_dl_info, HE_SIG_A_MU_DL_INFO_1, 1047 PACKET_EXTENSION_A_FACTOR); 1048 value = value << QDF_MON_STATUS_PRE_FEC_PAD_SHIFT; 1049 ppdu_info->rx_status.he_data5 |= value; 1050 1051 1052 value = HAL_RX_GET(he_sig_a_mu_dl_info, HE_SIG_A_MU_DL_INFO_1, 1053 PACKET_EXTENSION_PE_DISAMBIGUITY); 1054 value = value << QDF_MON_STATUS_PE_DISAMBIGUITY_SHIFT; 1055 ppdu_info->rx_status.he_data5 |= value; 1056 1057 /*data6*/ 1058 value = HAL_RX_GET(he_sig_a_mu_dl_info, HE_SIG_A_MU_DL_INFO_0, 1059 DOPPLER_INDICATION); 1060 value = value << QDF_MON_STATUS_DOPPLER_SHIFT; 1061 ppdu_info->rx_status.he_data6 |= value; 1062 1063 value = HAL_RX_GET(he_sig_a_mu_dl_info, HE_SIG_A_MU_DL_INFO_1, 1064 TXOP_DURATION); 1065 value = value << QDF_MON_STATUS_TXOP_SHIFT; 1066 ppdu_info->rx_status.he_data6 |= value; 1067 1068 /* HE-MU Flags */ 1069 /* HE-MU-flags1 */ 1070 ppdu_info->rx_status.he_flags1 = 1071 QDF_MON_STATUS_SIG_B_MCS_KNOWN | 1072 QDF_MON_STATUS_SIG_B_DCM_KNOWN | 1073 QDF_MON_STATUS_SIG_B_COMPRESSION_FLAG_1_KNOWN | 1074 QDF_MON_STATUS_SIG_B_SYM_NUM_KNOWN | 1075 QDF_MON_STATUS_RU_0_KNOWN; 1076 1077 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1078 HE_SIG_A_MU_DL_INFO_0, MCS_OF_SIG_B); 1079 ppdu_info->rx_status.he_flags1 |= value; 1080 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1081 HE_SIG_A_MU_DL_INFO_0, DCM_OF_SIG_B); 1082 value = value << QDF_MON_STATUS_DCM_FLAG_1_SHIFT; 1083 ppdu_info->rx_status.he_flags1 |= value; 1084 1085 /* HE-MU-flags2 */ 1086 ppdu_info->rx_status.he_flags2 = 1087 QDF_MON_STATUS_BW_KNOWN; 1088 1089 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1090 HE_SIG_A_MU_DL_INFO_0, TRANSMIT_BW); 1091 ppdu_info->rx_status.he_flags2 |= value; 1092 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1093 HE_SIG_A_MU_DL_INFO_0, COMP_MODE_SIG_B); 1094 value = value << QDF_MON_STATUS_SIG_B_COMPRESSION_FLAG_2_SHIFT; 1095 ppdu_info->rx_status.he_flags2 |= value; 1096 value = HAL_RX_GET(he_sig_a_mu_dl_info, 1097 HE_SIG_A_MU_DL_INFO_0, NUM_SIG_B_SYMBOLS); 1098 value = value - 1; 1099 value = value << QDF_MON_STATUS_NUM_SIG_B_SYMBOLS_SHIFT; 1100 ppdu_info->rx_status.he_flags2 |= value; 1101 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_MU_MIMO; 1102 break; 1103 } 1104 case WIFIPHYRX_HE_SIG_B1_MU_E: 1105 { 1106 1107 uint8_t *he_sig_b1_mu_info = (uint8_t *)rx_tlv + 1108 HAL_RX_OFFSET(UNIFIED_PHYRX_HE_SIG_B1_MU_0, 1109 HE_SIG_B1_MU_INFO_PHYRX_HE_SIG_B1_MU_INFO_DETAILS); 1110 1111 ppdu_info->rx_status.he_sig_b_common_known |= 1112 QDF_MON_STATUS_HE_SIG_B_COMMON_KNOWN_RU0; 1113 /* TODO: Check on the availability of other fields in 1114 * sig_b_common 1115 */ 1116 1117 value = HAL_RX_GET(he_sig_b1_mu_info, 1118 HE_SIG_B1_MU_INFO_0, RU_ALLOCATION); 1119 ppdu_info->rx_status.he_RU[0] = value; 1120 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_MU_MIMO; 1121 break; 1122 } 1123 case WIFIPHYRX_HE_SIG_B2_MU_E: 1124 { 1125 uint8_t *he_sig_b2_mu_info = (uint8_t *)rx_tlv + 1126 HAL_RX_OFFSET(UNIFIED_PHYRX_HE_SIG_B2_MU_0, 1127 HE_SIG_B2_MU_INFO_PHYRX_HE_SIG_B2_MU_INFO_DETAILS); 1128 /* 1129 * Not all "HE" fields can be updated from 1130 * WIFIPHYRX_HE_SIG_A_MU_DL_E TLV. Use WIFIPHYRX_HE_SIG_B2_MU_E 1131 * to populate rest of the "HE" fields for MU scenarios. 1132 */ 1133 1134 /* HE-data1 */ 1135 ppdu_info->rx_status.he_data1 |= 1136 QDF_MON_STATUS_HE_MCS_KNOWN | 1137 QDF_MON_STATUS_HE_CODING_KNOWN; 1138 1139 /* HE-data2 */ 1140 1141 /* HE-data3 */ 1142 value = HAL_RX_GET(he_sig_b2_mu_info, 1143 HE_SIG_B2_MU_INFO_0, STA_MCS); 1144 ppdu_info->rx_status.mcs = value; 1145 value = value << QDF_MON_STATUS_TRANSMIT_MCS_SHIFT; 1146 ppdu_info->rx_status.he_data3 |= value; 1147 1148 1149 value = HAL_RX_GET(he_sig_b2_mu_info, 1150 HE_SIG_B2_MU_INFO_0, STA_CODING); 1151 value = value << QDF_MON_STATUS_CODING_SHIFT; 1152 ppdu_info->rx_status.he_data3 |= value; 1153 1154 /* HE-data4 */ 1155 value = HAL_RX_GET(he_sig_b2_mu_info, 1156 HE_SIG_B2_MU_INFO_0, STA_ID); 1157 value = value << QDF_MON_STATUS_STA_ID_SHIFT; 1158 ppdu_info->rx_status.he_data4 |= value; 1159 1160 /* HE-data5 */ 1161 1162 /* HE-data6 */ 1163 value = HAL_RX_GET(he_sig_b2_mu_info, 1164 HE_SIG_B2_MU_INFO_0, NSTS); 1165 /* value n indicates n+1 spatial streams */ 1166 value++; 1167 ppdu_info->rx_status.nss = value; 1168 ppdu_info->rx_status.he_data6 |= value; 1169 1170 break; 1171 1172 } 1173 case WIFIPHYRX_HE_SIG_B2_OFDMA_E: 1174 { 1175 uint8_t *he_sig_b2_ofdma_info = 1176 (uint8_t *)rx_tlv + 1177 HAL_RX_OFFSET(UNIFIED_PHYRX_HE_SIG_B2_OFDMA_0, 1178 HE_SIG_B2_OFDMA_INFO_PHYRX_HE_SIG_B2_OFDMA_INFO_DETAILS); 1179 1180 /* 1181 * Not all "HE" fields can be updated from 1182 * WIFIPHYRX_HE_SIG_A_MU_DL_E TLV. Use WIFIPHYRX_HE_SIG_B2_MU_E 1183 * to populate rest of "HE" fields for MU OFDMA scenarios. 1184 */ 1185 1186 /* HE-data1 */ 1187 ppdu_info->rx_status.he_data1 |= 1188 QDF_MON_STATUS_HE_MCS_KNOWN | 1189 QDF_MON_STATUS_HE_DCM_KNOWN | 1190 QDF_MON_STATUS_HE_CODING_KNOWN; 1191 1192 /* HE-data2 */ 1193 ppdu_info->rx_status.he_data2 |= 1194 QDF_MON_STATUS_TXBF_KNOWN; 1195 1196 /* HE-data3 */ 1197 value = HAL_RX_GET(he_sig_b2_ofdma_info, 1198 HE_SIG_B2_OFDMA_INFO_0, STA_MCS); 1199 ppdu_info->rx_status.mcs = value; 1200 value = value << QDF_MON_STATUS_TRANSMIT_MCS_SHIFT; 1201 ppdu_info->rx_status.he_data3 |= value; 1202 1203 value = HAL_RX_GET(he_sig_b2_ofdma_info, 1204 HE_SIG_B2_OFDMA_INFO_0, STA_DCM); 1205 he_dcm = value; 1206 value = value << QDF_MON_STATUS_DCM_SHIFT; 1207 ppdu_info->rx_status.he_data3 |= value; 1208 1209 value = HAL_RX_GET(he_sig_b2_ofdma_info, 1210 HE_SIG_B2_OFDMA_INFO_0, STA_CODING); 1211 value = value << QDF_MON_STATUS_CODING_SHIFT; 1212 ppdu_info->rx_status.he_data3 |= value; 1213 1214 /* HE-data4 */ 1215 value = HAL_RX_GET(he_sig_b2_ofdma_info, 1216 HE_SIG_B2_OFDMA_INFO_0, STA_ID); 1217 value = value << QDF_MON_STATUS_STA_ID_SHIFT; 1218 ppdu_info->rx_status.he_data4 |= value; 1219 1220 /* HE-data5 */ 1221 value = HAL_RX_GET(he_sig_b2_ofdma_info, 1222 HE_SIG_B2_OFDMA_INFO_0, TXBF); 1223 value = value << QDF_MON_STATUS_TXBF_SHIFT; 1224 ppdu_info->rx_status.he_data5 |= value; 1225 1226 /* HE-data6 */ 1227 value = HAL_RX_GET(he_sig_b2_ofdma_info, 1228 HE_SIG_B2_OFDMA_INFO_0, NSTS); 1229 /* value n indicates n+1 spatial streams */ 1230 value++; 1231 ppdu_info->rx_status.nss = value; 1232 ppdu_info->rx_status.he_data6 |= value; 1233 ppdu_info->rx_status.reception_type = HAL_RX_TYPE_MU_OFDMA; 1234 break; 1235 } 1236 case WIFIPHYRX_RSSI_LEGACY_E: 1237 { 1238 uint8_t reception_type; 1239 int8_t rssi_value; 1240 uint8_t *rssi_info_tlv = (uint8_t *)rx_tlv + 1241 HAL_RX_OFFSET(UNIFIED_PHYRX_RSSI_LEGACY_19, 1242 RECEIVE_RSSI_INFO_PREAMBLE_RSSI_INFO_DETAILS); 1243 1244 ppdu_info->rx_status.rssi_comb = HAL_RX_GET(rx_tlv, 1245 PHYRX_RSSI_LEGACY_35, RSSI_COMB); 1246 ppdu_info->rx_status.bw = hal->ops->hal_rx_get_tlv(rx_tlv); 1247 ppdu_info->rx_status.he_re = 0; 1248 1249 reception_type = HAL_RX_GET(rx_tlv, 1250 PHYRX_RSSI_LEGACY_0, 1251 RECEPTION_TYPE); 1252 switch (reception_type) { 1253 case QDF_RECEPTION_TYPE_ULOFMDA: 1254 ppdu_info->rx_status.reception_type = 1255 HAL_RX_TYPE_MU_OFDMA; 1256 ppdu_info->rx_status.ulofdma_flag = 1; 1257 ppdu_info->rx_status.he_data1 = 1258 QDF_MON_STATUS_HE_TRIG_FORMAT_TYPE; 1259 break; 1260 case QDF_RECEPTION_TYPE_ULMIMO: 1261 ppdu_info->rx_status.reception_type = 1262 HAL_RX_TYPE_MU_MIMO; 1263 ppdu_info->rx_status.he_data1 = 1264 QDF_MON_STATUS_HE_MU_FORMAT_TYPE; 1265 break; 1266 default: 1267 ppdu_info->rx_status.reception_type = 1268 HAL_RX_TYPE_SU; 1269 break; 1270 } 1271 hal_rx_update_rssi_chain(ppdu_info, rssi_info_tlv); 1272 rssi_value = HAL_RX_GET(rssi_info_tlv, 1273 RECEIVE_RSSI_INFO_0, RSSI_PRI20_CHAIN0); 1274 ppdu_info->rx_status.rssi[0] = rssi_value; 1275 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1276 "RSSI_PRI20_CHAIN0: %d\n", rssi_value); 1277 1278 rssi_value = HAL_RX_GET(rssi_info_tlv, 1279 RECEIVE_RSSI_INFO_2, RSSI_PRI20_CHAIN1); 1280 ppdu_info->rx_status.rssi[1] = rssi_value; 1281 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1282 "RSSI_PRI20_CHAIN1: %d\n", rssi_value); 1283 1284 rssi_value = HAL_RX_GET(rssi_info_tlv, 1285 RECEIVE_RSSI_INFO_4, RSSI_PRI20_CHAIN2); 1286 ppdu_info->rx_status.rssi[2] = rssi_value; 1287 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1288 "RSSI_PRI20_CHAIN2: %d\n", rssi_value); 1289 1290 rssi_value = HAL_RX_GET(rssi_info_tlv, 1291 RECEIVE_RSSI_INFO_6, RSSI_PRI20_CHAIN3); 1292 ppdu_info->rx_status.rssi[3] = rssi_value; 1293 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1294 "RSSI_PRI20_CHAIN3: %d\n", rssi_value); 1295 1296 rssi_value = HAL_RX_GET(rssi_info_tlv, 1297 RECEIVE_RSSI_INFO_8, RSSI_PRI20_CHAIN4); 1298 ppdu_info->rx_status.rssi[4] = rssi_value; 1299 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1300 "RSSI_PRI20_CHAIN4: %d\n", rssi_value); 1301 1302 rssi_value = HAL_RX_GET(rssi_info_tlv, 1303 RECEIVE_RSSI_INFO_10, 1304 RSSI_PRI20_CHAIN5); 1305 ppdu_info->rx_status.rssi[5] = rssi_value; 1306 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1307 "RSSI_PRI20_CHAIN5: %d\n", rssi_value); 1308 1309 rssi_value = HAL_RX_GET(rssi_info_tlv, 1310 RECEIVE_RSSI_INFO_12, 1311 RSSI_PRI20_CHAIN6); 1312 ppdu_info->rx_status.rssi[6] = rssi_value; 1313 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1314 "RSSI_PRI20_CHAIN6: %d\n", rssi_value); 1315 1316 rssi_value = HAL_RX_GET(rssi_info_tlv, 1317 RECEIVE_RSSI_INFO_14, 1318 RSSI_PRI20_CHAIN7); 1319 ppdu_info->rx_status.rssi[7] = rssi_value; 1320 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1321 "RSSI_PRI20_CHAIN7: %d\n", rssi_value); 1322 break; 1323 } 1324 case WIFIPHYRX_OTHER_RECEIVE_INFO_E: 1325 hal_rx_proc_phyrx_other_receive_info_tlv(hal, rx_tlv_hdr, 1326 ppdu_info); 1327 break; 1328 case WIFIRX_HEADER_E: 1329 { 1330 struct hal_rx_ppdu_common_info *com_info = &ppdu_info->com_info; 1331 uint16_t mpdu_cnt = com_info->mpdu_cnt; 1332 1333 if (mpdu_cnt >= HAL_RX_MAX_MPDU) { 1334 hal_alert("Number of MPDUs per PPDU exceeded"); 1335 break; 1336 } 1337 /* Update first_msdu_payload for every mpdu and increment 1338 * com_info->mpdu_cnt for every WIFIRX_HEADER_E TLV 1339 */ 1340 ppdu_info->ppdu_msdu_info[mpdu_cnt].first_msdu_payload = 1341 rx_tlv; 1342 ppdu_info->ppdu_msdu_info[mpdu_cnt].payload_len = tlv_len; 1343 ppdu_info->ppdu_msdu_info[mpdu_cnt].nbuf = nbuf; 1344 ppdu_info->msdu_info.first_msdu_payload = rx_tlv; 1345 ppdu_info->msdu_info.payload_len = tlv_len; 1346 ppdu_info->user_id = user_id; 1347 ppdu_info->hdr_len = tlv_len; 1348 ppdu_info->data = rx_tlv; 1349 ppdu_info->data += 4; 1350 1351 /* for every RX_HEADER TLV increment mpdu_cnt */ 1352 com_info->mpdu_cnt++; 1353 return HAL_TLV_STATUS_HEADER; 1354 } 1355 case WIFIRX_MPDU_START_E: 1356 { 1357 uint8_t *rx_mpdu_start = 1358 (uint8_t *)rx_tlv + HAL_RX_OFFSET(UNIFIED_RX_MPDU_START_0, 1359 RX_MPDU_INFO_RX_MPDU_INFO_DETAILS); 1360 uint32_t ppdu_id = 1361 HAL_RX_GET_PPDU_ID(rx_mpdu_start); 1362 uint8_t filter_category = 0; 1363 1364 ppdu_info->nac_info.fc_valid = 1365 HAL_RX_GET_FC_VALID(rx_mpdu_start); 1366 1367 ppdu_info->nac_info.to_ds_flag = 1368 HAL_RX_GET_TO_DS_FLAG(rx_mpdu_start); 1369 1370 ppdu_info->nac_info.frame_control = 1371 HAL_RX_GET(rx_mpdu_start, 1372 RX_MPDU_INFO_14, 1373 MPDU_FRAME_CONTROL_FIELD); 1374 1375 ppdu_info->sw_frame_group_id = 1376 HAL_RX_GET_SW_FRAME_GROUP_ID(rx_mpdu_start); 1377 1378 if (ppdu_info->sw_frame_group_id == 1379 HAL_MPDU_SW_FRAME_GROUP_NULL_DATA) { 1380 ppdu_info->rx_status.frame_control_info_valid = 1381 ppdu_info->nac_info.fc_valid; 1382 ppdu_info->rx_status.frame_control = 1383 ppdu_info->nac_info.frame_control; 1384 } 1385 1386 ppdu_info->nac_info.mac_addr2_valid = 1387 HAL_RX_GET_MAC_ADDR2_VALID(rx_mpdu_start); 1388 1389 *(uint16_t *)&ppdu_info->nac_info.mac_addr2[0] = 1390 HAL_RX_GET(rx_mpdu_start, 1391 RX_MPDU_INFO_16, 1392 MAC_ADDR_AD2_15_0); 1393 1394 *(uint32_t *)&ppdu_info->nac_info.mac_addr2[2] = 1395 HAL_RX_GET(rx_mpdu_start, 1396 RX_MPDU_INFO_17, 1397 MAC_ADDR_AD2_47_16); 1398 1399 if (ppdu_info->rx_status.prev_ppdu_id != ppdu_id) { 1400 ppdu_info->rx_status.prev_ppdu_id = ppdu_id; 1401 ppdu_info->rx_status.ppdu_len = 1402 HAL_RX_GET(rx_mpdu_start, RX_MPDU_INFO_13, 1403 MPDU_LENGTH); 1404 } else { 1405 ppdu_info->rx_status.ppdu_len += 1406 HAL_RX_GET(rx_mpdu_start, RX_MPDU_INFO_13, 1407 MPDU_LENGTH); 1408 } 1409 1410 filter_category = 1411 HAL_RX_GET_FILTER_CATEGORY(rx_mpdu_start); 1412 1413 if (filter_category == 0) 1414 ppdu_info->rx_status.rxpcu_filter_pass = 1; 1415 else if (filter_category == 1) 1416 ppdu_info->rx_status.monitor_direct_used = 1; 1417 1418 ppdu_info->nac_info.mcast_bcast = 1419 HAL_RX_GET(rx_mpdu_start, 1420 RX_MPDU_INFO_13, 1421 MCAST_BCAST); 1422 break; 1423 } 1424 case WIFIRX_MPDU_END_E: 1425 ppdu_info->user_id = user_id; 1426 ppdu_info->fcs_err = 1427 HAL_RX_GET(rx_tlv, RX_MPDU_END_1, 1428 FCS_ERR); 1429 return HAL_TLV_STATUS_MPDU_END; 1430 case WIFIRX_MSDU_END_E: 1431 if (user_id < HAL_MAX_UL_MU_USERS) { 1432 ppdu_info->rx_msdu_info[user_id].cce_metadata = 1433 HAL_RX_MSDU_END_CCE_METADATA_GET(rx_tlv); 1434 ppdu_info->rx_msdu_info[user_id].fse_metadata = 1435 HAL_RX_MSDU_END_FSE_METADATA_GET(rx_tlv); 1436 ppdu_info->rx_msdu_info[user_id].is_flow_idx_timeout = 1437 HAL_RX_MSDU_END_FLOW_IDX_TIMEOUT_GET(rx_tlv); 1438 ppdu_info->rx_msdu_info[user_id].is_flow_idx_invalid = 1439 HAL_RX_MSDU_END_FLOW_IDX_INVALID_GET(rx_tlv); 1440 ppdu_info->rx_msdu_info[user_id].flow_idx = 1441 HAL_RX_MSDU_END_FLOW_IDX_GET(rx_tlv); 1442 } 1443 return HAL_TLV_STATUS_MSDU_END; 1444 case 0: 1445 return HAL_TLV_STATUS_PPDU_DONE; 1446 1447 default: 1448 if (hal_rx_handle_other_tlvs(tlv_tag, rx_tlv, ppdu_info)) 1449 unhandled = false; 1450 else 1451 unhandled = true; 1452 break; 1453 } 1454 1455 if (!unhandled) 1456 QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1457 "%s TLV type: %d, TLV len:%d %s", 1458 __func__, tlv_tag, tlv_len, 1459 unhandled == true ? "unhandled" : ""); 1460 1461 qdf_trace_hex_dump(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_DEBUG, 1462 rx_tlv, tlv_len); 1463 1464 return HAL_TLV_STATUS_PPDU_NOT_DONE; 1465 } 1466 1467 /** 1468 * hal_reo_setup - Initialize HW REO block 1469 * 1470 * @hal_soc: Opaque HAL SOC handle 1471 * @reo_params: parameters needed by HAL for REO config 1472 */ 1473 static void hal_reo_setup_generic(struct hal_soc *soc, 1474 void *reoparams) 1475 { 1476 uint32_t reg_val; 1477 struct hal_reo_params *reo_params = (struct hal_reo_params *)reoparams; 1478 1479 reg_val = HAL_REG_READ(soc, HWIO_REO_R0_GENERAL_ENABLE_ADDR( 1480 SEQ_WCSS_UMAC_REO_REG_OFFSET)); 1481 1482 hal_reo_config(soc, reg_val, reo_params); 1483 /* Other ring enable bits and REO_ENABLE will be set by FW */ 1484 1485 /* TODO: Setup destination ring mapping if enabled */ 1486 1487 /* TODO: Error destination ring setting is left to default. 1488 * Default setting is to send all errors to release ring. 1489 */ 1490 1491 HAL_REG_WRITE(soc, 1492 HWIO_REO_R0_AGING_THRESHOLD_IX_0_ADDR( 1493 SEQ_WCSS_UMAC_REO_REG_OFFSET), 1494 HAL_DEFAULT_BE_BK_VI_REO_TIMEOUT_MS * 1000); 1495 1496 HAL_REG_WRITE(soc, 1497 HWIO_REO_R0_AGING_THRESHOLD_IX_1_ADDR( 1498 SEQ_WCSS_UMAC_REO_REG_OFFSET), 1499 (HAL_DEFAULT_BE_BK_VI_REO_TIMEOUT_MS * 1000)); 1500 1501 HAL_REG_WRITE(soc, 1502 HWIO_REO_R0_AGING_THRESHOLD_IX_2_ADDR( 1503 SEQ_WCSS_UMAC_REO_REG_OFFSET), 1504 (HAL_DEFAULT_BE_BK_VI_REO_TIMEOUT_MS * 1000)); 1505 1506 HAL_REG_WRITE(soc, 1507 HWIO_REO_R0_AGING_THRESHOLD_IX_3_ADDR( 1508 SEQ_WCSS_UMAC_REO_REG_OFFSET), 1509 (HAL_DEFAULT_VO_REO_TIMEOUT_MS * 1000)); 1510 1511 /* 1512 * When hash based routing is enabled, routing of the rx packet 1513 * is done based on the following value: 1 _ _ _ _ The last 4 1514 * bits are based on hash[3:0]. This means the possible values 1515 * are 0x10 to 0x1f. This value is used to look-up the 1516 * ring ID configured in Destination_Ring_Ctrl_IX_* register. 1517 * The Destination_Ring_Ctrl_IX_2 and Destination_Ring_Ctrl_IX_3 1518 * registers need to be configured to set-up the 16 entries to 1519 * map the hash values to a ring number. There are 3 bits per 1520 * hash entry which are mapped as follows: 1521 * 0: TCL, 1:SW1, 2:SW2, * 3:SW3, 4:SW4, 5:Release, 6:FW(WIFI), 1522 * 7: NOT_USED. 1523 */ 1524 if (reo_params->rx_hash_enabled) { 1525 HAL_REG_WRITE(soc, 1526 HWIO_REO_R0_DESTINATION_RING_CTRL_IX_2_ADDR( 1527 SEQ_WCSS_UMAC_REO_REG_OFFSET), 1528 reo_params->remap1); 1529 1530 hal_debug("HWIO_REO_R0_DESTINATION_RING_CTRL_IX_2_ADDR 0x%x", 1531 HAL_REG_READ(soc, 1532 HWIO_REO_R0_DESTINATION_RING_CTRL_IX_2_ADDR( 1533 SEQ_WCSS_UMAC_REO_REG_OFFSET))); 1534 1535 HAL_REG_WRITE(soc, 1536 HWIO_REO_R0_DESTINATION_RING_CTRL_IX_3_ADDR( 1537 SEQ_WCSS_UMAC_REO_REG_OFFSET), 1538 reo_params->remap2); 1539 1540 hal_debug("HWIO_REO_R0_DESTINATION_RING_CTRL_IX_3_ADDR 0x%x", 1541 HAL_REG_READ(soc, 1542 HWIO_REO_R0_DESTINATION_RING_CTRL_IX_3_ADDR( 1543 SEQ_WCSS_UMAC_REO_REG_OFFSET))); 1544 } 1545 1546 1547 /* TODO: Check if the following registers shoould be setup by host: 1548 * AGING_CONTROL 1549 * HIGH_MEMORY_THRESHOLD 1550 * GLOBAL_LINK_DESC_COUNT_THRESH_IX_0[1,2] 1551 * GLOBAL_LINK_DESC_COUNT_CTRL 1552 */ 1553 } 1554 1555 /** 1556 * hal_get_hw_hptp_generic() - Get HW head and tail pointer value for any ring 1557 * @hal_soc: Opaque HAL SOC handle 1558 * @hal_ring: Source ring pointer 1559 * @headp: Head Pointer 1560 * @tailp: Tail Pointer 1561 * @ring: Ring type 1562 * 1563 * Return: Update tail pointer and head pointer in arguments. 1564 */ 1565 static inline 1566 void hal_get_hw_hptp_generic(struct hal_soc *hal_soc, 1567 hal_ring_handle_t hal_ring_hdl, 1568 uint32_t *headp, uint32_t *tailp, 1569 uint8_t ring) 1570 { 1571 struct hal_srng *srng = (struct hal_srng *)hal_ring_hdl; 1572 struct hal_hw_srng_config *ring_config; 1573 enum hal_ring_type ring_type = (enum hal_ring_type)ring; 1574 1575 if (!hal_soc || !srng) { 1576 QDF_TRACE(QDF_MODULE_ID_HAL, QDF_TRACE_LEVEL_ERROR, 1577 "%s: Context is Null", __func__); 1578 return; 1579 } 1580 1581 ring_config = HAL_SRNG_CONFIG(hal_soc, ring_type); 1582 if (!ring_config->lmac_ring) { 1583 if (srng->ring_dir == HAL_SRNG_SRC_RING) { 1584 *headp = SRNG_SRC_REG_READ(srng, HP); 1585 *tailp = SRNG_SRC_REG_READ(srng, TP); 1586 } else { 1587 *headp = SRNG_DST_REG_READ(srng, HP); 1588 *tailp = SRNG_DST_REG_READ(srng, TP); 1589 } 1590 } 1591 } 1592 1593 /** 1594 * hal_srng_src_hw_init - Private function to initialize SRNG 1595 * source ring HW 1596 * @hal_soc: HAL SOC handle 1597 * @srng: SRNG ring pointer 1598 */ 1599 static inline 1600 void hal_srng_src_hw_init_generic(struct hal_soc *hal, 1601 struct hal_srng *srng) 1602 { 1603 uint32_t reg_val = 0; 1604 uint64_t tp_addr = 0; 1605 1606 hal_debug("hw_init srng %d", srng->ring_id); 1607 1608 if (srng->flags & HAL_SRNG_MSI_INTR) { 1609 SRNG_SRC_REG_WRITE(srng, MSI1_BASE_LSB, 1610 srng->msi_addr & 0xffffffff); 1611 reg_val = SRNG_SM(SRNG_SRC_FLD(MSI1_BASE_MSB, ADDR), 1612 (uint64_t)(srng->msi_addr) >> 32) | 1613 SRNG_SM(SRNG_SRC_FLD(MSI1_BASE_MSB, 1614 MSI1_ENABLE), 1); 1615 SRNG_SRC_REG_WRITE(srng, MSI1_BASE_MSB, reg_val); 1616 SRNG_SRC_REG_WRITE(srng, MSI1_DATA, srng->msi_data); 1617 } 1618 1619 SRNG_SRC_REG_WRITE(srng, BASE_LSB, srng->ring_base_paddr & 0xffffffff); 1620 reg_val = SRNG_SM(SRNG_SRC_FLD(BASE_MSB, RING_BASE_ADDR_MSB), 1621 ((uint64_t)(srng->ring_base_paddr) >> 32)) | 1622 SRNG_SM(SRNG_SRC_FLD(BASE_MSB, RING_SIZE), 1623 srng->entry_size * srng->num_entries); 1624 SRNG_SRC_REG_WRITE(srng, BASE_MSB, reg_val); 1625 1626 reg_val = SRNG_SM(SRNG_SRC_FLD(ID, ENTRY_SIZE), srng->entry_size); 1627 SRNG_SRC_REG_WRITE(srng, ID, reg_val); 1628 1629 /** 1630 * Interrupt setup: 1631 * Default interrupt mode is 'pulse'. Need to setup SW_INTERRUPT_MODE 1632 * if level mode is required 1633 */ 1634 reg_val = 0; 1635 1636 /* 1637 * WAR - Hawkeye v1 has a hardware bug which requires timer value to be 1638 * programmed in terms of 1us resolution instead of 8us resolution as 1639 * given in MLD. 1640 */ 1641 if (srng->intr_timer_thres_us) { 1642 reg_val |= SRNG_SM(SRNG_SRC_FLD(CONSUMER_INT_SETUP_IX0, 1643 INTERRUPT_TIMER_THRESHOLD), 1644 srng->intr_timer_thres_us); 1645 /* For HK v2 this should be (srng->intr_timer_thres_us >> 3) */ 1646 } 1647 1648 if (srng->intr_batch_cntr_thres_entries) { 1649 reg_val |= SRNG_SM(SRNG_SRC_FLD(CONSUMER_INT_SETUP_IX0, 1650 BATCH_COUNTER_THRESHOLD), 1651 srng->intr_batch_cntr_thres_entries * 1652 srng->entry_size); 1653 } 1654 SRNG_SRC_REG_WRITE(srng, CONSUMER_INT_SETUP_IX0, reg_val); 1655 1656 reg_val = 0; 1657 if (srng->flags & HAL_SRNG_LOW_THRES_INTR_ENABLE) { 1658 reg_val |= SRNG_SM(SRNG_SRC_FLD(CONSUMER_INT_SETUP_IX1, 1659 LOW_THRESHOLD), srng->u.src_ring.low_threshold); 1660 } 1661 1662 SRNG_SRC_REG_WRITE(srng, CONSUMER_INT_SETUP_IX1, reg_val); 1663 1664 /* As per HW team, TP_ADDR and HP_ADDR for Idle link ring should 1665 * remain 0 to avoid some WBM stability issues. Remote head/tail 1666 * pointers are not required since this ring is completely managed 1667 * by WBM HW 1668 */ 1669 reg_val = 0; 1670 if (srng->ring_id != HAL_SRNG_WBM_IDLE_LINK) { 1671 tp_addr = (uint64_t)(hal->shadow_rdptr_mem_paddr + 1672 ((unsigned long)(srng->u.src_ring.tp_addr) - 1673 (unsigned long)(hal->shadow_rdptr_mem_vaddr))); 1674 SRNG_SRC_REG_WRITE(srng, TP_ADDR_LSB, tp_addr & 0xffffffff); 1675 SRNG_SRC_REG_WRITE(srng, TP_ADDR_MSB, tp_addr >> 32); 1676 } else { 1677 reg_val |= SRNG_SM(SRNG_SRC_FLD(MISC, RING_ID_DISABLE), 1); 1678 } 1679 1680 /* Initilaize head and tail pointers to indicate ring is empty */ 1681 SRNG_SRC_REG_WRITE(srng, HP, 0); 1682 SRNG_SRC_REG_WRITE(srng, TP, 0); 1683 *(srng->u.src_ring.tp_addr) = 0; 1684 1685 reg_val |= ((srng->flags & HAL_SRNG_DATA_TLV_SWAP) ? 1686 SRNG_SM(SRNG_SRC_FLD(MISC, DATA_TLV_SWAP_BIT), 1) : 0) | 1687 ((srng->flags & HAL_SRNG_RING_PTR_SWAP) ? 1688 SRNG_SM(SRNG_SRC_FLD(MISC, HOST_FW_SWAP_BIT), 1) : 0) | 1689 ((srng->flags & HAL_SRNG_MSI_SWAP) ? 1690 SRNG_SM(SRNG_SRC_FLD(MISC, MSI_SWAP_BIT), 1) : 0); 1691 1692 /* Loop count is not used for SRC rings */ 1693 reg_val |= SRNG_SM(SRNG_SRC_FLD(MISC, LOOPCNT_DISABLE), 1); 1694 1695 /* 1696 * reg_val |= SRNG_SM(SRNG_SRC_FLD(MISC, SRNG_ENABLE), 1); 1697 * todo: update fw_api and replace with above line 1698 * (when SRNG_ENABLE field for the MISC register is available in fw_api) 1699 * (WCSS_UMAC_CE_0_SRC_WFSS_CE_CHANNEL_SRC_R0_SRC_RING_MISC) 1700 */ 1701 reg_val |= 0x40; 1702 1703 SRNG_SRC_REG_WRITE(srng, MISC, reg_val); 1704 } 1705 1706 /** 1707 * hal_srng_dst_hw_init - Private function to initialize SRNG 1708 * destination ring HW 1709 * @hal_soc: HAL SOC handle 1710 * @srng: SRNG ring pointer 1711 */ 1712 static inline 1713 void hal_srng_dst_hw_init_generic(struct hal_soc *hal, 1714 struct hal_srng *srng) 1715 { 1716 uint32_t reg_val = 0; 1717 uint64_t hp_addr = 0; 1718 1719 hal_debug("hw_init srng %d", srng->ring_id); 1720 1721 if (srng->flags & HAL_SRNG_MSI_INTR) { 1722 SRNG_DST_REG_WRITE(srng, MSI1_BASE_LSB, 1723 srng->msi_addr & 0xffffffff); 1724 reg_val = SRNG_SM(SRNG_DST_FLD(MSI1_BASE_MSB, ADDR), 1725 (uint64_t)(srng->msi_addr) >> 32) | 1726 SRNG_SM(SRNG_DST_FLD(MSI1_BASE_MSB, 1727 MSI1_ENABLE), 1); 1728 SRNG_DST_REG_WRITE(srng, MSI1_BASE_MSB, reg_val); 1729 SRNG_DST_REG_WRITE(srng, MSI1_DATA, srng->msi_data); 1730 } 1731 1732 SRNG_DST_REG_WRITE(srng, BASE_LSB, srng->ring_base_paddr & 0xffffffff); 1733 reg_val = SRNG_SM(SRNG_DST_FLD(BASE_MSB, RING_BASE_ADDR_MSB), 1734 ((uint64_t)(srng->ring_base_paddr) >> 32)) | 1735 SRNG_SM(SRNG_DST_FLD(BASE_MSB, RING_SIZE), 1736 srng->entry_size * srng->num_entries); 1737 SRNG_DST_REG_WRITE(srng, BASE_MSB, reg_val); 1738 1739 reg_val = SRNG_SM(SRNG_DST_FLD(ID, RING_ID), srng->ring_id) | 1740 SRNG_SM(SRNG_DST_FLD(ID, ENTRY_SIZE), srng->entry_size); 1741 SRNG_DST_REG_WRITE(srng, ID, reg_val); 1742 1743 1744 /** 1745 * Interrupt setup: 1746 * Default interrupt mode is 'pulse'. Need to setup SW_INTERRUPT_MODE 1747 * if level mode is required 1748 */ 1749 reg_val = 0; 1750 if (srng->intr_timer_thres_us) { 1751 reg_val |= SRNG_SM(SRNG_DST_FLD(PRODUCER_INT_SETUP, 1752 INTERRUPT_TIMER_THRESHOLD), 1753 srng->intr_timer_thres_us >> 3); 1754 } 1755 1756 if (srng->intr_batch_cntr_thres_entries) { 1757 reg_val |= SRNG_SM(SRNG_DST_FLD(PRODUCER_INT_SETUP, 1758 BATCH_COUNTER_THRESHOLD), 1759 srng->intr_batch_cntr_thres_entries * 1760 srng->entry_size); 1761 } 1762 1763 SRNG_DST_REG_WRITE(srng, PRODUCER_INT_SETUP, reg_val); 1764 hp_addr = (uint64_t)(hal->shadow_rdptr_mem_paddr + 1765 ((unsigned long)(srng->u.dst_ring.hp_addr) - 1766 (unsigned long)(hal->shadow_rdptr_mem_vaddr))); 1767 SRNG_DST_REG_WRITE(srng, HP_ADDR_LSB, hp_addr & 0xffffffff); 1768 SRNG_DST_REG_WRITE(srng, HP_ADDR_MSB, hp_addr >> 32); 1769 1770 /* Initilaize head and tail pointers to indicate ring is empty */ 1771 SRNG_DST_REG_WRITE(srng, HP, 0); 1772 SRNG_DST_REG_WRITE(srng, TP, 0); 1773 *(srng->u.dst_ring.hp_addr) = 0; 1774 1775 reg_val = ((srng->flags & HAL_SRNG_DATA_TLV_SWAP) ? 1776 SRNG_SM(SRNG_DST_FLD(MISC, DATA_TLV_SWAP_BIT), 1) : 0) | 1777 ((srng->flags & HAL_SRNG_RING_PTR_SWAP) ? 1778 SRNG_SM(SRNG_DST_FLD(MISC, HOST_FW_SWAP_BIT), 1) : 0) | 1779 ((srng->flags & HAL_SRNG_MSI_SWAP) ? 1780 SRNG_SM(SRNG_DST_FLD(MISC, MSI_SWAP_BIT), 1) : 0); 1781 1782 /* 1783 * reg_val |= SRNG_SM(SRNG_SRC_FLD(MISC, SRNG_ENABLE), 1); 1784 * todo: update fw_api and replace with above line 1785 * (when SRNG_ENABLE field for the MISC register is available in fw_api) 1786 * (WCSS_UMAC_CE_0_SRC_WFSS_CE_CHANNEL_SRC_R0_SRC_RING_MISC) 1787 */ 1788 reg_val |= 0x40; 1789 1790 SRNG_DST_REG_WRITE(srng, MISC, reg_val); 1791 1792 } 1793 1794 #define HAL_RX_WBM_ERR_SRC_GET(wbm_desc) (((*(((uint32_t *) wbm_desc)+ \ 1795 (WBM_RELEASE_RING_2_RELEASE_SOURCE_MODULE_OFFSET >> 2))) & \ 1796 WBM_RELEASE_RING_2_RELEASE_SOURCE_MODULE_MASK) >> \ 1797 WBM_RELEASE_RING_2_RELEASE_SOURCE_MODULE_LSB) 1798 1799 #define HAL_RX_WBM_REO_PUSH_REASON_GET(wbm_desc) (((*(((uint32_t *) wbm_desc)+ \ 1800 (WBM_RELEASE_RING_2_REO_PUSH_REASON_OFFSET >> 2))) & \ 1801 WBM_RELEASE_RING_2_REO_PUSH_REASON_MASK) >> \ 1802 WBM_RELEASE_RING_2_REO_PUSH_REASON_LSB) 1803 1804 #define HAL_RX_WBM_REO_ERROR_CODE_GET(wbm_desc) (((*(((uint32_t *) wbm_desc)+ \ 1805 (WBM_RELEASE_RING_2_REO_ERROR_CODE_OFFSET >> 2))) & \ 1806 WBM_RELEASE_RING_2_REO_ERROR_CODE_MASK) >> \ 1807 WBM_RELEASE_RING_2_REO_ERROR_CODE_LSB) 1808 1809 #define HAL_RX_WBM_RXDMA_PUSH_REASON_GET(wbm_desc) \ 1810 (((*(((uint32_t *) wbm_desc) + \ 1811 (WBM_RELEASE_RING_2_RXDMA_PUSH_REASON_OFFSET >> 2))) & \ 1812 WBM_RELEASE_RING_2_RXDMA_PUSH_REASON_MASK) >> \ 1813 WBM_RELEASE_RING_2_RXDMA_PUSH_REASON_LSB) 1814 1815 #define HAL_RX_WBM_RXDMA_ERROR_CODE_GET(wbm_desc) \ 1816 (((*(((uint32_t *) wbm_desc) + \ 1817 (WBM_RELEASE_RING_2_RXDMA_ERROR_CODE_OFFSET >> 2))) & \ 1818 WBM_RELEASE_RING_2_RXDMA_ERROR_CODE_MASK) >> \ 1819 WBM_RELEASE_RING_2_RXDMA_ERROR_CODE_LSB) 1820 1821 /** 1822 * hal_rx_wbm_err_info_get_generic(): Retrieves WBM error code and reason and 1823 * save it to hal_wbm_err_desc_info structure passed by caller 1824 * @wbm_desc: wbm ring descriptor 1825 * @wbm_er_info1: hal_wbm_err_desc_info structure, output parameter. 1826 * Return: void 1827 */ 1828 static inline void hal_rx_wbm_err_info_get_generic(void *wbm_desc, 1829 void *wbm_er_info1) 1830 { 1831 struct hal_wbm_err_desc_info *wbm_er_info = 1832 (struct hal_wbm_err_desc_info *)wbm_er_info1; 1833 1834 wbm_er_info->wbm_err_src = HAL_RX_WBM_ERR_SRC_GET(wbm_desc); 1835 wbm_er_info->reo_psh_rsn = HAL_RX_WBM_REO_PUSH_REASON_GET(wbm_desc); 1836 wbm_er_info->reo_err_code = HAL_RX_WBM_REO_ERROR_CODE_GET(wbm_desc); 1837 wbm_er_info->rxdma_psh_rsn = HAL_RX_WBM_RXDMA_PUSH_REASON_GET(wbm_desc); 1838 wbm_er_info->rxdma_err_code = HAL_RX_WBM_RXDMA_ERROR_CODE_GET(wbm_desc); 1839 } 1840 1841 /** 1842 * hal_tx_comp_get_release_reason_generic() - TQM Release reason 1843 * @hal_desc: completion ring descriptor pointer 1844 * 1845 * This function will return the type of pointer - buffer or descriptor 1846 * 1847 * Return: buffer type 1848 */ 1849 static inline uint8_t hal_tx_comp_get_release_reason_generic(void *hal_desc) 1850 { 1851 uint32_t comp_desc = 1852 *(uint32_t *) (((uint8_t *) hal_desc) + 1853 WBM_RELEASE_RING_2_TQM_RELEASE_REASON_OFFSET); 1854 1855 return (comp_desc & WBM_RELEASE_RING_2_TQM_RELEASE_REASON_MASK) >> 1856 WBM_RELEASE_RING_2_TQM_RELEASE_REASON_LSB; 1857 } 1858 1859 /** 1860 * hal_rx_dump_mpdu_start_tlv_generic: dump RX mpdu_start TLV in structured 1861 * human readable format. 1862 * @mpdu_start: pointer the rx_attention TLV in pkt. 1863 * @dbg_level: log level. 1864 * 1865 * Return: void 1866 */ 1867 static inline void hal_rx_dump_mpdu_start_tlv_generic(void *mpdustart, 1868 uint8_t dbg_level) 1869 { 1870 struct rx_mpdu_start *mpdu_start = (struct rx_mpdu_start *)mpdustart; 1871 struct rx_mpdu_info *mpdu_info = 1872 (struct rx_mpdu_info *)&mpdu_start->rx_mpdu_info_details; 1873 1874 hal_verbose_debug( 1875 "rx_mpdu_start tlv (1/5) - " 1876 "rxpcu_mpdu_filter_in_category: %x " 1877 "sw_frame_group_id: %x " 1878 "ndp_frame: %x " 1879 "phy_err: %x " 1880 "phy_err_during_mpdu_header: %x " 1881 "protocol_version_err: %x " 1882 "ast_based_lookup_valid: %x " 1883 "phy_ppdu_id: %x " 1884 "ast_index: %x " 1885 "sw_peer_id: %x " 1886 "mpdu_frame_control_valid: %x " 1887 "mpdu_duration_valid: %x " 1888 "mac_addr_ad1_valid: %x " 1889 "mac_addr_ad2_valid: %x " 1890 "mac_addr_ad3_valid: %x " 1891 "mac_addr_ad4_valid: %x " 1892 "mpdu_sequence_control_valid: %x " 1893 "mpdu_qos_control_valid: %x " 1894 "mpdu_ht_control_valid: %x " 1895 "frame_encryption_info_valid: %x ", 1896 mpdu_info->rxpcu_mpdu_filter_in_category, 1897 mpdu_info->sw_frame_group_id, 1898 mpdu_info->ndp_frame, 1899 mpdu_info->phy_err, 1900 mpdu_info->phy_err_during_mpdu_header, 1901 mpdu_info->protocol_version_err, 1902 mpdu_info->ast_based_lookup_valid, 1903 mpdu_info->phy_ppdu_id, 1904 mpdu_info->ast_index, 1905 mpdu_info->sw_peer_id, 1906 mpdu_info->mpdu_frame_control_valid, 1907 mpdu_info->mpdu_duration_valid, 1908 mpdu_info->mac_addr_ad1_valid, 1909 mpdu_info->mac_addr_ad2_valid, 1910 mpdu_info->mac_addr_ad3_valid, 1911 mpdu_info->mac_addr_ad4_valid, 1912 mpdu_info->mpdu_sequence_control_valid, 1913 mpdu_info->mpdu_qos_control_valid, 1914 mpdu_info->mpdu_ht_control_valid, 1915 mpdu_info->frame_encryption_info_valid); 1916 1917 hal_verbose_debug( 1918 "rx_mpdu_start tlv (2/5) - " 1919 "fr_ds: %x " 1920 "to_ds: %x " 1921 "encrypted: %x " 1922 "mpdu_retry: %x " 1923 "mpdu_sequence_number: %x " 1924 "epd_en: %x " 1925 "all_frames_shall_be_encrypted: %x " 1926 "encrypt_type: %x " 1927 "mesh_sta: %x " 1928 "bssid_hit: %x " 1929 "bssid_number: %x " 1930 "tid: %x " 1931 "pn_31_0: %x " 1932 "pn_63_32: %x " 1933 "pn_95_64: %x " 1934 "pn_127_96: %x " 1935 "peer_meta_data: %x " 1936 "rxpt_classify_info.reo_destination_indication: %x " 1937 "rxpt_classify_info.use_flow_id_toeplitz_clfy: %x " 1938 "rx_reo_queue_desc_addr_31_0: %x ", 1939 mpdu_info->fr_ds, 1940 mpdu_info->to_ds, 1941 mpdu_info->encrypted, 1942 mpdu_info->mpdu_retry, 1943 mpdu_info->mpdu_sequence_number, 1944 mpdu_info->epd_en, 1945 mpdu_info->all_frames_shall_be_encrypted, 1946 mpdu_info->encrypt_type, 1947 mpdu_info->mesh_sta, 1948 mpdu_info->bssid_hit, 1949 mpdu_info->bssid_number, 1950 mpdu_info->tid, 1951 mpdu_info->pn_31_0, 1952 mpdu_info->pn_63_32, 1953 mpdu_info->pn_95_64, 1954 mpdu_info->pn_127_96, 1955 mpdu_info->peer_meta_data, 1956 mpdu_info->rxpt_classify_info_details.reo_destination_indication, 1957 mpdu_info->rxpt_classify_info_details.use_flow_id_toeplitz_clfy, 1958 mpdu_info->rx_reo_queue_desc_addr_31_0); 1959 1960 hal_verbose_debug( 1961 "rx_mpdu_start tlv (3/5) - " 1962 "rx_reo_queue_desc_addr_39_32: %x " 1963 "receive_queue_number: %x " 1964 "pre_delim_err_warning: %x " 1965 "first_delim_err: %x " 1966 "key_id_octet: %x " 1967 "new_peer_entry: %x " 1968 "decrypt_needed: %x " 1969 "decap_type: %x " 1970 "rx_insert_vlan_c_tag_padding: %x " 1971 "rx_insert_vlan_s_tag_padding: %x " 1972 "strip_vlan_c_tag_decap: %x " 1973 "strip_vlan_s_tag_decap: %x " 1974 "pre_delim_count: %x " 1975 "ampdu_flag: %x " 1976 "bar_frame: %x " 1977 "mpdu_length: %x " 1978 "first_mpdu: %x " 1979 "mcast_bcast: %x " 1980 "ast_index_not_found: %x " 1981 "ast_index_timeout: %x ", 1982 mpdu_info->rx_reo_queue_desc_addr_39_32, 1983 mpdu_info->receive_queue_number, 1984 mpdu_info->pre_delim_err_warning, 1985 mpdu_info->first_delim_err, 1986 mpdu_info->key_id_octet, 1987 mpdu_info->new_peer_entry, 1988 mpdu_info->decrypt_needed, 1989 mpdu_info->decap_type, 1990 mpdu_info->rx_insert_vlan_c_tag_padding, 1991 mpdu_info->rx_insert_vlan_s_tag_padding, 1992 mpdu_info->strip_vlan_c_tag_decap, 1993 mpdu_info->strip_vlan_s_tag_decap, 1994 mpdu_info->pre_delim_count, 1995 mpdu_info->ampdu_flag, 1996 mpdu_info->bar_frame, 1997 mpdu_info->mpdu_length, 1998 mpdu_info->first_mpdu, 1999 mpdu_info->mcast_bcast, 2000 mpdu_info->ast_index_not_found, 2001 mpdu_info->ast_index_timeout); 2002 2003 hal_verbose_debug( 2004 "rx_mpdu_start tlv (4/5) - " 2005 "power_mgmt: %x " 2006 "non_qos: %x " 2007 "null_data: %x " 2008 "mgmt_type: %x " 2009 "ctrl_type: %x " 2010 "more_data: %x " 2011 "eosp: %x " 2012 "fragment_flag: %x " 2013 "order: %x " 2014 "u_apsd_trigger: %x " 2015 "encrypt_required: %x " 2016 "directed: %x " 2017 "mpdu_frame_control_field: %x " 2018 "mpdu_duration_field: %x " 2019 "mac_addr_ad1_31_0: %x " 2020 "mac_addr_ad1_47_32: %x " 2021 "mac_addr_ad2_15_0: %x " 2022 "mac_addr_ad2_47_16: %x " 2023 "mac_addr_ad3_31_0: %x " 2024 "mac_addr_ad3_47_32: %x ", 2025 mpdu_info->power_mgmt, 2026 mpdu_info->non_qos, 2027 mpdu_info->null_data, 2028 mpdu_info->mgmt_type, 2029 mpdu_info->ctrl_type, 2030 mpdu_info->more_data, 2031 mpdu_info->eosp, 2032 mpdu_info->fragment_flag, 2033 mpdu_info->order, 2034 mpdu_info->u_apsd_trigger, 2035 mpdu_info->encrypt_required, 2036 mpdu_info->directed, 2037 mpdu_info->mpdu_frame_control_field, 2038 mpdu_info->mpdu_duration_field, 2039 mpdu_info->mac_addr_ad1_31_0, 2040 mpdu_info->mac_addr_ad1_47_32, 2041 mpdu_info->mac_addr_ad2_15_0, 2042 mpdu_info->mac_addr_ad2_47_16, 2043 mpdu_info->mac_addr_ad3_31_0, 2044 mpdu_info->mac_addr_ad3_47_32); 2045 2046 hal_verbose_debug( 2047 "rx_mpdu_start tlv (5/5) - " 2048 "mpdu_sequence_control_field: %x " 2049 "mac_addr_ad4_31_0: %x " 2050 "mac_addr_ad4_47_32: %x " 2051 "mpdu_qos_control_field: %x " 2052 "mpdu_ht_control_field: %x ", 2053 mpdu_info->mpdu_sequence_control_field, 2054 mpdu_info->mac_addr_ad4_31_0, 2055 mpdu_info->mac_addr_ad4_47_32, 2056 mpdu_info->mpdu_qos_control_field, 2057 mpdu_info->mpdu_ht_control_field); 2058 } 2059 2060 /** 2061 * hal_tx_desc_set_search_type - Set the search type value 2062 * @desc: Handle to Tx Descriptor 2063 * @search_type: search type 2064 * 0 – Normal search 2065 * 1 – Index based address search 2066 * 2 – Index based flow search 2067 * 2068 * Return: void 2069 */ 2070 #ifdef TCL_DATA_CMD_2_SEARCH_TYPE_OFFSET 2071 static void hal_tx_desc_set_search_type_generic(void *desc, 2072 uint8_t search_type) 2073 { 2074 HAL_SET_FLD(desc, TCL_DATA_CMD_2, SEARCH_TYPE) |= 2075 HAL_TX_SM(TCL_DATA_CMD_2, SEARCH_TYPE, search_type); 2076 } 2077 #else 2078 static void hal_tx_desc_set_search_type_generic(void *desc, 2079 uint8_t search_type) 2080 { 2081 } 2082 2083 #endif 2084 2085 /** 2086 * hal_tx_desc_set_search_index - Set the search index value 2087 * @desc: Handle to Tx Descriptor 2088 * @search_index: The index that will be used for index based address or 2089 * flow search. The field is valid when 'search_type' is 2090 * 1 0r 2 2091 * 2092 * Return: void 2093 */ 2094 #ifdef TCL_DATA_CMD_5_SEARCH_INDEX_OFFSET 2095 static void hal_tx_desc_set_search_index_generic(void *desc, 2096 uint32_t search_index) 2097 { 2098 HAL_SET_FLD(desc, TCL_DATA_CMD_5, SEARCH_INDEX) |= 2099 HAL_TX_SM(TCL_DATA_CMD_5, SEARCH_INDEX, search_index); 2100 } 2101 #else 2102 static void hal_tx_desc_set_search_index_generic(void *desc, 2103 uint32_t search_index) 2104 { 2105 } 2106 #endif 2107 2108 /** 2109 * hal_tx_desc_set_cache_set_num_generic - Set the cache-set-num value 2110 * @desc: Handle to Tx Descriptor 2111 * @cache_num: Cache set number that should be used to cache the index 2112 * based search results, for address and flow search. 2113 * This value should be equal to LSB four bits of the hash value 2114 * of match data, in case of search index points to an entry 2115 * which may be used in content based search also. The value can 2116 * be anything when the entry pointed by search index will not be 2117 * used for content based search. 2118 * 2119 * Return: void 2120 */ 2121 #ifdef TCL_DATA_CMD_5_CACHE_SET_NUM_OFFSET 2122 static void hal_tx_desc_set_cache_set_num_generic(void *desc, 2123 uint8_t cache_num) 2124 { 2125 HAL_SET_FLD(desc, TCL_DATA_CMD_5, CACHE_SET_NUM) |= 2126 HAL_TX_SM(TCL_DATA_CMD_5, CACHE_SET_NUM, cache_num); 2127 } 2128 #else 2129 static void hal_tx_desc_set_cache_set_num_generic(void *desc, 2130 uint8_t cache_num) 2131 { 2132 } 2133 #endif 2134 2135 /** 2136 * hal_tx_set_pcp_tid_map_generic() - Configure default PCP to TID map table 2137 * @soc: HAL SoC context 2138 * @map: PCP-TID mapping table 2139 * 2140 * PCP are mapped to 8 TID values using TID values programmed 2141 * in one set of mapping registers PCP_TID_MAP_<0 to 6> 2142 * The mapping register has TID mapping for 8 PCP values 2143 * 2144 * Return: none 2145 */ 2146 static void hal_tx_set_pcp_tid_map_generic(struct hal_soc *soc, uint8_t *map) 2147 { 2148 uint32_t addr, value; 2149 2150 addr = HWIO_TCL_R0_PCP_TID_MAP_ADDR( 2151 SEQ_WCSS_UMAC_MAC_TCL_REG_OFFSET); 2152 2153 value = (map[0] | 2154 (map[1] << HWIO_TCL_R0_PCP_TID_MAP_PCP_1_SHFT) | 2155 (map[2] << HWIO_TCL_R0_PCP_TID_MAP_PCP_2_SHFT) | 2156 (map[3] << HWIO_TCL_R0_PCP_TID_MAP_PCP_3_SHFT) | 2157 (map[4] << HWIO_TCL_R0_PCP_TID_MAP_PCP_4_SHFT) | 2158 (map[5] << HWIO_TCL_R0_PCP_TID_MAP_PCP_5_SHFT) | 2159 (map[6] << HWIO_TCL_R0_PCP_TID_MAP_PCP_6_SHFT) | 2160 (map[7] << HWIO_TCL_R0_PCP_TID_MAP_PCP_7_SHFT)); 2161 2162 HAL_REG_WRITE(soc, addr, (value & HWIO_TCL_R0_PCP_TID_MAP_RMSK)); 2163 } 2164 2165 /** 2166 * hal_tx_update_pcp_tid_generic() - Update the pcp tid map table with 2167 * value received from user-space 2168 * @soc: HAL SoC context 2169 * @pcp: pcp value 2170 * @tid : tid value 2171 * 2172 * Return: void 2173 */ 2174 static 2175 void hal_tx_update_pcp_tid_generic(struct hal_soc *soc, 2176 uint8_t pcp, uint8_t tid) 2177 { 2178 uint32_t addr, value, regval; 2179 2180 addr = HWIO_TCL_R0_PCP_TID_MAP_ADDR( 2181 SEQ_WCSS_UMAC_MAC_TCL_REG_OFFSET); 2182 2183 value = (uint32_t)tid << (HAL_TX_BITS_PER_TID * pcp); 2184 2185 /* Read back previous PCP TID config and update 2186 * with new config. 2187 */ 2188 regval = HAL_REG_READ(soc, addr); 2189 regval &= ~(HAL_TX_TID_BITS_MASK << (HAL_TX_BITS_PER_TID * pcp)); 2190 regval |= value; 2191 2192 HAL_REG_WRITE(soc, addr, 2193 (regval & HWIO_TCL_R0_PCP_TID_MAP_RMSK)); 2194 } 2195 2196 /** 2197 * hal_tx_update_tidmap_prty_generic() - Update the tid map priority 2198 * @soc: HAL SoC context 2199 * @val: priority value 2200 * 2201 * Return: void 2202 */ 2203 static 2204 void hal_tx_update_tidmap_prty_generic(struct hal_soc *soc, uint8_t value) 2205 { 2206 uint32_t addr; 2207 2208 addr = HWIO_TCL_R0_TID_MAP_PRTY_ADDR( 2209 SEQ_WCSS_UMAC_MAC_TCL_REG_OFFSET); 2210 2211 HAL_REG_WRITE(soc, addr, 2212 (value & HWIO_TCL_R0_TID_MAP_PRTY_RMSK)); 2213 } 2214 2215 #endif /* _HAL_GENERIC_API_H_ */ 2216