1 /** @file
2  * @brief Network statistics
3  *
4  * Network statistics data. This should only be enabled when
5  * debugging as it consumes memory.
6  */
7 
8 /*
9  * Copyright (c) 2016 Intel Corporation
10  *
11  * SPDX-License-Identifier: Apache-2.0
12  */
13 
14 #ifndef ZEPHYR_INCLUDE_NET_NET_STATS_H_
15 #define ZEPHYR_INCLUDE_NET_NET_STATS_H_
16 
17 #include <zephyr/types.h>
18 #include <net/net_core.h>
19 #include <net/net_mgmt.h>
20 
21 #ifdef __cplusplus
22 extern "C" {
23 #endif
24 
25 /**
26  * @brief Network statistics library
27  * @defgroup net_stats Network Statistics Library
28  * @ingroup networking
29  * @{
30  */
31 
32 /**
33  * @typedef net_stats_t
34  * @brief Network statistics counter
35  */
36 typedef uint32_t net_stats_t;
37 
38 /**
39  * @brief Number of bytes sent and received.
40  */
41 struct net_stats_bytes {
42 	/** Number of bytes sent */
43 	net_stats_t sent;
44 	/** Number of bytes received */
45 	net_stats_t received;
46 };
47 
48 /**
49  * @brief Number of network packets sent and received.
50  */
51 struct net_stats_pkts {
52 	/** Number of packets sent */
53 	net_stats_t tx;
54 	/** Number of packets received */
55 	net_stats_t rx;
56 };
57 
58 /**
59  * @brief IP layer statistics
60  */
61 struct net_stats_ip {
62 	/** Number of received packets at the IP layer. */
63 	net_stats_t recv;
64 
65 	/** Number of sent packets at the IP layer. */
66 	net_stats_t sent;
67 
68 	/** Number of forwarded packets at the IP layer. */
69 	net_stats_t forwarded;
70 
71 	/** Number of dropped packets at the IP layer. */
72 	net_stats_t drop;
73 };
74 
75 /**
76  * @brief IP layer error statistics
77  */
78 struct net_stats_ip_errors {
79 	/** Number of packets dropped due to wrong IP version
80 	 * or header length.
81 	 */
82 	net_stats_t vhlerr;
83 
84 	 /** Number of packets dropped due to wrong IP length, high byte. */
85 	net_stats_t hblenerr;
86 
87 	/** Number of packets dropped due to wrong IP length, low byte. */
88 	net_stats_t lblenerr;
89 
90 	/** Number of packets dropped because they were IP fragments. */
91 	net_stats_t fragerr;
92 
93 	/** Number of packets dropped due to IP checksum errors. */
94 	net_stats_t chkerr;
95 
96 	/** Number of packets dropped because they were neither ICMP,
97 	 * UDP nor TCP.
98 	 */
99 	net_stats_t protoerr;
100 };
101 
102 /**
103  * @brief ICMP statistics
104  */
105 struct net_stats_icmp {
106 	/** Number of received ICMP packets. */
107 	net_stats_t recv;
108 
109 	/** Number of sent ICMP packets. */
110 	net_stats_t sent;
111 
112 	/** Number of dropped ICMP packets. */
113 	net_stats_t drop;
114 
115 	/** Number of ICMP packets with a wrong type. */
116 	net_stats_t typeerr;
117 
118 	/** Number of ICMP packets with a bad checksum. */
119 	net_stats_t chkerr;
120 };
121 
122 /**
123  * @brief TCP statistics
124  */
125 struct net_stats_tcp {
126 	/** Amount of received and sent TCP application data. */
127 	struct net_stats_bytes bytes;
128 
129 	/** Amount of retransmitted data. */
130 	net_stats_t resent;
131 
132 	/** Number of dropped packets at the TCP layer. */
133 	net_stats_t drop;
134 
135 	/** Number of received TCP segments. */
136 	net_stats_t recv;
137 
138 	/** Number of sent TCP segments. */
139 	net_stats_t sent;
140 
141 	/** Number of dropped TCP segments. */
142 	net_stats_t seg_drop;
143 
144 	/** Number of TCP segments with a bad checksum. */
145 	net_stats_t chkerr;
146 
147 	/** Number of received TCP segments with a bad ACK number. */
148 	net_stats_t ackerr;
149 
150 	/** Number of received bad TCP RST (reset) segments. */
151 	net_stats_t rsterr;
152 
153 	/** Number of received TCP RST (reset) segments. */
154 	net_stats_t rst;
155 
156 	/** Number of retransmitted TCP segments. */
157 	net_stats_t rexmit;
158 
159 	/** Number of dropped connection attempts because too few connections
160 	 * were available.
161 	 */
162 	net_stats_t conndrop;
163 
164 	/** Number of connection attempts for closed ports, triggering a RST. */
165 	net_stats_t connrst;
166 };
167 
168 /**
169  * @brief UDP statistics
170  */
171 struct net_stats_udp {
172 	/** Number of dropped UDP segments. */
173 	net_stats_t drop;
174 
175 	/** Number of received UDP segments. */
176 	net_stats_t recv;
177 
178 	/** Number of sent UDP segments. */
179 	net_stats_t sent;
180 
181 	/** Number of UDP segments with a bad checksum. */
182 	net_stats_t chkerr;
183 };
184 
185 /**
186  * @brief IPv6 neighbor discovery statistics
187  */
188 struct net_stats_ipv6_nd {
189 	net_stats_t drop;
190 	net_stats_t recv;
191 	net_stats_t sent;
192 };
193 
194 /**
195  * @brief IPv6 multicast listener daemon statistics
196  */
197 struct net_stats_ipv6_mld {
198 	/** Number of received IPv6 MLD queries */
199 	net_stats_t recv;
200 
201 	/** Number of sent IPv6 MLD reports */
202 	net_stats_t sent;
203 
204 	/** Number of dropped IPv6 MLD packets */
205 	net_stats_t drop;
206 };
207 
208 /**
209  * @brief IPv4 IGMP daemon statistics
210  */
211 struct net_stats_ipv4_igmp {
212 	/** Number of received IPv4 IGMP queries */
213 	net_stats_t recv;
214 
215 	/** Number of sent IPv4 IGMP reports */
216 	net_stats_t sent;
217 
218 	/** Number of dropped IPv4 IGMP packets */
219 	net_stats_t drop;
220 };
221 
222 /**
223  * @brief Network packet transfer times for calculating average TX time
224  */
225 struct net_stats_tx_time {
226 	uint64_t sum;
227 	net_stats_t count;
228 };
229 
230 /**
231  * @brief Network packet receive times for calculating average RX time
232  */
233 struct net_stats_rx_time {
234 	uint64_t sum;
235 	net_stats_t count;
236 };
237 
238 #if NET_TC_TX_COUNT == 0
239 #define NET_TC_TX_STATS_COUNT 1
240 #else
241 #define NET_TC_TX_STATS_COUNT NET_TC_TX_COUNT
242 #endif
243 
244 #if NET_TC_RX_COUNT == 0
245 #define NET_TC_RX_STATS_COUNT 1
246 #else
247 #define NET_TC_RX_STATS_COUNT NET_TC_RX_COUNT
248 #endif
249 
250 /**
251  * @brief Traffic class statistics
252  */
253 struct net_stats_tc {
254 	struct {
255 		struct net_stats_tx_time tx_time;
256 #if defined(CONFIG_NET_PKT_TXTIME_STATS_DETAIL)
257 		struct net_stats_tx_time
258 				tx_time_detail[NET_PKT_DETAIL_STATS_COUNT];
259 #endif
260 		net_stats_t pkts;
261 		net_stats_t bytes;
262 		uint8_t priority;
263 	} sent[NET_TC_TX_STATS_COUNT];
264 
265 	struct {
266 		struct net_stats_rx_time rx_time;
267 #if defined(CONFIG_NET_PKT_RXTIME_STATS_DETAIL)
268 		struct net_stats_rx_time
269 				rx_time_detail[NET_PKT_DETAIL_STATS_COUNT];
270 #endif
271 		net_stats_t pkts;
272 		net_stats_t bytes;
273 		uint8_t priority;
274 	} recv[NET_TC_RX_STATS_COUNT];
275 };
276 
277 
278 /**
279  * @brief Power management statistics
280  */
281 struct net_stats_pm {
282 	uint64_t overall_suspend_time;
283 	net_stats_t suspend_count;
284 	uint32_t last_suspend_time;
285 	uint32_t start_time;
286 };
287 
288 
289 /**
290  * @brief All network statistics in one struct.
291  */
292 struct net_stats {
293 	/** Count of malformed packets or packets we do not have handler for */
294 	net_stats_t processing_error;
295 
296 	/**
297 	 * This calculates amount of data transferred through all the
298 	 * network interfaces.
299 	 */
300 	struct net_stats_bytes bytes;
301 
302 	/** IP layer errors */
303 	struct net_stats_ip_errors ip_errors;
304 
305 #if defined(CONFIG_NET_STATISTICS_IPV6)
306 	/** IPv6 statistics */
307 	struct net_stats_ip ipv6;
308 #endif
309 
310 #if defined(CONFIG_NET_STATISTICS_IPV4)
311 	/** IPv4 statistics */
312 	struct net_stats_ip ipv4;
313 #endif
314 
315 #if defined(CONFIG_NET_STATISTICS_ICMP)
316 	/** ICMP statistics */
317 	struct net_stats_icmp icmp;
318 #endif
319 
320 #if defined(CONFIG_NET_STATISTICS_TCP)
321 	/** TCP statistics */
322 	struct net_stats_tcp tcp;
323 #endif
324 
325 #if defined(CONFIG_NET_STATISTICS_UDP)
326 	/** UDP statistics */
327 	struct net_stats_udp udp;
328 #endif
329 
330 #if defined(CONFIG_NET_STATISTICS_IPV6_ND)
331 	/** IPv6 neighbor discovery statistics */
332 	struct net_stats_ipv6_nd ipv6_nd;
333 #endif
334 
335 #if defined(CONFIG_NET_STATISTICS_MLD)
336 	/** IPv6 MLD statistics */
337 	struct net_stats_ipv6_mld ipv6_mld;
338 #endif
339 
340 #if defined(CONFIG_NET_STATISTICS_IGMP)
341 	/** IPv4 IGMP statistics */
342 	struct net_stats_ipv4_igmp ipv4_igmp;
343 #endif
344 
345 #if NET_TC_COUNT > 1
346 	/** Traffic class statistics */
347 	struct net_stats_tc tc;
348 #endif
349 
350 #if defined(CONFIG_NET_PKT_TXTIME_STATS)
351 	/** Network packet TX time statistics */
352 	struct net_stats_tx_time tx_time;
353 #endif
354 
355 #if defined(CONFIG_NET_PKT_RXTIME_STATS)
356 	/** Network packet RX time statistics */
357 	struct net_stats_rx_time rx_time;
358 #endif
359 
360 #if defined(CONFIG_NET_PKT_TXTIME_STATS_DETAIL)
361 	/** Network packet TX time detail statistics */
362 	struct net_stats_tx_time tx_time_detail[NET_PKT_DETAIL_STATS_COUNT];
363 #endif
364 #if defined(CONFIG_NET_PKT_RXTIME_STATS_DETAIL)
365 	/** Network packet RX time detail statistics */
366 	struct net_stats_rx_time rx_time_detail[NET_PKT_DETAIL_STATS_COUNT];
367 #endif
368 
369 #if defined(CONFIG_NET_STATISTICS_POWER_MANAGEMENT)
370 	struct net_stats_pm pm;
371 #endif
372 };
373 
374 /**
375  * @brief Ethernet error statistics
376  */
377 struct net_stats_eth_errors {
378 	net_stats_t rx_length_errors;
379 	net_stats_t rx_over_errors;
380 	net_stats_t rx_crc_errors;
381 	net_stats_t rx_frame_errors;
382 	net_stats_t rx_no_buffer_count;
383 	net_stats_t rx_missed_errors;
384 	net_stats_t rx_long_length_errors;
385 	net_stats_t rx_short_length_errors;
386 	net_stats_t rx_align_errors;
387 	net_stats_t rx_dma_failed;
388 	net_stats_t rx_buf_alloc_failed;
389 
390 	net_stats_t tx_aborted_errors;
391 	net_stats_t tx_carrier_errors;
392 	net_stats_t tx_fifo_errors;
393 	net_stats_t tx_heartbeat_errors;
394 	net_stats_t tx_window_errors;
395 	net_stats_t tx_dma_failed;
396 
397 	net_stats_t uncorr_ecc_errors;
398 	net_stats_t corr_ecc_errors;
399 };
400 
401 /**
402  * @brief Ethernet flow control statistics
403  */
404 struct net_stats_eth_flow {
405 	net_stats_t rx_flow_control_xon;
406 	net_stats_t rx_flow_control_xoff;
407 	net_stats_t tx_flow_control_xon;
408 	net_stats_t tx_flow_control_xoff;
409 };
410 
411 /**
412  * @brief Ethernet checksum statistics
413  */
414 struct net_stats_eth_csum {
415 	net_stats_t rx_csum_offload_good;
416 	net_stats_t rx_csum_offload_errors;
417 };
418 
419 /**
420  * @brief Ethernet hardware timestamp statistics
421  */
422 struct net_stats_eth_hw_timestamp {
423 	net_stats_t rx_hwtstamp_cleared;
424 	net_stats_t tx_hwtstamp_timeouts;
425 	net_stats_t tx_hwtstamp_skipped;
426 };
427 
428 #ifdef CONFIG_NET_STATISTICS_ETHERNET_VENDOR
429 /**
430  * @brief Ethernet vendor specific statistics
431  */
432 struct net_stats_eth_vendor {
433 	const char * const key;
434 	uint32_t value;
435 };
436 #endif
437 
438 /**
439  * @brief All Ethernet specific statistics
440  */
441 struct net_stats_eth {
442 	struct net_stats_bytes bytes;
443 	struct net_stats_pkts pkts;
444 	struct net_stats_pkts broadcast;
445 	struct net_stats_pkts multicast;
446 	struct net_stats_pkts errors;
447 	struct net_stats_eth_errors error_details;
448 	struct net_stats_eth_flow flow_control;
449 	struct net_stats_eth_csum csum;
450 	struct net_stats_eth_hw_timestamp hw_timestamp;
451 	net_stats_t collisions;
452 	net_stats_t tx_dropped;
453 	net_stats_t tx_timeout_count;
454 	net_stats_t tx_restart_queue;
455 #ifdef CONFIG_NET_STATISTICS_ETHERNET_VENDOR
456 	/** Array is terminated with an entry containing a NULL key */
457 	struct net_stats_eth_vendor *vendor;
458 #endif
459 };
460 
461 /**
462  * @brief All PPP specific statistics
463  */
464 struct net_stats_ppp {
465 	struct net_stats_bytes bytes;
466 	struct net_stats_pkts pkts;
467 
468 	/** Number of received and dropped PPP frames. */
469 	net_stats_t drop;
470 
471 	/** Number of received PPP frames with a bad checksum. */
472 	net_stats_t chkerr;
473 };
474 
475 #if defined(CONFIG_NET_STATISTICS_USER_API)
476 /* Management part definitions */
477 
478 #define _NET_STATS_LAYER	NET_MGMT_LAYER_L3
479 #define _NET_STATS_CODE		0x101
480 #define _NET_STATS_BASE		(NET_MGMT_LAYER(_NET_STATS_LAYER) |	\
481 				 NET_MGMT_LAYER_CODE(_NET_STATS_CODE))
482 
483 enum net_request_stats_cmd {
484 	NET_REQUEST_STATS_CMD_GET_ALL = 1,
485 	NET_REQUEST_STATS_CMD_GET_PROCESSING_ERROR,
486 	NET_REQUEST_STATS_CMD_GET_BYTES,
487 	NET_REQUEST_STATS_CMD_GET_IP_ERRORS,
488 	NET_REQUEST_STATS_CMD_GET_IPV4,
489 	NET_REQUEST_STATS_CMD_GET_IPV6,
490 	NET_REQUEST_STATS_CMD_GET_IPV6_ND,
491 	NET_REQUEST_STATS_CMD_GET_ICMP,
492 	NET_REQUEST_STATS_CMD_GET_UDP,
493 	NET_REQUEST_STATS_CMD_GET_TCP,
494 	NET_REQUEST_STATS_CMD_GET_ETHERNET,
495 	NET_REQUEST_STATS_CMD_GET_PPP,
496 	NET_REQUEST_STATS_CMD_GET_PM
497 };
498 
499 #define NET_REQUEST_STATS_GET_ALL				\
500 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_ALL)
501 
502 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_ALL);
503 
504 #define NET_REQUEST_STATS_GET_PROCESSING_ERROR				\
505 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_PROCESSING_ERROR)
506 
507 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_PROCESSING_ERROR);
508 
509 #define NET_REQUEST_STATS_GET_BYTES				\
510 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_BYTES)
511 
512 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_BYTES);
513 
514 #define NET_REQUEST_STATS_GET_IP_ERRORS				\
515 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_IP_ERRORS)
516 
517 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_IP_ERRORS);
518 
519 #if defined(CONFIG_NET_STATISTICS_IPV4)
520 #define NET_REQUEST_STATS_GET_IPV4				\
521 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_IPV4)
522 
523 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_IPV4);
524 #endif /* CONFIG_NET_STATISTICS_IPV4 */
525 
526 #if defined(CONFIG_NET_STATISTICS_IPV6)
527 #define NET_REQUEST_STATS_GET_IPV6				\
528 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_IPV6)
529 
530 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_IPV6);
531 #endif /* CONFIG_NET_STATISTICS_IPV6 */
532 
533 #if defined(CONFIG_NET_STATISTICS_IPV6_ND)
534 #define NET_REQUEST_STATS_GET_IPV6_ND				\
535 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_IPV6_ND)
536 
537 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_IPV6_ND);
538 #endif /* CONFIG_NET_STATISTICS_IPV6_ND */
539 
540 #if defined(CONFIG_NET_STATISTICS_ICMP)
541 #define NET_REQUEST_STATS_GET_ICMP				\
542 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_ICMP)
543 
544 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_ICMP);
545 #endif /* CONFIG_NET_STATISTICS_ICMP */
546 
547 #if defined(CONFIG_NET_STATISTICS_UDP)
548 #define NET_REQUEST_STATS_GET_UDP				\
549 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_UDP)
550 
551 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_UDP);
552 #endif /* CONFIG_NET_STATISTICS_UDP */
553 
554 #if defined(CONFIG_NET_STATISTICS_TCP)
555 #define NET_REQUEST_STATS_GET_TCP				\
556 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_TCP)
557 
558 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_TCP);
559 #endif /* CONFIG_NET_STATISTICS_TCP */
560 
561 #if defined(CONFIG_NET_STATISTICS_ETHERNET)
562 #define NET_REQUEST_STATS_GET_ETHERNET				\
563 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_ETHERNET)
564 
565 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_ETHERNET);
566 #endif /* CONFIG_NET_STATISTICS_ETHERNET */
567 
568 #if defined(CONFIG_NET_STATISTICS_PPP)
569 #define NET_REQUEST_STATS_GET_PPP				\
570 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_PPP)
571 
572 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_PPP);
573 #endif /* CONFIG_NET_STATISTICS_PPP */
574 
575 #endif /* CONFIG_NET_STATISTICS_USER_API */
576 
577 #if defined(CONFIG_NET_STATISTICS_POWER_MANAGEMENT)
578 #define NET_REQUEST_STATS_GET_PM				\
579 	(_NET_STATS_BASE | NET_REQUEST_STATS_CMD_GET_PM)
580 
581 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_STATS_GET_PM);
582 #endif /* CONFIG_NET_STATISTICS_POWER_MANAGEMENT */
583 
584 /**
585  * @}
586  */
587 
588 #ifdef __cplusplus
589 }
590 #endif
591 
592 #endif /* ZEPHYR_INCLUDE_NET_NET_STATS_H_ */
593