@@ -877,23 +877,32 @@ void ath11k_hal_srng_access_end(struct ath11k_base *ab, struct hal_srng *srng)
877
877
/* For LMAC rings, ring pointer updates are done through FW and
878
878
* hence written to a shared memory location that is read by FW
879
879
*/
880
- if (srng -> ring_dir == HAL_SRNG_DIR_SRC )
880
+ if (srng -> ring_dir == HAL_SRNG_DIR_SRC ) {
881
+ srng -> u .src_ring .last_tp =
882
+ * (volatile u32 * )srng -> u .src_ring .tp_addr ;
881
883
* srng -> u .src_ring .hp_addr = srng -> u .src_ring .hp ;
882
- else
884
+ } else {
885
+ srng -> u .dst_ring .last_hp = * srng -> u .dst_ring .hp_addr ;
883
886
* srng -> u .dst_ring .tp_addr = srng -> u .dst_ring .tp ;
887
+ }
884
888
} else {
885
889
if (srng -> ring_dir == HAL_SRNG_DIR_SRC ) {
890
+ srng -> u .src_ring .last_tp =
891
+ * (volatile u32 * )srng -> u .src_ring .tp_addr ;
886
892
ath11k_ahb_write32 (ab ,
887
893
(unsigned long )srng -> u .src_ring .hp_addr -
888
894
(unsigned long )ab -> mem ,
889
895
srng -> u .src_ring .hp );
890
896
} else {
897
+ srng -> u .dst_ring .last_hp = * srng -> u .dst_ring .hp_addr ;
891
898
ath11k_ahb_write32 (ab ,
892
899
(unsigned long )srng -> u .dst_ring .tp_addr -
893
900
(unsigned long )ab -> mem ,
894
901
srng -> u .dst_ring .tp );
895
902
}
896
903
}
904
+
905
+ srng -> timestamp = jiffies ;
897
906
}
898
907
899
908
void ath11k_hal_setup_link_idle_list (struct ath11k_base * ab ,
@@ -1017,6 +1026,7 @@ int ath11k_hal_srng_setup(struct ath11k_base *ab, enum hal_ring_type type,
1017
1026
params -> intr_batch_cntr_thres_entries ;
1018
1027
srng -> intr_timer_thres_us = params -> intr_timer_thres_us ;
1019
1028
srng -> flags = params -> flags ;
1029
+ srng -> initialized = 1 ;
1020
1030
spin_lock_init (& srng -> lock );
1021
1031
1022
1032
for (i = 0 ; i < HAL_SRNG_NUM_REG_GRP ; i ++ ) {
@@ -1122,3 +1132,55 @@ void ath11k_hal_srng_deinit(struct ath11k_base *ab)
1122
1132
ath11k_hal_free_cont_rdp (ab );
1123
1133
ath11k_hal_free_cont_wrp (ab );
1124
1134
}
1135
+
1136
+ void ath11k_hal_dump_srng_stats (struct ath11k_base * ab )
1137
+ {
1138
+ struct hal_srng * srng ;
1139
+ struct ath11k_ext_irq_grp * irq_grp ;
1140
+ struct ath11k_ce_pipe * ce_pipe ;
1141
+ int i ;
1142
+
1143
+ ath11k_err (ab , "Last interrupt received for each CE:\n" );
1144
+ for (i = 0 ; i < CE_COUNT ; i ++ ) {
1145
+ ce_pipe = & ab -> ce .ce_pipe [i ];
1146
+
1147
+ if (ath11k_ce_get_attr_flags (i ) & CE_ATTR_DIS_INTR )
1148
+ continue ;
1149
+
1150
+ ath11k_err (ab , "CE_id %d pipe_num %d %ums before\n" ,
1151
+ i , ce_pipe -> pipe_num ,
1152
+ jiffies_to_msecs (jiffies - ce_pipe -> timestamp ));
1153
+ }
1154
+
1155
+ ath11k_err (ab , "\nLast interrupt received for each group:\n" );
1156
+ for (i = 0 ; i < ATH11K_EXT_IRQ_GRP_NUM_MAX ; i ++ ) {
1157
+ irq_grp = & ab -> ext_irq_grp [i ];
1158
+ ath11k_err (ab , "group_id %d %ums before\n" ,
1159
+ irq_grp -> grp_id ,
1160
+ jiffies_to_msecs (jiffies - irq_grp -> timestamp ));
1161
+ }
1162
+
1163
+ for (i = 0 ; i < HAL_SRNG_RING_ID_MAX ; i ++ ) {
1164
+ srng = & ab -> hal .srng_list [i ];
1165
+
1166
+ if (!srng -> initialized )
1167
+ continue ;
1168
+
1169
+ if (srng -> ring_dir == HAL_SRNG_DIR_SRC )
1170
+ ath11k_err (ab ,
1171
+ "src srng id %u hp %u, reap_hp %u, cur tp %u, cached tp %u last tp %u napi processed before %ums\n" ,
1172
+ srng -> ring_id , srng -> u .src_ring .hp ,
1173
+ srng -> u .src_ring .reap_hp ,
1174
+ * srng -> u .src_ring .tp_addr , srng -> u .src_ring .cached_tp ,
1175
+ srng -> u .src_ring .last_tp ,
1176
+ jiffies_to_msecs (jiffies - srng -> timestamp ));
1177
+ else if (srng -> ring_dir == HAL_SRNG_DIR_DST )
1178
+ ath11k_err (ab ,
1179
+ "dst srng id %u tp %u, cur hp %u, cached hp %u last hp %u napi processed before %ums\n" ,
1180
+ srng -> ring_id , srng -> u .dst_ring .tp ,
1181
+ * srng -> u .dst_ring .hp_addr ,
1182
+ srng -> u .dst_ring .cached_hp ,
1183
+ srng -> u .dst_ring .last_hp ,
1184
+ jiffies_to_msecs (jiffies - srng -> timestamp ));
1185
+ }
1186
+ }
0 commit comments