xref: /freebsd/tools/tools/ifinfo/rfc1650.c (revision 61e21613)
1 #include <sys/types.h>
2 #include <sys/socket.h>		/* for PF_LINK */
3 #include <sys/sysctl.h>
4 #include <sys/time.h>
5 
6 #include <err.h>
7 #include <stdio.h>
8 #include <string.h>
9 #include <sysexits.h>
10 
11 #include <net/if.h>
12 #include <net/if_types.h>
13 #include <net/if_mib.h>
14 
15 #include "ifinfo.h"
16 
17 #define print(msg, var) \
18 	if (var) printf("\t" msg ": %lu\n", (u_long)var)
19 
20 static void identify_chipset(u_int32_t chipset);
21 
22 void
23 print_1650(const void *xmd, size_t len)
24 {
25 	const struct ifmib_iso_8802_3 *md = xmd;
26 
27 	if (len != sizeof *md)
28 		warnx("cannot interpret %lu bytes of MIB data", (u_long)len);
29 
30 	identify_chipset(md->dot3StatsEtherChipSet);
31 	print("Alignment errors", md->dot3StatsAlignmentErrors);
32 	print("FCS errors", md->dot3StatsFCSErrors);
33 	print("Single-collision frames", md->dot3StatsSingleCollisionFrames);
34 	print("Multiple-collision frames", md->dot3StatsMultipleCollisionFrames);
35 	print("SQE (Heartbeat) test errors", md->dot3StatsSQETestErrors);
36 	print("Deferred transmissions", md->dot3StatsDeferredTransmissions);
37 	print("Late collisions", md->dot3StatsLateCollisions);
38 	print("Excessive collisions", md->dot3StatsExcessiveCollisions);
39 	print("Internal transmit errors", md->dot3StatsInternalMacTransmitErrors);
40 	print("Carrier sense errors", md->dot3StatsCarrierSenseErrors);
41 	print("Frame-too-long errors", md->dot3StatsFrameTooLongs);
42 	print("Internal receive errors", md->dot3StatsInternalMacReceiveErrors);
43 	print("Missed frames", md->dot3StatsMissedFrames);
44 #define	cprint(num) print("Packets with " #num " collisions", \
45 			  md->dot3StatsCollFrequencies[num - 1])
46 	if (md->dot3Compliance >= DOT3COMPLIANCE_COLLS) {
47 		cprint(1); cprint(2); cprint(3); cprint(4);
48 		cprint(5); cprint(6); cprint(7); cprint(8);
49 		cprint(9); cprint(10); cprint(11); cprint(12);
50 		cprint(13); cprint(14); cprint(15); cprint(16);
51 	}
52 	switch(md->dot3Compliance) {
53 	case DOT3COMPLIANCE_STATS:
54 		printf("\tCompliance: statistics only\n");
55 		break;
56 	case DOT3COMPLIANCE_COLLS:
57 		printf("\tCompliance: statistics and collisions\n");
58 		break;
59 	}
60 }
61 
62 static const char *const amd[] = {
63 	0, "Am7990", "Am79900", "Am79C940"
64 };
65 
66 static const char *const intel[] = {
67 	0, "82586", "82596", "82557"
68 };
69 
70 static const char *const national[] = {
71 	0, "8390", "Sonic"
72 };
73 
74 static const char *const fujitsu[] = {
75 	0, "86950"
76 };
77 
78 static const char *const digital[] = {
79 	0, "DC21040", "DC21140", "DC21041", "DC21140A", "DC21142"
80 };
81 
82 static const char *const westerndigital[] = {
83 	0, "83C690", "83C790"
84 };
85 
86 #define vendor(name, sets) { name, sets, (sizeof sets)/(sizeof sets[0]) }
87 static struct {
88 	const char *name;
89 	const char *const *chips;
90 	size_t len;
91 } chipset_names[] = {
92 	{ 0 },
93 	vendor("AMD", amd),
94 	vendor("Intel", intel),
95 	{ 0 },
96 	vendor("National Semiconductor", national),
97 	vendor("Fujitsu", fujitsu),
98 	vendor("Digital", digital),
99 	vendor("Western Digital", westerndigital)
100 };
101 
102 static void
103 identify_chipset(u_int32_t chipset)
104 {
105 	enum dot3Vendors vendor = DOT3CHIPSET_VENDOR(chipset);
106 	u_int part = DOT3CHIPSET_PART(chipset);
107 
108 	printf("\tChipset: ");
109 	if (vendor < 1
110 	    || vendor >= (sizeof chipset_names)/(sizeof chipset_names[0])
111 	    || !chipset_names[vendor].name) {
112 		printf("unknown\n");
113 		return;
114 	}
115 
116 	printf("%s ", chipset_names[vendor].name);
117 	if (part < 1 || part >= chipset_names[vendor].len) {
118 		printf("unknown\n");
119 		return;
120 	}
121 
122 	printf("%s\n", chipset_names[vendor].chips[part]);
123 }
124 
125