41 42#include <net/if.h> 43#include <net/if_dl.h> 44#include <net/if_types.h> 45#include <netinet/in.h> 46#include <netinet/in_var.h> 47#define KERNEL 1 48#include <netinet/if_ether.h> 49#undef KERNEL 50#include <netipx/ipx.h> 51#include <netipx/ipx_if.h> 52#ifdef NS 53#include <netns/ns.h> 54#include <netns/ns_if.h> 55#endif 56#ifdef ISO 57#include <netiso/iso.h> 58#include <netiso/iso_var.h> 59#endif 60#include <arpa/inet.h> 61 62#include <signal.h> 63#include <stdio.h> 64#include <string.h> 65#include <unistd.h> 66 67#include "netstat.h" 68 69#define YES 1 70#define NO 0 71 72static void sidewaysintpr __P((u_int, u_long)); 73static void catchalarm __P((int)); 74 75/* 76 * Print a description of the network interfaces. 77 */ 78void 79intpr(interval, ifnetaddr) 80 int interval; 81 u_long ifnetaddr; 82{ 83 struct ifnet ifnet; 84 union { 85 struct ifaddr ifa; 86 struct in_ifaddr in; 87 struct ipx_ifaddr ipx; 88#ifdef NS 89 struct ns_ifaddr ns; 90#endif 91#ifdef ISO 92 struct iso_ifaddr iso; 93#endif 94 } ifaddr; 95 u_long ifaddraddr; 96 u_long ifaddrfound; 97 u_long ifnetfound; 98 struct sockaddr *sa; 99 char name[32], tname[16]; 100 101 if (ifnetaddr == 0) { 102 printf("ifnet: symbol not defined\n"); 103 return; 104 } 105 if (interval) { 106 sidewaysintpr((unsigned)interval, ifnetaddr); 107 return; 108 } 109 if (kread(ifnetaddr, (char *)&ifnetaddr, sizeof ifnetaddr)) 110 return; 111 printf("%-5.5s %-5.5s %-13.13s %-15.15s %8.8s %5.5s", 112 "Name", "Mtu", "Network", "Address", "Ipkts", "Ierrs"); 113 if (bflag) 114 printf(" %10.10s","Ibytes"); 115 printf(" %8.8s %5.5s", "Opkts", "Oerrs"); 116 if (bflag) 117 printf(" %10.10s","Obytes"); 118 printf(" %5s", "Coll"); 119 if (tflag) 120 printf(" %s", "Time"); 121 if (dflag) 122 printf(" %s", "Drop"); 123 putchar('\n'); 124 ifaddraddr = 0; 125 while (ifnetaddr || ifaddraddr) { 126 struct sockaddr_in *sin; 127 register char *cp; 128 int n, m; 129 130 if (ifaddraddr == 0) { 131 ifnetfound = ifnetaddr; 132 if (kread(ifnetaddr, (char *)&ifnet, sizeof ifnet) || 133 kread((u_long)ifnet.if_name, tname, 16)) 134 return; 135 tname[15] = '\0'; 136 ifnetaddr = (u_long)ifnet.if_next; 137 snprintf(name, 32, "%s%d", tname, ifnet.if_unit); 138 if (interface != 0 && (strcmp(name, interface) != 0)) 139 continue; 140 cp = index(name, '\0'); 141 if ((ifnet.if_flags&IFF_UP) == 0) 142 *cp++ = '*'; 143 *cp = '\0'; 144 ifaddraddr = (u_long)ifnet.if_addrlist; 145 } 146 printf("%-5.5s %-5lu ", name, ifnet.if_mtu); 147 ifaddrfound = ifaddraddr; 148 if (ifaddraddr == 0) { 149 printf("%-13.13s ", "none"); 150 printf("%-15.15s ", "none"); 151 } else { 152 if (kread(ifaddraddr, (char *)&ifaddr, sizeof ifaddr)) { 153 ifaddraddr = 0; 154 continue; 155 } 156#define CP(x) ((char *)(x)) 157 cp = (CP(ifaddr.ifa.ifa_addr) - CP(ifaddraddr)) + 158 CP(&ifaddr); sa = (struct sockaddr *)cp; 159 switch (sa->sa_family) { 160 case AF_UNSPEC: 161 printf("%-13.13s ", "none"); 162 printf("%-15.15s ", "none"); 163 break; 164 case AF_INET: 165 sin = (struct sockaddr_in *)sa; 166#ifdef notdef 167 /* can't use inet_makeaddr because kernel 168 * keeps nets unshifted. 169 */ 170 in = inet_makeaddr(ifaddr.in.ia_subnet, 171 INADDR_ANY); 172 printf("%-13.13s ", netname(in.s_addr, 173 ifaddr.in.ia_subnetmask)); 174#else 175 printf("%-13.13s ", 176 netname(htonl(ifaddr.in.ia_subnet), 177 ifaddr.in.ia_subnetmask)); 178#endif 179 printf("%-15.15s ", 180 routename(sin->sin_addr.s_addr)); 181 break; 182 case AF_IPX: 183 { 184 struct sockaddr_ipx *sipx = 185 (struct sockaddr_ipx *)sa; 186 u_long net; 187 char netnum[10]; 188 189 *(union ipx_net *) &net = sipx->sipx_addr.x_net; 190 sprintf(netnum, "%lx", ntohl(net)); 191 printf("ipx:%-8s ", netnum); 192/* printf("ipx:%-8s ", netname(net, 0L)); */ 193 printf("%-15s ", 194 ipx_phost((struct sockaddr *)sipx)); 195 } 196 break; 197 198 case AF_APPLETALK: 199 printf("atalk:%-12.12s ",atalk_print(sa,0x10) ); 200 printf("%-9.9s ",atalk_print(sa,0x0b) ); 201 break; 202#ifdef NS 203 case AF_NS: 204 { 205 struct sockaddr_ns *sns = 206 (struct sockaddr_ns *)sa; 207 u_long net; 208 char netnum[10]; 209 210 *(union ns_net *) &net = sns->sns_addr.x_net; 211 sprintf(netnum, "%lxH", ntohl(net)); 212 upHex(netnum); 213 printf("ns:%-8s ", netnum); 214 printf("%-15s ", 215 ns_phost((struct sockaddr *)sns)); 216 } 217 break; 218#endif 219 case AF_LINK: 220 { 221 struct sockaddr_dl *sdl = 222 (struct sockaddr_dl *)sa; 223 cp = (char *)LLADDR(sdl); 224 n = sdl->sdl_alen; 225 } 226 m = printf("%-11.11s ", "<Link>"); 227 goto hexprint; 228 default: 229 m = printf("(%d)", sa->sa_family); 230 for (cp = sa->sa_len + (char *)sa; 231 --cp > sa->sa_data && (*cp == 0);) {} 232 n = cp - sa->sa_data + 1; 233 cp = sa->sa_data; 234 hexprint: 235 while (--n >= 0) 236 m += printf("%02x%c", *cp++ & 0xff, 237 n > 0 ? '.' : ' '); 238 m = 30 - m; 239 while (m-- > 0) 240 putchar(' '); 241 break; 242 } 243 ifaddraddr = (u_long)ifaddr.ifa.ifa_next; 244 } 245 printf("%8lu %5lu ", 246 ifnet.if_ipackets, ifnet.if_ierrors); 247 if (bflag) 248 printf("%10lu ", ifnet.if_ibytes); 249 printf("%8lu %5lu ", 250 ifnet.if_opackets, ifnet.if_oerrors); 251 if (bflag) 252 printf("%10lu ", ifnet.if_obytes); 253 printf("%5lu", ifnet.if_collisions); 254 if (tflag) 255 printf(" %3d", ifnet.if_timer); 256 if (dflag) 257 printf(" %3d", ifnet.if_snd.ifq_drops); 258 putchar('\n'); 259 if (aflag && ifaddrfound) { 260 /* 261 * Print family's multicast addresses 262 */ 263 switch (sa->sa_family) { 264 case AF_INET: 265 { 266 u_long multiaddr; 267 struct in_multi inm; 268 269 multiaddr = (u_long)ifaddr.in.ia_multiaddrs.lh_first; 270 while (multiaddr != 0) { 271 kread(multiaddr, (char *)&inm, 272 sizeof inm); 273 multiaddr = (u_long)inm.inm_entry.le_next; 274 printf("%23s %s\n", "", 275 routename(inm.inm_addr.s_addr)); 276 } 277 break; 278 } 279 case AF_LINK: 280 switch (ifnet.if_type) { 281 case IFT_ETHER: 282 case IFT_FDDI: /*XXX*/ 283 { 284 off_t multiaddr; 285 struct arpcom ac; 286 struct ether_multi enm; 287 288 kread(ifnetfound, (char *)&ac, sizeof ac); 289 multiaddr = (u_long)ac.ac_multiaddrs; 290 while (multiaddr != 0) { 291 kread(multiaddr, (char *)&enm, 292 sizeof enm); 293 multiaddr = (u_long)enm.enm_next; 294 printf("%23s %s", "", 295 ether_ntoa(&enm.enm_addrlo)); 296 if (bcmp(&enm.enm_addrlo, 297 &enm.enm_addrhi, 6) != 0) 298 printf(" to %s", 299 ether_ntoa(&enm.enm_addrhi)); 300 printf("\n"); 301 } 302 break; 303 } 304 default: 305 break; 306 } 307 default: 308 break; 309 } 310 } 311 } 312} 313 314#define MAXIF 10 315struct iftot { 316 char ift_name[16]; /* interface name */ 317 u_int ift_ip; /* input packets */ 318 u_int ift_ie; /* input errors */ 319 u_int ift_op; /* output packets */ 320 u_int ift_oe; /* output errors */ 321 u_int ift_co; /* collisions */ 322 u_int ift_dr; /* drops */ 323 u_int ift_ib; /* input bytes */ 324 u_int ift_ob; /* output bytes */ 325} iftot[MAXIF]; 326 327u_char signalled; /* set if alarm goes off "early" */ 328 329/* 330 * Print a running summary of interface statistics. 331 * Repeat display every interval seconds, showing statistics 332 * collected over that interval. Assumes that interval is non-zero. 333 * First line printed at top of screen is always cumulative. 334 */ 335static void 336sidewaysintpr(interval, off) 337 unsigned interval; 338 u_long off; 339{ 340 struct ifnet ifnet; 341 u_long firstifnet; 342 register struct iftot *ip, *total; 343 register int line; 344 struct iftot *lastif, *sum, *interesting; 345 int oldmask, first; 346 u_long interesting_off; 347 348 if (kread(off, (char *)&firstifnet, sizeof (u_long))) 349 return; 350 lastif = iftot; 351 sum = iftot + MAXIF - 1; 352 total = sum - 1; 353 interesting = NULL; 354 interesting_off = 0; 355 for (off = firstifnet, ip = iftot; off;) { 356 char name[16], tname[16]; 357 358 if (kread(off, (char *)&ifnet, sizeof ifnet)) 359 break; 360 if (kread((u_long)ifnet.if_name, tname, 16)) 361 break; 362 tname[15] = '\0'; 363 snprintf(name, 16, "%s%d", tname, ifnet.if_unit); 364 if (interface && strcmp(name, interface) == 0) { 365 interesting = ip; 366 interesting_off = off; 367 } 368 snprintf(ip->ift_name, 16, "(%s)", name);; 369 ip++; 370 if (ip >= iftot + MAXIF - 2) 371 break; 372 off = (u_long) ifnet.if_next; 373 } 374 lastif = ip; 375 376 (void)signal(SIGALRM, catchalarm); 377 signalled = NO; 378 (void)alarm(interval); 379 for (ip = iftot; ip < iftot + MAXIF; ip++) { 380 ip->ift_ip = 0; 381 ip->ift_ie = 0; 382 ip->ift_ib = 0; 383 ip->ift_op = 0; 384 ip->ift_oe = 0; 385 ip->ift_ob = 0; 386 ip->ift_co = 0; 387 ip->ift_dr = 0; 388 } 389 first = 1; 390banner: 391 printf("%17s %14s %16s", "input", 392 interesting ? interesting->ift_name : "(Total)", "output"); 393 putchar('\n'); 394 printf("%10s %5s %10s %10s %5s %10s %5s", 395 "packets", "errs", "bytes", "packets", "errs", "bytes", "colls"); 396 if (dflag) 397 printf(" %5.5s", "drops"); 398 putchar('\n'); 399 fflush(stdout); 400 line = 0; 401loop: 402 if (interesting != NULL) { 403 ip = interesting; 404 if (kread(interesting_off, (char *)&ifnet, sizeof ifnet)) { 405 printf("???\n"); 406 exit(1); 407 }; 408 if (!first) { 409 printf("%10lu %5lu %10lu %10lu %5lu %10lu %5lu", 410 ifnet.if_ipackets - ip->ift_ip, 411 ifnet.if_ierrors - ip->ift_ie, 412 ifnet.if_ibytes - ip->ift_ib, 413 ifnet.if_opackets - ip->ift_op, 414 ifnet.if_oerrors - ip->ift_oe, 415 ifnet.if_obytes - ip->ift_ob, 416 ifnet.if_collisions - ip->ift_co); 417 if (dflag) 418 printf(" %5u", ifnet.if_snd.ifq_drops - ip->ift_dr); 419 } 420 ip->ift_ip = ifnet.if_ipackets; 421 ip->ift_ie = ifnet.if_ierrors; 422 ip->ift_ib = ifnet.if_ibytes; 423 ip->ift_op = ifnet.if_opackets; 424 ip->ift_oe = ifnet.if_oerrors; 425 ip->ift_ob = ifnet.if_obytes; 426 ip->ift_co = ifnet.if_collisions; 427 ip->ift_dr = ifnet.if_snd.ifq_drops; 428 } else { 429 sum->ift_ip = 0; 430 sum->ift_ie = 0; 431 sum->ift_ib = 0; 432 sum->ift_op = 0; 433 sum->ift_oe = 0; 434 sum->ift_ob = 0; 435 sum->ift_co = 0; 436 sum->ift_dr = 0; 437 for (off = firstifnet, ip = iftot; off && ip < lastif; ip++) { 438 if (kread(off, (char *)&ifnet, sizeof ifnet)) { 439 off = 0; 440 continue; 441 } 442 sum->ift_ip += ifnet.if_ipackets; 443 sum->ift_ie += ifnet.if_ierrors; 444 sum->ift_ib += ifnet.if_ibytes; 445 sum->ift_op += ifnet.if_opackets; 446 sum->ift_oe += ifnet.if_oerrors; 447 sum->ift_ob += ifnet.if_obytes; 448 sum->ift_co += ifnet.if_collisions; 449 sum->ift_dr += ifnet.if_snd.ifq_drops; 450 off = (u_long) ifnet.if_next; 451 } 452 if (!first) { 453 printf("%10u %5u %10u %10u %5u %10u %5u", 454 sum->ift_ip - total->ift_ip, 455 sum->ift_ie - total->ift_ie, 456 sum->ift_ib - total->ift_ib, 457 sum->ift_op - total->ift_op, 458 sum->ift_oe - total->ift_oe, 459 sum->ift_ob - total->ift_ob, 460 sum->ift_co - total->ift_co); 461 if (dflag) 462 printf(" %5u", sum->ift_dr - total->ift_dr); 463 } 464 *total = *sum; 465 } 466 if (!first) 467 putchar('\n'); 468 fflush(stdout); 469 oldmask = sigblock(sigmask(SIGALRM)); 470 if (! signalled) { 471 sigpause(0); 472 } 473 sigsetmask(oldmask); 474 signalled = NO; 475 (void)alarm(interval); 476 line++; 477 first = 0; 478 if (line == 21) 479 goto banner; 480 else 481 goto loop; 482 /*NOTREACHED*/ 483} 484 485/* 486 * Called if an interval expires before sidewaysintpr has completed a loop. 487 * Sets a flag to not wait for the alarm. 488 */ 489static void 490catchalarm(signo) 491 int signo; 492{ 493 signalled = YES; 494}
| 42 43#include <net/if.h> 44#include <net/if_dl.h> 45#include <net/if_types.h> 46#include <netinet/in.h> 47#include <netinet/in_var.h> 48#define KERNEL 1 49#include <netinet/if_ether.h> 50#undef KERNEL 51#include <netipx/ipx.h> 52#include <netipx/ipx_if.h> 53#ifdef NS 54#include <netns/ns.h> 55#include <netns/ns_if.h> 56#endif 57#ifdef ISO 58#include <netiso/iso.h> 59#include <netiso/iso_var.h> 60#endif 61#include <arpa/inet.h> 62 63#include <signal.h> 64#include <stdio.h> 65#include <string.h> 66#include <unistd.h> 67 68#include "netstat.h" 69 70#define YES 1 71#define NO 0 72 73static void sidewaysintpr __P((u_int, u_long)); 74static void catchalarm __P((int)); 75 76/* 77 * Print a description of the network interfaces. 78 */ 79void 80intpr(interval, ifnetaddr) 81 int interval; 82 u_long ifnetaddr; 83{ 84 struct ifnet ifnet; 85 union { 86 struct ifaddr ifa; 87 struct in_ifaddr in; 88 struct ipx_ifaddr ipx; 89#ifdef NS 90 struct ns_ifaddr ns; 91#endif 92#ifdef ISO 93 struct iso_ifaddr iso; 94#endif 95 } ifaddr; 96 u_long ifaddraddr; 97 u_long ifaddrfound; 98 u_long ifnetfound; 99 struct sockaddr *sa; 100 char name[32], tname[16]; 101 102 if (ifnetaddr == 0) { 103 printf("ifnet: symbol not defined\n"); 104 return; 105 } 106 if (interval) { 107 sidewaysintpr((unsigned)interval, ifnetaddr); 108 return; 109 } 110 if (kread(ifnetaddr, (char *)&ifnetaddr, sizeof ifnetaddr)) 111 return; 112 printf("%-5.5s %-5.5s %-13.13s %-15.15s %8.8s %5.5s", 113 "Name", "Mtu", "Network", "Address", "Ipkts", "Ierrs"); 114 if (bflag) 115 printf(" %10.10s","Ibytes"); 116 printf(" %8.8s %5.5s", "Opkts", "Oerrs"); 117 if (bflag) 118 printf(" %10.10s","Obytes"); 119 printf(" %5s", "Coll"); 120 if (tflag) 121 printf(" %s", "Time"); 122 if (dflag) 123 printf(" %s", "Drop"); 124 putchar('\n'); 125 ifaddraddr = 0; 126 while (ifnetaddr || ifaddraddr) { 127 struct sockaddr_in *sin; 128 register char *cp; 129 int n, m; 130 131 if (ifaddraddr == 0) { 132 ifnetfound = ifnetaddr; 133 if (kread(ifnetaddr, (char *)&ifnet, sizeof ifnet) || 134 kread((u_long)ifnet.if_name, tname, 16)) 135 return; 136 tname[15] = '\0'; 137 ifnetaddr = (u_long)ifnet.if_next; 138 snprintf(name, 32, "%s%d", tname, ifnet.if_unit); 139 if (interface != 0 && (strcmp(name, interface) != 0)) 140 continue; 141 cp = index(name, '\0'); 142 if ((ifnet.if_flags&IFF_UP) == 0) 143 *cp++ = '*'; 144 *cp = '\0'; 145 ifaddraddr = (u_long)ifnet.if_addrlist; 146 } 147 printf("%-5.5s %-5lu ", name, ifnet.if_mtu); 148 ifaddrfound = ifaddraddr; 149 if (ifaddraddr == 0) { 150 printf("%-13.13s ", "none"); 151 printf("%-15.15s ", "none"); 152 } else { 153 if (kread(ifaddraddr, (char *)&ifaddr, sizeof ifaddr)) { 154 ifaddraddr = 0; 155 continue; 156 } 157#define CP(x) ((char *)(x)) 158 cp = (CP(ifaddr.ifa.ifa_addr) - CP(ifaddraddr)) + 159 CP(&ifaddr); sa = (struct sockaddr *)cp; 160 switch (sa->sa_family) { 161 case AF_UNSPEC: 162 printf("%-13.13s ", "none"); 163 printf("%-15.15s ", "none"); 164 break; 165 case AF_INET: 166 sin = (struct sockaddr_in *)sa; 167#ifdef notdef 168 /* can't use inet_makeaddr because kernel 169 * keeps nets unshifted. 170 */ 171 in = inet_makeaddr(ifaddr.in.ia_subnet, 172 INADDR_ANY); 173 printf("%-13.13s ", netname(in.s_addr, 174 ifaddr.in.ia_subnetmask)); 175#else 176 printf("%-13.13s ", 177 netname(htonl(ifaddr.in.ia_subnet), 178 ifaddr.in.ia_subnetmask)); 179#endif 180 printf("%-15.15s ", 181 routename(sin->sin_addr.s_addr)); 182 break; 183 case AF_IPX: 184 { 185 struct sockaddr_ipx *sipx = 186 (struct sockaddr_ipx *)sa; 187 u_long net; 188 char netnum[10]; 189 190 *(union ipx_net *) &net = sipx->sipx_addr.x_net; 191 sprintf(netnum, "%lx", ntohl(net)); 192 printf("ipx:%-8s ", netnum); 193/* printf("ipx:%-8s ", netname(net, 0L)); */ 194 printf("%-15s ", 195 ipx_phost((struct sockaddr *)sipx)); 196 } 197 break; 198 199 case AF_APPLETALK: 200 printf("atalk:%-12.12s ",atalk_print(sa,0x10) ); 201 printf("%-9.9s ",atalk_print(sa,0x0b) ); 202 break; 203#ifdef NS 204 case AF_NS: 205 { 206 struct sockaddr_ns *sns = 207 (struct sockaddr_ns *)sa; 208 u_long net; 209 char netnum[10]; 210 211 *(union ns_net *) &net = sns->sns_addr.x_net; 212 sprintf(netnum, "%lxH", ntohl(net)); 213 upHex(netnum); 214 printf("ns:%-8s ", netnum); 215 printf("%-15s ", 216 ns_phost((struct sockaddr *)sns)); 217 } 218 break; 219#endif 220 case AF_LINK: 221 { 222 struct sockaddr_dl *sdl = 223 (struct sockaddr_dl *)sa; 224 cp = (char *)LLADDR(sdl); 225 n = sdl->sdl_alen; 226 } 227 m = printf("%-11.11s ", "<Link>"); 228 goto hexprint; 229 default: 230 m = printf("(%d)", sa->sa_family); 231 for (cp = sa->sa_len + (char *)sa; 232 --cp > sa->sa_data && (*cp == 0);) {} 233 n = cp - sa->sa_data + 1; 234 cp = sa->sa_data; 235 hexprint: 236 while (--n >= 0) 237 m += printf("%02x%c", *cp++ & 0xff, 238 n > 0 ? '.' : ' '); 239 m = 30 - m; 240 while (m-- > 0) 241 putchar(' '); 242 break; 243 } 244 ifaddraddr = (u_long)ifaddr.ifa.ifa_next; 245 } 246 printf("%8lu %5lu ", 247 ifnet.if_ipackets, ifnet.if_ierrors); 248 if (bflag) 249 printf("%10lu ", ifnet.if_ibytes); 250 printf("%8lu %5lu ", 251 ifnet.if_opackets, ifnet.if_oerrors); 252 if (bflag) 253 printf("%10lu ", ifnet.if_obytes); 254 printf("%5lu", ifnet.if_collisions); 255 if (tflag) 256 printf(" %3d", ifnet.if_timer); 257 if (dflag) 258 printf(" %3d", ifnet.if_snd.ifq_drops); 259 putchar('\n'); 260 if (aflag && ifaddrfound) { 261 /* 262 * Print family's multicast addresses 263 */ 264 switch (sa->sa_family) { 265 case AF_INET: 266 { 267 u_long multiaddr; 268 struct in_multi inm; 269 270 multiaddr = (u_long)ifaddr.in.ia_multiaddrs.lh_first; 271 while (multiaddr != 0) { 272 kread(multiaddr, (char *)&inm, 273 sizeof inm); 274 multiaddr = (u_long)inm.inm_entry.le_next; 275 printf("%23s %s\n", "", 276 routename(inm.inm_addr.s_addr)); 277 } 278 break; 279 } 280 case AF_LINK: 281 switch (ifnet.if_type) { 282 case IFT_ETHER: 283 case IFT_FDDI: /*XXX*/ 284 { 285 off_t multiaddr; 286 struct arpcom ac; 287 struct ether_multi enm; 288 289 kread(ifnetfound, (char *)&ac, sizeof ac); 290 multiaddr = (u_long)ac.ac_multiaddrs; 291 while (multiaddr != 0) { 292 kread(multiaddr, (char *)&enm, 293 sizeof enm); 294 multiaddr = (u_long)enm.enm_next; 295 printf("%23s %s", "", 296 ether_ntoa(&enm.enm_addrlo)); 297 if (bcmp(&enm.enm_addrlo, 298 &enm.enm_addrhi, 6) != 0) 299 printf(" to %s", 300 ether_ntoa(&enm.enm_addrhi)); 301 printf("\n"); 302 } 303 break; 304 } 305 default: 306 break; 307 } 308 default: 309 break; 310 } 311 } 312 } 313} 314 315#define MAXIF 10 316struct iftot { 317 char ift_name[16]; /* interface name */ 318 u_int ift_ip; /* input packets */ 319 u_int ift_ie; /* input errors */ 320 u_int ift_op; /* output packets */ 321 u_int ift_oe; /* output errors */ 322 u_int ift_co; /* collisions */ 323 u_int ift_dr; /* drops */ 324 u_int ift_ib; /* input bytes */ 325 u_int ift_ob; /* output bytes */ 326} iftot[MAXIF]; 327 328u_char signalled; /* set if alarm goes off "early" */ 329 330/* 331 * Print a running summary of interface statistics. 332 * Repeat display every interval seconds, showing statistics 333 * collected over that interval. Assumes that interval is non-zero. 334 * First line printed at top of screen is always cumulative. 335 */ 336static void 337sidewaysintpr(interval, off) 338 unsigned interval; 339 u_long off; 340{ 341 struct ifnet ifnet; 342 u_long firstifnet; 343 register struct iftot *ip, *total; 344 register int line; 345 struct iftot *lastif, *sum, *interesting; 346 int oldmask, first; 347 u_long interesting_off; 348 349 if (kread(off, (char *)&firstifnet, sizeof (u_long))) 350 return; 351 lastif = iftot; 352 sum = iftot + MAXIF - 1; 353 total = sum - 1; 354 interesting = NULL; 355 interesting_off = 0; 356 for (off = firstifnet, ip = iftot; off;) { 357 char name[16], tname[16]; 358 359 if (kread(off, (char *)&ifnet, sizeof ifnet)) 360 break; 361 if (kread((u_long)ifnet.if_name, tname, 16)) 362 break; 363 tname[15] = '\0'; 364 snprintf(name, 16, "%s%d", tname, ifnet.if_unit); 365 if (interface && strcmp(name, interface) == 0) { 366 interesting = ip; 367 interesting_off = off; 368 } 369 snprintf(ip->ift_name, 16, "(%s)", name);; 370 ip++; 371 if (ip >= iftot + MAXIF - 2) 372 break; 373 off = (u_long) ifnet.if_next; 374 } 375 lastif = ip; 376 377 (void)signal(SIGALRM, catchalarm); 378 signalled = NO; 379 (void)alarm(interval); 380 for (ip = iftot; ip < iftot + MAXIF; ip++) { 381 ip->ift_ip = 0; 382 ip->ift_ie = 0; 383 ip->ift_ib = 0; 384 ip->ift_op = 0; 385 ip->ift_oe = 0; 386 ip->ift_ob = 0; 387 ip->ift_co = 0; 388 ip->ift_dr = 0; 389 } 390 first = 1; 391banner: 392 printf("%17s %14s %16s", "input", 393 interesting ? interesting->ift_name : "(Total)", "output"); 394 putchar('\n'); 395 printf("%10s %5s %10s %10s %5s %10s %5s", 396 "packets", "errs", "bytes", "packets", "errs", "bytes", "colls"); 397 if (dflag) 398 printf(" %5.5s", "drops"); 399 putchar('\n'); 400 fflush(stdout); 401 line = 0; 402loop: 403 if (interesting != NULL) { 404 ip = interesting; 405 if (kread(interesting_off, (char *)&ifnet, sizeof ifnet)) { 406 printf("???\n"); 407 exit(1); 408 }; 409 if (!first) { 410 printf("%10lu %5lu %10lu %10lu %5lu %10lu %5lu", 411 ifnet.if_ipackets - ip->ift_ip, 412 ifnet.if_ierrors - ip->ift_ie, 413 ifnet.if_ibytes - ip->ift_ib, 414 ifnet.if_opackets - ip->ift_op, 415 ifnet.if_oerrors - ip->ift_oe, 416 ifnet.if_obytes - ip->ift_ob, 417 ifnet.if_collisions - ip->ift_co); 418 if (dflag) 419 printf(" %5u", ifnet.if_snd.ifq_drops - ip->ift_dr); 420 } 421 ip->ift_ip = ifnet.if_ipackets; 422 ip->ift_ie = ifnet.if_ierrors; 423 ip->ift_ib = ifnet.if_ibytes; 424 ip->ift_op = ifnet.if_opackets; 425 ip->ift_oe = ifnet.if_oerrors; 426 ip->ift_ob = ifnet.if_obytes; 427 ip->ift_co = ifnet.if_collisions; 428 ip->ift_dr = ifnet.if_snd.ifq_drops; 429 } else { 430 sum->ift_ip = 0; 431 sum->ift_ie = 0; 432 sum->ift_ib = 0; 433 sum->ift_op = 0; 434 sum->ift_oe = 0; 435 sum->ift_ob = 0; 436 sum->ift_co = 0; 437 sum->ift_dr = 0; 438 for (off = firstifnet, ip = iftot; off && ip < lastif; ip++) { 439 if (kread(off, (char *)&ifnet, sizeof ifnet)) { 440 off = 0; 441 continue; 442 } 443 sum->ift_ip += ifnet.if_ipackets; 444 sum->ift_ie += ifnet.if_ierrors; 445 sum->ift_ib += ifnet.if_ibytes; 446 sum->ift_op += ifnet.if_opackets; 447 sum->ift_oe += ifnet.if_oerrors; 448 sum->ift_ob += ifnet.if_obytes; 449 sum->ift_co += ifnet.if_collisions; 450 sum->ift_dr += ifnet.if_snd.ifq_drops; 451 off = (u_long) ifnet.if_next; 452 } 453 if (!first) { 454 printf("%10u %5u %10u %10u %5u %10u %5u", 455 sum->ift_ip - total->ift_ip, 456 sum->ift_ie - total->ift_ie, 457 sum->ift_ib - total->ift_ib, 458 sum->ift_op - total->ift_op, 459 sum->ift_oe - total->ift_oe, 460 sum->ift_ob - total->ift_ob, 461 sum->ift_co - total->ift_co); 462 if (dflag) 463 printf(" %5u", sum->ift_dr - total->ift_dr); 464 } 465 *total = *sum; 466 } 467 if (!first) 468 putchar('\n'); 469 fflush(stdout); 470 oldmask = sigblock(sigmask(SIGALRM)); 471 if (! signalled) { 472 sigpause(0); 473 } 474 sigsetmask(oldmask); 475 signalled = NO; 476 (void)alarm(interval); 477 line++; 478 first = 0; 479 if (line == 21) 480 goto banner; 481 else 482 goto loop; 483 /*NOTREACHED*/ 484} 485 486/* 487 * Called if an interval expires before sidewaysintpr has completed a loop. 488 * Sets a flag to not wait for the alarm. 489 */ 490static void 491catchalarm(signo) 492 int signo; 493{ 494 signalled = YES; 495}
|