diff options
author | Srinivas Girigowda <quic_sgirigow@quicinc.com> | 2019-03-28 16:37:13 -0700 |
---|---|---|
committer | Sunil Ravi <sunilravi@google.com> | 2019-04-02 21:08:41 +0000 |
commit | d9e4d7c698fda8db6f2532f370185eaeac3ca910 (patch) | |
tree | de3a73d4e08f71626f636dbe6786a310f56f543b /qcwcn | |
parent | 275cf8ba9ecf957cc18c302c3555ddeb43b66c75 (diff) | |
download | wlan-d9e4d7c698fda8db6f2532f370185eaeac3ca910.tar.gz |
Revert "Revert "Wifi-hal: TX Per Packet stats for V2 version.""
This reverts commit 41d7798f68a93664a836c8b86c23addd3db9d17f.
Bug: 129272032
Bug: 118484168
Test: Connect STA to AP and play youtube.
Change-Id: If86b053c4e083cf1c01e7d7293d79706c6bb093e
Diffstat (limited to 'qcwcn')
-rw-r--r-- | qcwcn/wifi_hal/common.h | 8 | ||||
-rw-r--r-- | qcwcn/wifi_hal/pkt_stats.h | 195 | ||||
-rw-r--r-- | qcwcn/wifi_hal/wifi_hal.cpp | 21 | ||||
-rw-r--r-- | qcwcn/wifi_hal/wifilogger.cpp | 3 | ||||
-rw-r--r-- | qcwcn/wifi_hal/wifilogger_diag.cpp | 264 |
5 files changed, 479 insertions, 12 deletions
diff --git a/qcwcn/wifi_hal/common.h b/qcwcn/wifi_hal/common.h index c847313..0b3a765 100644 --- a/qcwcn/wifi_hal/common.h +++ b/qcwcn/wifi_hal/common.h @@ -94,6 +94,13 @@ typedef struct { size_t flags_len; } features_info; +enum pkt_log_version { + PKT_LOG_V0 = 0, // UNSPECIFIED Target + PKT_LOG_V1 = 1, // ROME Base Target + PKT_LOG_V2 = 2, // HELIUM Base Target + PKT_LOG_V3 = 3, // LETHIUM Base target +}; + struct gscan_event_handlers_s; struct rssi_monitor_event_handler_s; struct cld80211_ctx; @@ -154,6 +161,7 @@ typedef struct hal_info_s { wifi_capa capa; struct cld80211_ctx *cldctx; bool apf_enabled; + pkt_log_version pkt_log_ver; } hal_info; wifi_error wifi_register_handler(wifi_handle handle, int cmd, nl_recvmsg_msg_cb_t func, void *arg); diff --git a/qcwcn/wifi_hal/pkt_stats.h b/qcwcn/wifi_hal/pkt_stats.h index d1cc71a..88a58c0 100644 --- a/qcwcn/wifi_hal/pkt_stats.h +++ b/qcwcn/wifi_hal/pkt_stats.h @@ -50,6 +50,9 @@ #define BW_OFFSET 8 #define INVALID_RSSI 255 +/* Based on pkt log V2, this type of event will triggered */ +#define PKTLOG_TYPE_PKT_SW_EVENT 10 + #define PKT_INFO_FLG_TX_LOCAL_S 0x1 #define PKT_INFO_FLG_RX_HOST_RXD 0x2 #define PKT_INFO_FLG_TX_REMOTE_S 0x4 @@ -63,6 +66,30 @@ #define PKT_INFO_FLG_UNKNOWN_S 0x400 #define PKT_INFO_FLG_PKT_DUMP_V2 0x8000 +/* Depend on packet log version V2 this + * offset are define, for more info need to + * check from firmware side. + */ +#define TX_SUCCESS_TMS_OFFSET 56 +#define LINK_LAYER_TX_SQN_OFFSET 66 +#define RATE_CODE_OFFSET 68 +#define TX_STATUS_OFFSET 70 +#define TX_RSSI_OFFSET 71 +#define NO_RETRIES_OFFSET 75 +#define EXT_FLAGS_OFFSET 76 +#define BMAP_FAILED_OFFSET 84 +#define BMAP_ENQUEUED_OFFSET 92 +#define FRAME_CTRL_OFFSET 216 +#define QOS_CTRL_OFFSET 218 + +/* MAX HT/VHT mcs index */ +#define MAX_VHT_MCS_IDX 10 +#define MAX_HT_MCS_IDX 8 + +/* MAX CCK/OFDM rate index */ +#define MAX_CCK_MCS_IDX 4 +#define MAX_OFDM_MCS_IDX 8 + /* MASK value of flags based on RX_STAT content. * These are the events that carry Rx decriptor */ @@ -86,7 +113,8 @@ typedef struct { typedef struct { u16 flags; u16 missed_cnt; - u16 log_type; + u16 log_type : 8; //[7:0] + u16 mac_id : 8; //[15:8] u16 size; u32 timestamp; u32 reserved; @@ -323,6 +351,171 @@ typedef struct { * if any event is missed. */ +/* PKT_LOG_V2 Base strcuture used to parse buffer */ +typedef struct { + u16 frm_ctrl; + u8 tx_ok; + u16 qos_ctrl; + u64 bmap_failed; + u64 bmap_enqueued; +} __attribute__((packed)) node_pkt_stats; + +typedef u8 A_RATECODE; + +/* Rate Code as per PKT_LOG_V2 Version */ +typedef struct { + A_RATECODE rateCode; + u8 flags; +} RATE_CODE; + +/* bandwidht type*/ +typedef enum { + BW_20MHZ, + BW_40MHZ, + BW_80MHZ, + BW_160MHZ, +} bandwidth; + +/* Preamble type*/ +typedef enum { + WIFI_HW_RATECODE_PREAM_OFDM = 0, + WIFI_HW_RATECODE_PREAM_CCK = 1, + WIFI_HW_RATECODE_PREAM_HT = 2, + WIFI_HW_RATECODE_PREAM_VHT = 3, + WIFI_HW_RATECODE_PREAM_COUNT, +} WIFI_HW_RATECODE_PREAM_TYPE; + +/** + * struct index_data_rate_type - non vht data rate type + * @rate_index: cck rate index + * @cck_rate: CCK supported rate table + */ +struct index_data_rate_cck_type { + uint8_t rate_index; + uint16_t cck_rate[2]; +}; + +/** + * struct index_data_rate_type - non vht data rate type + * @rate_index: ofdm rate index + * @ofdm__rate: OFDM supported rate table + */ +struct index_data_rate_ofdm_type { + uint8_t rate_index; + uint16_t ofdm_rate[2]; +}; + +/*Below CCK/OFDM table refer from firmware Arch */ +/* Rate Table Based on CCK */ +static struct index_data_rate_cck_type cck_mcs_nss1[] = { + /*RC LKbps SKbps */ + {0x40, {11000, 11000} }, + {0x41, {5500, 5500} }, + {0x42, {2000, 2000} }, + {0x43, {1000, 1000} } +}; + +/* Rate Table Based on OFDM */ +static struct index_data_rate_ofdm_type ofdm_mcs_nss1[] = { + /*RC LKbps SKbps */ + {0x00, {48000, 48000} }, + {0x01, {34000, 24000} }, + {0x02, {12000, 12000} }, + {0x03, {6000, 6000} }, + {0x04, {54000, 54000} }, + {0x05, {36000, 36000} }, + {0x06, {18000, 18000} }, + {0x07, {9000, 9000} } +}; + +/** + * struct index_data_rate_type - non vht data rate type + * @mcs_index: mcs rate index + * @ht20_rate: HT20 supported rate table + * @ht40_rate: HT40 supported rate table + */ +struct index_data_rate_type { + uint8_t mcs_index; + uint16_t ht20_rate[2]; + uint16_t ht40_rate[2]; +}; + +/** + * struct index_vht_data_rate_type - vht data rate type + * @mcs_index: mcs rate index + * @ht20_rate: VHT20 supported rate table + * @ht40_rate: VHT40 supported rate table + * @ht80_rate: VHT80 supported rate table + */ +struct index_vht_data_rate_type { + uint8_t mcs_index; + uint16_t ht20_rate[2]; + uint16_t ht40_rate[2]; + uint16_t ht80_rate[2]; +}; + +/*Below HT/VHT table refer from Host Driver + * MCS Based rate table + * HT MCS parameters with Nss = 1 + */ +static struct index_data_rate_type mcs_nss1[] = { + /* MCS L20 S20 L40 S40 */ + {0, {65, 72}, {135, 150 } }, + {1, {130, 144}, {270, 300 } }, + {2, {195, 217}, {405, 450 } }, + {3, {260, 289}, {540, 600 } }, + {4, {390, 433}, {815, 900 } }, + {5, {520, 578}, {1080, 1200} }, + {6, {585, 650}, {1215, 1350} }, + {7, {650, 722}, {1350, 1500} } +}; + +/* HT MCS parameters with Nss = 2 */ +static struct index_data_rate_type mcs_nss2[] = { + /* MCS L20 S20 L40 S40 */ + {0, {130, 144}, {270, 300 } }, + {1, {260, 289}, {540, 600 } }, + {2, {390, 433}, {810, 900 } }, + {3, {520, 578}, {1080, 1200} }, + {4, {780, 867}, {1620, 1800} }, + {5, {1040, 1156}, {2160, 2400} }, + {6, {1170, 1300}, {2430, 2700} }, + {7, {1300, 1440}, {2700, 3000} } +}; + +/* MCS Based VHT rate table + * MCS parameters with Nss = 1 + */ +static struct index_vht_data_rate_type vht_mcs_nss1[] = { + /* MCS L20 S20 L40 S40 L80 S80 */ + {0, {65, 72 }, {135, 150}, {293, 325} }, + {1, {130, 144}, {270, 300}, {585, 650} }, + {2, {195, 217}, {405, 450}, {878, 975} }, + {3, {260, 289}, {540, 600}, {1170, 1300} }, + {4, {390, 433}, {810, 900}, {1755, 1950} }, + {5, {520, 578}, {1080, 1200}, {2340, 2600} }, + {6, {585, 650}, {1215, 1350}, {2633, 2925} }, + {7, {650, 722}, {1350, 1500}, {2925, 3250} }, + {8, {780, 867}, {1620, 1800}, {3510, 3900} }, + {9, {865, 960}, {1800, 2000}, {3900, 4333} } +}; + +/*MCS parameters with Nss = 2*/ +static struct index_vht_data_rate_type vht_mcs_nss2[] = { + /* MCS L20 S20 L40 S40 L80 S80 */ + {0, {130, 144}, {270, 300}, { 585, 650} }, + {1, {260, 289}, {540, 600}, {1170, 1300} }, + {2, {390, 433}, {810, 900}, {1755, 1950} }, + {3, {520, 578}, {1080, 1200}, {2340, 2600} }, + {4, {780, 867}, {1620, 1800}, {3510, 3900} }, + {5, {1040, 1156}, {2160, 2400}, {4680, 5200} }, + {6, {1170, 1300}, {2430, 2700}, {5265, 5850} }, + {7, {1300, 1444}, {2700, 3000}, {5850, 6500} }, + {8, {1560, 1733}, {3240, 3600}, {7020, 7800} }, + {9, {1730, 1920}, {3600, 4000}, {7800, 8667} } +}; +/*********************************************************/ + #define RING_BUF_ENTRY_SIZE 512 #define PKT_STATS_BUF_SIZE 128 struct pkt_stats_s { diff --git a/qcwcn/wifi_hal/wifi_hal.cpp b/qcwcn/wifi_hal/wifi_hal.cpp index 8834bba..0881c0b 100644 --- a/qcwcn/wifi_hal/wifi_hal.cpp +++ b/qcwcn/wifi_hal/wifi_hal.cpp @@ -65,6 +65,7 @@ #define WIFI_HAL_CMD_SOCK_PORT 644 #define WIFI_HAL_EVENT_SOCK_PORT 645 +#define MAX_HW_VER_LENGTH 100 /* * Defines for wifi_wait_for_driver_ready() * Specify durations between polls and max wait time @@ -494,6 +495,8 @@ wifi_error wifi_initialize(wifi_handle *handle) struct nl_cb *cb = NULL; int status = 0; int index; + char hw_ver_type[MAX_HW_VER_LENGTH]; + char *hw_name = NULL; ALOGI("Initializing wifi"); hal_info *info = (hal_info *)malloc(sizeof(hal_info)); @@ -670,6 +673,24 @@ wifi_error wifi_initialize(wifi_handle *handle) if (ret != WIFI_SUCCESS) ALOGE("Failed to get supported logger feature set: %d", ret); + ret = wifi_get_firmware_version(iface_handle, hw_ver_type, + MAX_HW_VER_LENGTH); + if (ret == WIFI_SUCCESS) { + hw_name = strstr(hw_ver_type, "HW:"); + if (hw_name) { + hw_name += strlen("HW:"); + if (strncmp(hw_name, "QCA6174", 7) == 0) + info->pkt_log_ver = PKT_LOG_V1; + else + info->pkt_log_ver = PKT_LOG_V2; + } else { + info->pkt_log_ver = PKT_LOG_V0; + } + ALOGV("%s: hardware version type %d", __func__, info->pkt_log_ver); + } else { + ALOGE("Failed to get supported logger feature set: %d", ret); + } + ret = get_firmware_bus_max_size_supported(iface_handle); if (ret != WIFI_SUCCESS) { ALOGE("Failed to get supported bus size, error : %d", ret); diff --git a/qcwcn/wifi_hal/wifilogger.cpp b/qcwcn/wifi_hal/wifilogger.cpp index 38aad86..7e8efe6 100644 --- a/qcwcn/wifi_hal/wifilogger.cpp +++ b/qcwcn/wifi_hal/wifilogger.cpp @@ -147,7 +147,8 @@ wifi_error wifi_start_logging(wifi_interface_handle iface, if (ret != WIFI_SUCCESS) ALOGE("%s: Error %d happened. ", __FUNCTION__, ret); - ALOGV("%s: Logging Started for %s.", __FUNCTION__, buffer_name); + ALOGV("%s: Logging Started for %s. with verboselevel %d", + __FUNCTION__, buffer_name,verbose_level); rb_start_logging(&info->rb_infos[ring_id], verbose_level, flags, max_interval_sec, min_data_size); cleanup: diff --git a/qcwcn/wifi_hal/wifilogger_diag.cpp b/qcwcn/wifi_hal/wifilogger_diag.cpp index 34d8549..3714c54 100644 --- a/qcwcn/wifi_hal/wifilogger_diag.cpp +++ b/qcwcn/wifi_hal/wifilogger_diag.cpp @@ -1321,6 +1321,85 @@ static wifi_error update_stats_to_ring_buf(hal_info *info, return WIFI_SUCCESS; } +static u16 get_rate_v1(u16 mcs_r) +{ + MCS mcs; + int index = 0; + u16 tx_rate = 0; + u8 nss; + + mcs.mcs = mcs_r; + nss = mcs.mcs_s.nss + 1; + + switch (mcs.mcs_s.preamble) { + case WIFI_HW_RATECODE_PREAM_OFDM: + for (index = 0; index < MAX_OFDM_MCS_IDX; index++) { + if ((mcs.mcs_s.rate & 0xF) == index) + tx_rate = (u16) ofdm_mcs_nss1[index].ofdm_rate[mcs.mcs_s.short_gi] / 1000; + } + break; + case WIFI_HW_RATECODE_PREAM_CCK: + for (index = 0; index < MAX_CCK_MCS_IDX; index++) { + if ((mcs.mcs_s.rate & 0xF) == index) + tx_rate = (u16) cck_mcs_nss1[index].cck_rate[mcs.mcs_s.short_gi] / 1000; + } + break; + case WIFI_HW_RATECODE_PREAM_HT: + if (nss == 1) { + for (index = 0; index < MAX_HT_MCS_IDX; index++) { + if (mcs.mcs_s.rate == index) { + if (mcs.mcs_s.bw == BW_20MHZ) + tx_rate = (u16) mcs_nss1[index].ht20_rate[mcs.mcs_s.short_gi] / 10; + if (mcs.mcs_s.bw == BW_40MHZ) + tx_rate = (u16) mcs_nss1[index].ht40_rate[mcs.mcs_s.short_gi] / 10; + } + } + } else if (nss == 2) { + for (index = 0; index < MAX_HT_MCS_IDX; index++) { + if (mcs.mcs_s.rate == index) { + if (mcs.mcs_s.bw == BW_20MHZ) + tx_rate = (u16) mcs_nss2[index].ht20_rate[mcs.mcs_s.short_gi] / 10; + if (mcs.mcs_s.bw == BW_40MHZ) + tx_rate = (u16) mcs_nss2[index].ht40_rate[mcs.mcs_s.short_gi] / 10; + } + } + } else { + ALOGE("Unexpected nss %d", nss); + } + break; + case WIFI_HW_RATECODE_PREAM_VHT: + if (nss == 1) { + for (index = 0; index < MAX_VHT_MCS_IDX; index++) { + if (mcs.mcs_s.rate == index) { + if (mcs.mcs_s.bw == BW_20MHZ) + tx_rate = (u16) vht_mcs_nss1[index].ht20_rate[mcs.mcs_s.short_gi] / 10; + if (mcs.mcs_s.bw == BW_40MHZ) + tx_rate = (u16) vht_mcs_nss1[index].ht40_rate[mcs.mcs_s.short_gi] / 10; + if (mcs.mcs_s.bw == BW_80MHZ) + tx_rate = (u16) vht_mcs_nss1[index].ht40_rate[mcs.mcs_s.short_gi] / 10; + } + } + } else if (nss == 2) { + for (index = 0; index < MAX_VHT_MCS_IDX; index++) { + if (mcs.mcs_s.rate == index) { + if (mcs.mcs_s.bw == BW_20MHZ) + tx_rate = (u16) vht_mcs_nss2[index].ht20_rate[mcs.mcs_s.short_gi] / 10; + if (mcs.mcs_s.bw == BW_40MHZ) + tx_rate = (u16) vht_mcs_nss2[index].ht40_rate[mcs.mcs_s.short_gi] / 10; + if (mcs.mcs_s.bw == BW_80MHZ) + tx_rate = (u16) vht_mcs_nss2[index].ht40_rate[mcs.mcs_s.short_gi] / 10; + } + } + } else { + ALOGE("Unexpected nss %d", nss); + } + break; + default: + ALOGE("Unexpected preamble %d", mcs.mcs_s.preamble); + } + return tx_rate; +} + static u16 get_rate(u16 mcs_r) { u16 tx_rate = 0; @@ -1551,6 +1630,25 @@ static wifi_error parse_rx_stats(hal_info *info, u8 *buf, u16 size) return status; } +static u16 get_tx_mcs_v1(u8 *data) +{ + MCS mcs; + RATE_CODE rate_code; + u16 extended_flags; + mcs.mcs = 0; + + rate_code = *((RATE_CODE*)(data + RATE_CODE_OFFSET)); + extended_flags = *((u16*)(data + EXT_FLAGS_OFFSET)); + + mcs.mcs_s.rate = rate_code.rateCode & 0xF; + mcs.mcs_s.nss = (rate_code.rateCode >> 4) & 0x3; + mcs.mcs_s.preamble = (rate_code.rateCode >> 6) & 0x3; + mcs.mcs_s.short_gi = (((extended_flags >> 12) & 0x1) == 1) ? 1 : 0; + mcs.mcs_s.bw = (rate_code.flags >> 5) & 0x3; + + return mcs.mcs; +} + static u16 get_tx_mcs(u8 series, struct tx_ppdu_start *ppdu_start) { @@ -2012,8 +2110,135 @@ static wifi_error parse_pkt_fate_stats(hal_info *info, u8 *buf, u16 size) return WIFI_SUCCESS; } +/* + * --------------------------------------------------------------------------------- + * | pkt log | packet log data contain sub packet log info | + * | header |------------------------------------------------------------------| + * | | sub pkt log | sub pkt log | sub pkt log | sub pkt log | | + * | | header | data | header | data |..... | + * |-------------------------------------------------------------------------------- + */ +static wifi_error parse_stats_sw_event(hal_info *info, + wh_pktlog_hdr_v2_t *pkt_stats_header) +{ + u32 pkt_stats_len; + int num_of_node = 0; + u8 *data; + u8 *node_pkt_data; + wh_pktlog_hdr_v2_t *pkt_stats_node_header; + int node_pkt_type,pkt_sub_type,node_pkt_len,i; + wifi_error status = WIFI_SUCCESS; + node_pkt_stats node_pkt_t; + wifi_ring_buffer_entry *pRingBufferEntry = + (wifi_ring_buffer_entry *)info->pkt_stats->tx_stats; + + wifi_ring_per_packet_status_entry *rb_pkt_stats = + (wifi_ring_per_packet_status_entry *)(pRingBufferEntry + 1); + + pkt_stats_len = pkt_stats_header->size; + data = ((u8 *)pkt_stats_header + sizeof(wh_pktlog_hdr_v2_t)); + num_of_node = (pkt_stats_header->reserved >> 16) & 0xFFFF; + pkt_sub_type = pkt_stats_header->reserved & 0xFFFF; + + do { + if (pkt_stats_len < sizeof(wh_pktlog_hdr_v2_t)) { + status = WIFI_ERROR_INVALID_ARGS; + break; + } + if (pkt_sub_type == 1) { + pkt_stats_node_header = (wh_pktlog_hdr_v2_t *)data; + if (pkt_stats_node_header) { + node_pkt_type = pkt_stats_node_header->log_type; + node_pkt_len = pkt_stats_node_header->size; + node_pkt_data = ((u8 *)pkt_stats_node_header + sizeof(wh_pktlog_hdr_v2_t)); + switch (node_pkt_type) { + case PKTLOG_TYPE_TX_CTRL: + info->pkt_stats->tx_stats_events |= BIT(PKTLOG_TYPE_TX_CTRL); + break; + case PKTLOG_TYPE_TX_STAT: + { + memset(rb_pkt_stats, 0, sizeof(wifi_ring_per_packet_status_entry)); + memset(&node_pkt_t, 0, sizeof(node_pkt_stats)); + node_pkt_t.frm_ctrl = *((u16*)(node_pkt_data + FRAME_CTRL_OFFSET)); + if (node_pkt_t.frm_ctrl & BIT(DATA_PROTECTED)) + rb_pkt_stats->flags |= PER_PACKET_ENTRY_FLAGS_PROTECTED; + rb_pkt_stats->transmit_success_timestamp = + *((u64*)(node_pkt_data + TX_SUCCESS_TMS_OFFSET)); + rb_pkt_stats->link_layer_transmit_sequence = + *((u16*)(node_pkt_data + LINK_LAYER_TX_SQN_OFFSET)); + node_pkt_t.tx_ok = *((u8*)(node_pkt_data + TX_STATUS_OFFSET)); + if (node_pkt_t.tx_ok == 0) + rb_pkt_stats->flags |= PER_PACKET_ENTRY_FLAGS_TX_SUCCESS; + rb_pkt_stats->rssi = *((u8*)(node_pkt_data + TX_RSSI_OFFSET)); + rb_pkt_stats->num_retries = *((u8*)(node_pkt_data + NO_RETRIES_OFFSET)); + node_pkt_t.qos_ctrl = *((u8*)(node_pkt_data + QOS_CTRL_OFFSET)); + rb_pkt_stats->tid = node_pkt_t.qos_ctrl & 0xF; + rb_pkt_stats->MCS = get_tx_mcs_v1(node_pkt_data); + rb_pkt_stats->last_transmit_rate = get_rate_v1(rb_pkt_stats->MCS); + node_pkt_t.bmap_failed = *((u64*)(node_pkt_data + BMAP_FAILED_OFFSET)); + node_pkt_t.bmap_enqueued = *((u64*)(node_pkt_data + BMAP_ENQUEUED_OFFSET)); + + info->pkt_stats->tx_stats_events |= BIT(PKTLOG_TYPE_TX_STAT); + rb_pkt_stats->flags |= PER_PACKET_ENTRY_FLAGS_80211_HEADER; + } + break; + } + if (info->pkt_stats->tx_stats_events & BIT(PKTLOG_TYPE_TX_STAT)) { + /* if bmap_enqueued is 1 ,Handle non aggregated cases */ + if (node_pkt_t.bmap_enqueued == 1) { + status = update_stats_to_ring_buf(info, + (u8 *)pRingBufferEntry, + sizeof(wifi_ring_buffer_entry) + + sizeof(wifi_ring_per_packet_status_entry)); + if (status != WIFI_SUCCESS) { + ALOGE("Failed to write into the ring buffer : %d", node_pkt_type); + } + } else { + /* if bmap_enqueued is more than 1 ,Handle aggregated cases */ + for (i = 0; i < MAX_BA_WINDOW_SIZE; i++) { + if (((node_pkt_t.bmap_enqueued >> i) & 0x1) == 1) { + if (((node_pkt_t.bmap_failed >> i) & 0x1) == 1) { + rb_pkt_stats->flags &= ~PER_PACKET_ENTRY_FLAGS_TX_SUCCESS; + } else { + rb_pkt_stats->flags |= PER_PACKET_ENTRY_FLAGS_TX_SUCCESS; + } + status = update_stats_to_ring_buf(info, + (u8 *)pRingBufferEntry, + sizeof(wifi_ring_buffer_entry) + + sizeof(wifi_ring_per_packet_status_entry)); + if (status != WIFI_SUCCESS) { + ALOGE("Failed to write into the ring buffer : %d", node_pkt_type); + break; + } + rb_pkt_stats->link_layer_transmit_sequence += 1; + } + } + } + } + } + pkt_stats_len = (pkt_stats_len - (sizeof(wh_pktlog_hdr_v2_t) + node_pkt_len)); + data = (u8*) (data + sizeof(wh_pktlog_hdr_v2_t) + node_pkt_len); + info->pkt_stats->tx_stats_events = 0; + } + } while (pkt_stats_len > 0); + return status; +} + +/* Added This function to parse stats based on PKT_LOG_V2 Version */ +static wifi_error parse_stats_record_v2(hal_info *info, + wh_pktlog_hdr_v2_t *pkt_stats_header) +{ + wifi_error status = WIFI_SUCCESS; + + if (pkt_stats_header->log_type == PKTLOG_TYPE_PKT_SW_EVENT) { + status = parse_stats_sw_event(info, pkt_stats_header); + } else + ALOGE("%s: invalid log_type %d",__FUNCTION__, pkt_stats_header->log_type); + + return status; +} -static wifi_error parse_stats_record(hal_info *info, +static wifi_error parse_stats_record_v1(hal_info *info, wh_pktlog_hdr_t *pkt_stats_header) { wifi_error status; @@ -2056,6 +2281,7 @@ static wifi_error parse_stats_record(hal_info *info, static wifi_error parse_stats(hal_info *info, u8 *data, u32 buflen) { wh_pktlog_hdr_t *pkt_stats_header; + wh_pktlog_hdr_v2_t *pkt_stats_header_t; wifi_error status = WIFI_SUCCESS; do { @@ -2070,18 +2296,36 @@ static wifi_error parse_stats(hal_info *info, u8 *data, u32 buflen) status = WIFI_ERROR_INVALID_ARGS; break; } - status = parse_stats_record(info, pkt_stats_header); - if (status != WIFI_SUCCESS) { - ALOGE("Failed to parse the stats type : %d", - pkt_stats_header->log_type); - return status; + /* Pkt_log_V2 based packet parsing */ + if (info->pkt_log_ver == PKT_LOG_V2) { + pkt_stats_header_t = (wh_pktlog_hdr_v2_t *)data; + status = parse_stats_record_v2(info, pkt_stats_header_t); + if (status != WIFI_SUCCESS) { + ALOGE("Failed to parse the stats type : %d", + pkt_stats_header_t->log_type); + return status; + } + /* Pkt_log_V1 based packet parsing */ + } else { + status = parse_stats_record_v1(info, pkt_stats_header); + if (status != WIFI_SUCCESS) { + ALOGE("Failed to parse the stats type : %d", + pkt_stats_header->log_type); + return status; + } } - if (pkt_stats_header->flags & PKT_INFO_FLG_PKT_DUMP_V2){ + + if (info->pkt_log_ver == PKT_LOG_V1) { + if (pkt_stats_header->flags & PKT_INFO_FLG_PKT_DUMP_V2){ + data += (sizeof(wh_pktlog_hdr_v2_t) + pkt_stats_header->size); + buflen -= (sizeof(wh_pktlog_hdr_v2_t) + pkt_stats_header->size); + } else { + data += (sizeof(wh_pktlog_hdr_t) + pkt_stats_header->size); + buflen -= (sizeof(wh_pktlog_hdr_t) + pkt_stats_header->size); + } + } else if (info->pkt_log_ver == PKT_LOG_V2) { data += (sizeof(wh_pktlog_hdr_v2_t) + pkt_stats_header->size); buflen -= (sizeof(wh_pktlog_hdr_v2_t) + pkt_stats_header->size); - } else { - data += (sizeof(wh_pktlog_hdr_t) + pkt_stats_header->size); - buflen -= (sizeof(wh_pktlog_hdr_t) + pkt_stats_header->size); } } while (buflen > 0); |