Watt-32 tcp/ip  2.2 dev-rel.10
pcstat.c
Go to the documentation of this file.
1 
5 /* Update and printing of MAC/IP/ICMP/IGMP/UDP/TCP input/output
6  * statistics counters.
7  *
8  * Copyright (c) 1997-2002 Gisle Vanem <gvanem@yahoo.no>
9  *
10  * Redistribution and use in source and binary forms, with or without
11  * modification, are permitted provided that the following conditions
12  * are met:
13  * 1. Redistributions of source code must retain the above copyright
14  * notice, this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright
16  * notice, this list of conditions and the following disclaimer in the
17  * documentation and/or other materials provided with the distribution.
18  * 3. All advertising materials mentioning features or use of this software
19  * must display the following acknowledgement:
20  * This product includes software developed by Gisle Vanem
21  * Bergen, Norway.
22  *
23  * THIS SOFTWARE IS PROVIDED BY ME (Gisle Vanem) AND CONTRIBUTORS ``AS IS''
24  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
25  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
26  * ARE DISCLAIMED. IN NO EVENT SHALL I OR CONTRIBUTORS BE LIABLE FOR ANY
27  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
28  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
29  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
30  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
32  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33  *
34  * G. Vanem <gvanem@yahoo.no> 1997
35  */
36 
37 #include <stdio.h>
38 #include <string.h>
39 #include <netinet/in.h>
40 #include <net/ppp_defs.h>
41 #include <arpa/inet.h>
42 
43 #include "wattcp.h"
44 #include "strings.h"
45 #include "sock_ini.h"
46 #include "pcconfig.h"
47 #include "pcicmp.h"
48 #include "pcqueue.h"
49 #include "pcsed.h"
50 #include "split.h"
51 #include "misc.h"
52 #include "timer.h"
53 #include "pcpkt.h"
54 #include "pcdbug.h"
55 #include "pppoe.h"
56 #include "pcstat.h"
57 
58 int W32_CALL sock_stats (sock_type *sock, DWORD *days, WORD *inactive,
59  WORD *cwindow, DWORD *avg, DWORD *sd)
60 {
61  _tcp_Socket *s = &sock->tcp;
62 
63  if (s->ip_type != TCP_PROTO)
64  return (0);
65 
66  if (days) *days = get_day_num() - start_day;
67  if (inactive) *inactive = sock_inactive;
68 #if defined(USE_UDP_ONLY)
69  if (cwindow) *cwindow = 0;
70  if (avg) *avg = 0;
71  if (sd) *sd = 0;
72 #else
73  if (cwindow) *cwindow = s->cwindow;
74  if (avg) *avg = s->vj_sa >> 3;
75  if (sd) *sd = s->vj_sd >> 2;
76 #endif
77  return (1);
78 }
79 
80 #if !defined(USE_STATISTICS)
81  void print_mac_stats (void) {}
82  void print_vjc_stats (void) {}
83  void print_pkt_stats (void) {}
84  void print_ip4_stats (void) {}
85  void print_ip6_stats (void) {}
86  void print_icmp_stats(void) {}
87  void print_icmp6_stats(void) {}
88  void print_igmp_stats(void) {}
89  void print_udp_stats (void) {}
90  void print_tcp_stats (void) {}
91  void print_cache_stats(void) {}
92  void print_all_stats (void) {}
93  void reset_stats (void) {}
94 
95 #else /* rest of file */
96 
97 struct macstat macstats;
98 struct ipstat ip4stats;
99 struct ip6stat ip6stats;
100 struct udpstat udpstats;
101 struct icmpstat icmpstats;
102 struct icmp6stat icmp6stats;
103 struct igmpstat igmpstats;
104 struct pppoestat pppoestats;
105 struct cache_stat cache_stats;
106 
107 #if !defined(USE_UDP_ONLY)
108 struct tcpstat tcpstats;
109 #endif
110 
111 void W32_CALL reset_stats (void)
112 {
113  memset (&macstats, 0, sizeof(macstats));
114  memset (&ip4stats, 0, sizeof(ip4stats));
115  memset (&ip6stats, 0, sizeof(ip6stats));
116  memset (&udpstats, 0, sizeof(udpstats));
117  memset (&icmpstats, 0, sizeof(icmpstats));
118  memset (&igmpstats, 0, sizeof(igmpstats));
119  memset (&pppoestats, 0, sizeof(pppoestats));
120  memset (&cache_stats,0, sizeof(cache_stats));
121 #if !defined(USE_UDP_ONLY)
122  memset (&tcpstats, 0, sizeof(tcpstats));
123 #endif
124 }
125 
126 static __inline void show_stat (const char *name, DWORD num)
127 {
128  if (num)
129  (*_printf) (" %-13s %10lu\n", name, num);
130 }
131 
132 #if defined(HAVE_UINT64) && defined(USE_IPV6)
133 static __inline void show_stat64 (const char *name, uint64 num)
134 {
135  if (num)
136  (*_printf) (" %-13s %10" U64_FMT "\n", name, num);
137 }
138 #endif
139 
140 void W32_CALL print_cache_stats (void)
141 {
142  (*_printf) ("Cache stats:\n"
143  " ARP-cache: hits %lu, misses %lu\n"
144  " Route-cache: hits %lu, misses %lu\n",
145  cache_stats.num_arp_hits, cache_stats.num_arp_misses,
146  cache_stats.num_route_hits, cache_stats.num_route_misses);
147 }
148 
149 void W32_CALL print_mac_stats (void)
150 {
151  (*_printf) ("MAC input stats:\n"
152  " dropped %lu, waiting %d, looped %lu, non-IP recv %lu sent %lu\n"
153  " unknown types, %lu, LLC frames %lu, IP-recursions %lu",
154  pkt_dropped(), pkt_waiting(), macstats.num_mac_loop,
155  macstats.non_ip_recv, macstats.non_ip_sent,
156  macstats.num_unk_type, macstats.num_llc_frames,
157  macstats.num_ip_recurse);
158 
159 #if defined(USE_FAST_PKT) || defined(WIN32)
160  (*_printf) (" \n wrong handle %lu, bad-sync %lu, too large %lu, too small %lu",
161  macstats.num_wrong_handle, macstats.num_bad_sync,
162  macstats.num_too_large, macstats.num_too_small);
163 #endif
164 
165  (*_printf) (" \nMAC output stats:\n"
166  " Tx errors %10lu %s\n"
167  " Tx retries %10lu\n"
168  " Tx timeout %10lu\n",
169  macstats.num_tx_err, macstats.num_tx_err ? "****" : "",
170  macstats.num_tx_retry, macstats.num_tx_timeout);
171 }
172 
173 void W32_CALL print_arp_stats (void)
174 {
175  (*_printf) ("ARP Requests: %10lu recv\n"
176  " Requests: %10lu sent\n"
177  " Replies: %10lu recv\n"
178  " Replies: %10lu sent\n",
179  macstats.arp.request_recv, macstats.arp.request_sent,
180  macstats.arp.reply_recv, macstats.arp.reply_sent);
181 }
182 
183 void W32_CALL print_rarp_stats (void)
184 {
185 #if defined(USE_RARP)
186  DWORD total = macstats.rarp.request_recv +
187  macstats.rarp.request_sent +
188  macstats.rarp.reply_recv +
189  macstats.rarp.reply_sent;
190 
191  if (total > 0)
192  (*_printf) ("RARP Requests: %10lu recv\n"
193  " Requests: %10lu sent\n"
194  " Replies: %10lu recv\n"
195  " Replies: %10lu sent\n",
196  macstats.rarp.request_recv, macstats.rarp.request_sent,
197  macstats.rarp.reply_recv, macstats.rarp.reply_sent);
198 #endif
199 }
200 
201 void W32_CALL print_vjc_stats (void)
202 {
203 #if defined(__MSDOS__)
204  struct slcompress vjc;
205 
206  if (stricmp(_pktdrvrname,"PPPD220F") && /* not using DOSPPP driver */
207  stricmp(_pktdrvrname,"LADSoftPPP$")) /* or LadSoft's lsppp */
208  return;
209 
210  (*_printf) ("VJ compression:\n");
211 
212  if (!pkt_get_vjstats(&vjc))
213  {
214  (*_printf) (" not available\n\n");
215  return;
216  }
217 
218  (*_printf) (" Tx TCP packets: %lu, non-TCP: %lu\n",
219  vjc.sls_o_tcp, vjc.sls_o_nontcp);
220 
221  (*_printf) (" Rx error packets: %lu, tossed: %lu\n",
222  vjc.sls_i_error, vjc.sls_i_tossed);
223 
224  (*_printf) (" Rx runt packets: %lu, bad checksum: %lu\n",
225  vjc.sls_i_runt, vjc.sls_i_badcheck);
226 
227  (*_printf) (" connection state searches: %lu, misses: %lu\n",
228  vjc.sls_o_searches, vjc.sls_o_misses);
229 
230  (*_printf) (" oldest xmit in ring: %-9u\n", vjc.xmit_oldest);
231  (*_printf) (" compression state flags: 0x%X\n", vjc.flags);
232 
233  (*_printf) (" highest slot: Tx %-5u Rx %u\n",
234  vjc.tslot_limit, vjc.rslot_limit);
235 
236  (*_printf) (" most recent id: Tx %-5u Rx %u\n",
237  vjc.xmit_current, vjc.recv_current);
238 
239  (*_printf) (" uncompressed packets: Tx %-5lu Rx %lu\n",
240  vjc.sls_o_uncompressed, vjc.sls_i_uncompressed);
241 
242  (*_printf) (" compressed packets: Tx %-5lu Rx %lu\n",
243  vjc.sls_o_compressed, vjc.sls_i_compressed);
244 
245  if (!stricmp(_pktdrvrname,"PPPD220F")) /* using DOSPPP driver */
246  {
247  struct cstate cstate;
248  WORD cs_ofs, rx_num = 0, tx_num = 0;
249 
250  (*_printf) (" Connection states:\n");
251 
252  for (cs_ofs = vjc.cstate_ptr_tstate;
253  pkt_get_cstate(&cstate,cs_ofs) && tx_num < vjc.tslot_limit;
254  cs_ofs = cstate.cs_next, tx_num++)
255  (*_printf) (" Tx-id %2d: IP %15s -> %15s, TCP port %u -> %d\n",
256  cstate.cs_this,
257  inet_ntoa(*(struct in_addr*)&cstate.cs_ip.source),
258  inet_ntoa(*(struct in_addr*)&cstate.cs_ip.destination),
259  intel16(cstate.cs_tcp.srcPort),
260  intel16(cstate.cs_tcp.dstPort));
261 
262  for (cs_ofs = vjc.cstate_ptr_rstate;
263  pkt_get_cstate(&cstate,cs_ofs) && rx_num < vjc.rslot_limit;
264  cs_ofs = cstate.cs_next, rx_num++)
265  (*_printf) (" Rx-id %2d: IP %15s -> %15s, TCP port %u -> %d\n",
266  cstate.cs_this,
267  inet_ntoa(*(struct in_addr*)&cstate.cs_ip.source),
268  inet_ntoa(*(struct in_addr*)&cstate.cs_ip.destination),
269  intel16(cstate.cs_tcp.srcPort),
270  intel16(cstate.cs_tcp.dstPort));
271  if (rx_num + tx_num == 0)
272  (*_printf) (" not available\n");
273  }
274  (*_printf) (" \n");
275 #endif /* __MSDOS__ */
276 }
277 
278 void W32_CALL print_pkt_stats (void)
279 {
280  struct PktStats stat, total;
281  char tot_rx [15] = " ?";
282  char tot_tx [15] = " ?";
283 
284  (*_printf) ("Driver statistics:\n");
285  if (!pkt_get_stats(&stat,&total))
286  {
287  (*_printf) (" Not available\n");
288  return;
289  }
290 
291  /*
292  * The total.in_bytes and total.out_bytes (since boot) are only
293  * available for DOS packet-drivers. Win32 drivers count only total
294  * packets since driver was started. Print a '? for Win32.
295  */
296 #if defined(__MSDOS__)
297  sprintf (tot_rx, "%10lu", total.in_bytes);
298  sprintf (tot_tx, "%10lu", total.out_bytes);
299 #endif
300 
301  (*_printf) (" Rx: %9lu pkt, %10lu bytes, %6lu errors, %6lu lost (this session)\n",
302  stat.in_packets, stat.in_bytes, stat.in_errors, stat.lost);
303  (*_printf) (" Tx: %9lu pkt, %10lu bytes, %6lu errors\n",
304  stat.out_packets, stat.out_bytes, stat.out_errors);
305 
306  (*_printf) (" Rx: %9lu pkt, %s bytes, %6lu errors, %6lu lost (since boot)\n",
307  total.in_packets, tot_rx, total.in_errors, total.lost);
308  (*_printf) (" Tx: %9lu pkt, %s bytes, %6lu errors\n",
309  total.out_packets, tot_tx, total.out_errors);
310 }
311 
312 void W32_CALL print_pppoe_stats (void)
313 {
314 #if defined(USE_PPPOE)
315  (*_printf) ("PPPoE stats:\n");
316  show_stat ("Tx Discovery:", pppoestats.num_disc_sent);
317  show_stat ("Rx Discovery:", pppoestats.num_disc_recv);
318  show_stat ("Tx Session:", pppoestats.num_sess_sent);
319  show_stat ("Rx Session:", pppoestats.num_sess_recv);
320 #endif
321 }
322 
323 void W32_CALL print_ip4_stats (void)
324 {
325  (*_printf) ("IP4 input stats:\n");
326  show_stat ("total:", ip4stats.ips_total);
327  show_stat ("badsum:", ip4stats.ips_badsum);
328  show_stat ("badver:", ip4stats.ips_badvers);
329  show_stat ("short:", ip4stats.ips_tooshort);
330  show_stat ("frags:", ip4stats.ips_fragments);
331  show_stat ("fragdrop:", ip4stats.ips_fragdropped);
332  show_stat ("fragtimeout:",ip4stats.ips_fragtimeout);
333  show_stat ("reassemble:", ip4stats.ips_reassembled);
334  show_stat ("noproto:", ip4stats.ips_noproto);
335  show_stat ("delivered:", ip4stats.ips_delivered);
336  show_stat ("badoptions:", ip4stats.ips_badoptions);
337  show_stat ("dropped:", ip4stats.ips_idropped);
338 
339  (*_printf) ("IP4 output stats:\n");
340  show_stat ("total:", ip4stats.ips_rawout);
341  show_stat ("noroute:", ip4stats.ips_noroute);
342  show_stat ("frags:", ip4stats.ips_ofragments);
343  show_stat ("dropped:", ip4stats.ips_odropped);
344 }
345 
346 void W32_CALL print_ip6_stats (void)
347 {
348 #if defined(HAVE_UINT64) && defined(USE_IPV6)
349  (*_printf) ("IP6 input stats:\n");
350  show_stat64 ("total:", ip6stats.ip6s_total);
351  show_stat64 ("badver:", ip6stats.ip6s_badvers);
352  show_stat64 ("short:", ip6stats.ip6s_tooshort);
353  show_stat64 ("frags:", ip6stats.ip6s_fragments);
354  show_stat64 ("fragdrop:", ip6stats.ip6s_fragdropped);
355  show_stat64 ("fragtime:", ip6stats.ip6s_fragtimeout);
356  show_stat64 ("reassemble:",ip6stats.ip6s_reassembled);
357  show_stat64 ("delivered:", ip6stats.ip6s_delivered);
358  show_stat64 ("badoptions:",ip6stats.ip6s_badoptions);
359 
360  (*_printf) ("IP6 output stats:\n");
361  show_stat64 ("total:", ip6stats.ip6s_rawout);
362  show_stat64 ("noroute:", ip6stats.ip6s_noroute);
363  show_stat64 ("frags:", ip6stats.ip6s_ofragments);
364  show_stat64 ("dropped:", ip6stats.ip6s_odropped);
365 #endif
366 }
367 
368 void W32_CALL print_icmp6_stats (void)
369 {
370 #if defined(HAVE_UINT64) && defined(USE_IPV6)
371  uint64 total_in = 0;
372  uint64 total_out = 0;
373  int i;
374 
375  (*_printf) ("ICMP6 input stats:\n");
376 
377  for (i = 0; i < DIM(icmp6stats.icp6s_inhist); i++)
378  total_in += icmp6stats.icp6s_inhist[i];
379 
380  show_stat64 ("total:", total_in);
381 
382  show_stat64 ("badsum:", icmp6stats.icp6s_checksum);
383  show_stat64 ("short:", icmp6stats.icp6s_tooshort);
384  show_stat64 ("badcode:", icmp6stats.icp6s_badcode);
385 
386  (*_printf) ("ICMP6 output stats:\n");
387  for (i = 0; i < DIM(icmp6stats.icp6s_outhist); i++)
388  total_out += icmp6stats.icp6s_outhist[i];
389 
390  show_stat64 ("total:", total_out);
391  show_stat64 ("too big:", icmp6stats.icp6s_opacket_too_big);
392  show_stat64 ("exceed xmit:", icmp6stats.icp6s_otime_exceed_transit);
393  show_stat64 ("exceed reasm:",icmp6stats.icp6s_otime_exceed_reassembly);
394 #endif
395 }
396 
397 void W32_CALL print_icmp_stats (void)
398 {
399  DWORD total_in = 0;
400  DWORD total_out = 0;
401  int i;
402  static const char *types[ICMP_MAXTYPE+1] = {
403  "echoreply:",
404  "1?:",
405  "2?:",
406  "unreach:",
407  "srcquench:",
408  "redirect:",
409  "6?:",
410  "7?:",
411  "echorequest:",
412  "router adv:",
413  "router sol:",
414  "timex:",
415  "parm prob:",
416  "tstamp req:",
417  "tstamp rep:",
418  "info req:",
419  "info rep:",
420  "mask req:",
421  "mask rep:"
422  };
423 
424  (*_printf) ("ICMP input stats:\n");
425  for (i = 0; i < ICMP_MAXTYPE; i++)
426  total_in += icmpstats.icps_inhist[i];
427  show_stat ("total:", total_in);
428 
429  show_stat ("badsum:", icmpstats.icps_checksum);
430  show_stat ("badcode:",icmpstats.icps_badcode);
431  show_stat ("short:", icmpstats.icps_tooshort);
432 
433  for (i = 0; i < ICMP_MAXTYPE; i++)
434  show_stat (types[i], icmpstats.icps_inhist[i]);
435 
436  (*_printf) ("ICMP output stats:\n");
437  for (i = 0; i < ICMP_MAXTYPE; i++)
438  total_out += icmpstats.icps_outhist[i];
439  show_stat ("total:", total_out);
440 
441  for (i = 0; i < ICMP_MAXTYPE; i++)
442  show_stat (types[i], icmpstats.icps_outhist[i]);
443 }
444 
445 void W32_CALL print_igmp_stats (void)
446 {
447 #if defined(USE_MULTICAST)
448  (*_printf) ("IGMP input stats:\n");
449  show_stat ("total:", igmpstats.igps_rcv_total);
450  show_stat ("badsum:", igmpstats.igps_rcv_badsum);
451  show_stat ("short:", igmpstats.igps_rcv_tooshort);
452  show_stat ("queries:", igmpstats.igps_rcv_queries);
453  show_stat ("queries (bad):",igmpstats.igps_rcv_badqueries);
454  show_stat ("reports:", igmpstats.igps_rcv_reports);
455  show_stat (" bad:", igmpstats.igps_rcv_badreports);
456  show_stat (" group:", igmpstats.igps_rcv_ourreports);
457 
458  (*_printf) ("IGMP output stats:\n");
459  show_stat ("reports:", igmpstats.igps_snd_reports);
460 #endif
461 }
462 
463 void W32_CALL print_udp_stats (void)
464 {
465  (*_printf) ("UDP input stats:\n");
466  show_stat ("total:", udpstats.udps_ipackets);
467  show_stat ("drops:", udpstats.udps_hdrops);
468  show_stat ("badsum:", udpstats.udps_badsum);
469  show_stat ("no service:", udpstats.udps_noport);
470  show_stat ("broadcast:", udpstats.udps_noportbcast);
471  show_stat ("queue full:", udpstats.udps_fullsock);
472 
473  (*_printf) ("UDP output stats:\n");
474  show_stat ("total:", udpstats.udps_opackets);
475 }
476 
477 void W32_CALL print_tcp_stats (void)
478 {
479 #if !defined(USE_UDP_ONLY)
480  (*_printf) ("TCP input stats:\n");
481  show_stat ("total:", tcpstats.tcps_rcvtotal);
482  show_stat ("drops:", tcpstats.tcps_drops);
483  show_stat ("badsum:", tcpstats.tcps_rcvbadsum);
484  show_stat ("badhofs:", tcpstats.tcps_rcvbadoff);
485  show_stat ("conn-okay:", tcpstats.tcps_connects);
486  show_stat ("conn-accept:", tcpstats.tcps_accepts);
487  show_stat ("conn-drops:", tcpstats.tcps_conndrops);
488  show_stat ("inS pkts:", tcpstats.tcps_rcvpack);
489  show_stat ("inS bytes:", tcpstats.tcps_rcvbyte);
490  show_stat ("OoO pkts:", tcpstats.tcps_rcvoopack);
491  show_stat ("OoO bytes:", tcpstats.tcps_rcvoobyte);
492  show_stat ("ACK pkts:", tcpstats.tcps_rcvackpack);
493  show_stat ("ACK bytes:", tcpstats.tcps_rcvackbyte);
494  show_stat ("ACK nosent:", tcpstats.tcps_rcvacktoomuch);
495  show_stat ("dup ACK:", tcpstats.tcps_rcvduppack);
496  show_stat ("dup bytes:", tcpstats.tcps_rcvdupbyte);
497  show_stat ("pers-drop:", tcpstats.tcps_persistdrop);
498 
499  (*_printf) ("TCP output stats:\n");
500  show_stat ("total:", tcpstats.tcps_sndtotal);
501  show_stat ("data pkts:", tcpstats.tcps_sndpack);
502  show_stat ("data bytes:", tcpstats.tcps_sndbyte);
503  show_stat ("conn-attempt:",tcpstats.tcps_connattempt);
504  show_stat ("SYN/FIN/RST:", tcpstats.tcps_sndctrl);
505  show_stat ("close/drops:", tcpstats.tcps_closed);
506  show_stat ("OOB pkts:", tcpstats.tcps_sndurg);
507  show_stat ("ACK pkts:", tcpstats.tcps_sndacks);
508  show_stat ("ACK dly:", tcpstats.tcps_delack);
509  show_stat ("ACK win upd:", tcpstats.tcps_sndwinup);
510  show_stat ("retrans to:", tcpstats.tcps_rexmttimeo);
511  show_stat ("keepalive pr:",tcpstats.tcps_keepprobe);
512  show_stat ("keepalive to:",tcpstats.tcps_keeptimeo);
513  show_stat ("RTTcache add:",tcpstats.tcps_cachedrtt);
514  show_stat ("RTTcache get:",tcpstats.tcps_usedrtt);
515 #endif
516 }
517 
518 /* \todo print a nice table of everything. Something like:
519 
520  IP4 SENT RECEIVED
521  total
522  badsum
523  tooshort
524  toosmall
525  badhlen
526  badlen
527  fragments
528  fragdropped
529  fragtimeout
530  forward
531  cantforward
532  redirectsent
533  noproto
534  delivered
535  localout
536  odropped
537  idropped
538  reassembled
539  fragmented
540  ofragments
541  cantfrag
542  badoptions
543  noroute
544  badvers
545  rawout
546  toolong
547 
548  */
549 void W32_CALL print_all_stats (void)
550 {
551  int save = ctrace_on;
552 
553  ctrace_on = 0;
554 
555  (*_printf) ("\n");
556 
557  print_cache_stats();
558  print_vjc_stats();
559  print_pkt_stats();
560  print_mac_stats();
561 
562  if (!_pktserial)
563  {
564  print_arp_stats();
565  print_rarp_stats();
566  print_pppoe_stats();
567  }
568 
569  print_ip4_stats();
570  print_ip6_stats();
571  print_icmp_stats();
572  print_icmp6_stats();
573  print_igmp_stats();
574  print_udp_stats();
575  print_tcp_stats();
576 
577  ctrace_on = save;
578 }
579 
580 /*
581  * Called from the link-layer input routine _eth_arrived().
582  */
583 void update_in_stat (void)
584 {
585  const struct pkt_split *ps;
586  const eth_Header *eth;
587  const tok_Header *tok;
588  const fddi_Header *fddi;
589  const ICMP_PKT *icmp;
590  BOOL got_ip = FALSE;
591  BYTE type;
592 
593  for (ps = pkt_get_split_in(); ps->data; ps++)
594  {
595  switch (ps->type)
596  {
597  case TYPE_ETHER_HEAD:
598  eth = (const eth_Header*) ps->data;
599  if (!memcmp(eth->source,_eth_addr,sizeof(_eth_addr)))
600  macstats.num_mac_loop++;
601  break;
602 
603  case TYPE_TOKEN_HEAD:
604  tok = (const tok_Header*) ps->data;
605  if (!memcmp(tok->source,_eth_addr,sizeof(_eth_addr)))
606  macstats.num_mac_loop++;
607  break;
608 
609  case TYPE_FDDI_HEAD:
610  fddi = (const fddi_Header*) ps->data;
611  if (!memcmp(fddi->source,_eth_addr,sizeof(_eth_addr)))
612  macstats.num_mac_loop++;
613  break;
614 
615  case TYPE_LLC_HEAD:
616  macstats.num_llc_frames++;
617  break;
618 
619  case TYPE_ARP:
620  {
621  const arp_Header *arp = (const arp_Header*) ps->data;
622 
623  if (arp->opcode == ARP_REQUEST)
624  macstats.arp.request_recv++;
625  else if (arp->opcode == ARP_REPLY)
626  macstats.arp.reply_recv++;
627  break;
628  }
629 #if defined(USE_RARP)
630  case TYPE_RARP:
631  {
632  const rarp_Header *rarp = (const rarp_Header*) ps->data;
633 
634  if (rarp->opcode == RARP_REQUEST)
635  macstats.rarp.request_recv++;
636  else if (rarp->opcode == RARP_REPLY)
637  macstats.rarp.reply_recv++;
638  break;
639  }
640 #endif
641 
642 #if defined(USE_PPPOE)
643  case TYPE_PPPOE_DISC:
644  pppoestats.num_disc_recv++;
645  break;
646 
647  case TYPE_PPPOE_SESS:
648  pppoestats.num_sess_recv++;
649  break;
650 
651  case TYPE_PPP_LCP:
652  case TYPE_PPP_IPCP:
654  break;
655 #endif
656 
657 #if defined(USE_IPV6)
658  case TYPE_IP6:
659  ip6stats.ip6s_total++;
660  got_ip = TRUE;
661  break;
662 
663  case TYPE_IP6_HOP:
664  case TYPE_IP6_IPV6:
665  case TYPE_IP6_ROUTING:
666  case TYPE_IP6_FRAGMENT:
667  case TYPE_IP6_ESP:
668  case TYPE_IP6_AUTH:
669  case TYPE_IP6_ICMP:
670  case TYPE_IP6_DEST:
672  break;
673  case TYPE_IP6_NONE:
674  case TYPE_IP6_UNSUPP:
675  break; /* ignore */
676 #endif
677 
678  case TYPE_IP4:
679  ip4stats.ips_total++;
680  got_ip = TRUE;
681  break;
682 
683  case TYPE_IP4_FRAG:
684  got_ip = TRUE;
685  case TYPE_IP4_OPTIONS:
686  break;
687 
688  case TYPE_ICMP:
689  icmp = (const ICMP_PKT*) ps->data;
690  type = icmp->unused.type;
691  if (type <= ICMP_MAXTYPE)
692  icmpstats.icps_inhist[(int)type]++;
693  return;
694 
695  case TYPE_IGMP:
696  igmpstats.igps_rcv_total++;
697  return;
698 
699  case TYPE_UDP_HEAD:
700  udpstats.udps_ipackets++;
701  return;
702 
703 #if !defined(USE_UDP_ONLY)
704  case TYPE_TCP_HEAD:
705  tcpstats.tcps_rcvtotal++;
706  return;
707 #endif
708 
709  default:
710 #if defined(USE_DEBUG) && 1 /* !! bug hunt */
711  dbug_printf ("Unknown split-type %d\n", ps->type);
712 #endif
713  macstats.num_unk_type++;
714  break;
715  }
716  }
717  if (!got_ip)
718  macstats.non_ip_recv++;
719 }
720 
721 /*
722  * Called from the link-layer output routine _eth_send().
723  */
724 void update_out_stat (void)
725 {
726  const struct pkt_split *ps;
727  const arp_Header *arp;
728  const in_Header *ip;
729  const ICMP_PKT *icmp;
730  BOOL got_ip = FALSE;
731  BYTE type;
732  DWORD ofs;
733 
734  for (ps = pkt_get_split_out(); ps->data; ps++)
735  {
736  switch (ps->type)
737  {
738  case TYPE_ARP:
739  arp = (arp_Header*) ps->data;
740  if (arp->opcode == ARP_REQUEST)
741  macstats.arp.request_sent++;
742  else if (arp->opcode == ARP_REPLY)
743  macstats.arp.reply_sent++;
744  break;
745 
746 #if defined(USE_RARP)
747  case TYPE_RARP:
748  {
749  const rarp_Header *rarp = (rarp_Header*) ps->data;
750 
751  if (rarp->opcode == RARP_REQUEST)
752  macstats.rarp.request_sent++;
753  else if (rarp->opcode == RARP_REPLY)
754  macstats.rarp.reply_sent++;
755  }
756  break;
757 #endif
758 
759 #if defined(USE_PPPOE)
760  case TYPE_PPPOE_DISC:
761  pppoestats.num_disc_sent++;
762  break;
763 
764  case TYPE_PPPOE_SESS:
765  pppoestats.num_sess_sent++;
766 
767  case TYPE_PPP_LCP:
768  case TYPE_PPP_IPCP:
770  break;
771 #endif
772 
773 #if defined(USE_IPV6)
774  case TYPE_IP6:
775  got_ip = TRUE;
776  ip6stats.ip6s_rawout++;
777  break;
778 
779  case TYPE_IP6_HOP:
780  case TYPE_IP6_IPV6:
781  case TYPE_IP6_ROUTING:
782  case TYPE_IP6_FRAGMENT:
783  case TYPE_IP6_ESP:
784  case TYPE_IP6_AUTH:
785  case TYPE_IP6_ICMP:
786  case TYPE_IP6_DEST:
788  break;
789 #endif
790 
791  case TYPE_IP4:
792  got_ip = TRUE;
793  ip = (const struct in_Header*) ps->data;
794  ip4stats.ips_rawout++; /* count raw IP (fragmented or not) */
795 
796  ofs = intel16 (ip->frag_ofs);
797  ofs = (ofs & IP_OFFMASK) << 3;
798  if (ofs)
799  return; /* only fragments with ofs 0 (already counted) */
800  break;
801 
802  case TYPE_ICMP:
803  icmp = (const ICMP_PKT*) ps->data;
804  type = icmp->unused.type;
805  if (type <= ICMP_MAXTYPE)
806  icmpstats.icps_outhist[(int)type]++;
807  return;
808 
809 #if defined(USE_MULTICAST)
810  case TYPE_IGMP:
811  {
812  const IGMPv1_packet *igmp = (const IGMPv1_packet*) ps->data;
813 
814  if (igmp->version == 1 && igmp->type == IGMPv1_REPORT)
815  igmpstats.igps_snd_reports++;
816  return;
817  }
818 #endif
819 
820  case TYPE_UDP_HEAD:
821  udpstats.udps_opackets++;
822  return;
823 
824 #if !defined(USE_UDP_ONLY)
825  case TYPE_TCP_HEAD:
826  {
827  const tcp_Header *tcp = (const tcp_Header*) ps->data;
828  BYTE flags;
829 
830  flags = tcp->flags & tcp_FlagMASK;
831  tcpstats.tcps_sndtotal++;
832 
833  if (flags & (tcp_FlagSYN|tcp_FlagFIN|tcp_FlagRST))
834  tcpstats.tcps_sndctrl++;
835  else if (flags & tcp_FlagACK) /* ACK only flag */
836  tcpstats.tcps_sndacks++;
837  if (flags & tcp_FlagURG)
838  tcpstats.tcps_sndurg++;
839  if (flags & (tcp_FlagFIN|tcp_FlagRST))
840  tcpstats.tcps_closed++;
841  }
842  break;
843 
844  case TYPE_TCP_DATA:
845  if (ps->len > 0)
846  {
847  tcpstats.tcps_sndpack++;
848  tcpstats.tcps_sndbyte += ps->len;
849  }
850  return; /* nothing behind this */
851 #endif
852 
853  default: ; /* squelch gcc warning */
854  }
855  }
856 
857  if (!got_ip)
858  macstats.non_ip_sent++;
859 }
860 #endif /* USE_STATISTICS */
861 
Definition: pcpkt.h:135
int pkt_waiting(void)
Return number of packets waiting in queue.
Definition: pcpkt.c:1378
Definition: ip_var.h:131
DWORD vj_sd
VJ's alg, standard deviation (RTTVAR)
Definition: wattcp.h:644
void update_out_stat(void)
Definition: pcstat.c:724
BYTE cwindow
Congestion window.
Definition: wattcp.h:639
Definition: pcstat.h:44
DWORD start_day
Start-day of watt_sock_init()
Definition: timer.c:48
DWORD get_day_num(void)
Simplified method of getting days since 1970-01-01.
Definition: misc.c:200
Core definitions.
Definition: ip_icmp.h:62
Definition: igmp.h:62
DWORD pkt_dropped(void)
Return number of packets dropped.
Definition: pcpkt.c:1394
mac_address _eth_addr
Local link-layer source address.
Definition: pcsed.c:50
DWORD vj_sa
VJ's alg, standard average (SRTT)
Definition: wattcp.h:643
int pkt_get_stats(struct PktStats *stats, struct PktStats *total)
Get PKTDRVR statistics.
Definition: pcpkt.c:1243
u_long ips_reassembled
Definition: ip_var.h:149
unsigned long long uint64
our unsigned "long long" type
Definition: wattcp.h:60
Definition: ip.h:67
char _pktdrvrname[20]
Name of PKDRVR.
Definition: pcpkt.c:62
Definition: in.h:146
BOOL _pktserial
using serial driver, SLIP/PPP
Definition: pcpkt.c:54
Definition: tcp.h:778
void update_in_stat(void)
Definition: pcstat.c:583