version 1.55, 2007/12/19 01:47:00 |
version 1.56, 2008/01/03 21:01:40 |
|
|
* SUCH DAMAGE. |
* SUCH DAMAGE. |
*/ |
*/ |
|
|
|
#include <sys/param.h> |
#include <sys/types.h> |
#include <sys/types.h> |
#include <sys/protosw.h> |
#include <sys/protosw.h> |
#include <sys/socket.h> |
#include <sys/socket.h> |
|
#include <sys/sysctl.h> |
|
|
#include <net/if.h> |
#include <net/if.h> |
#include <net/if_dl.h> |
#include <net/if_dl.h> |
#include <net/if_types.h> |
#include <net/if_types.h> |
|
#include <net/route.h> |
#include <netinet/in.h> |
#include <netinet/in.h> |
#include <netinet/in_var.h> |
#include <netinet/in_var.h> |
#include <netinet/if_ether.h> |
#include <netinet/if_ether.h> |
|
|
|
|
#include "netstat.h" |
#include "netstat.h" |
|
|
#define YES 1 |
static void print_addr(struct sockaddr *, struct sockaddr **, struct if_data *); |
#define NO 0 |
static void sidewaysintpr(u_int); |
|
|
static void sidewaysintpr(u_int, u_long); |
|
static void catchalarm(int); |
static void catchalarm(int); |
|
static void get_rtaddrs(int, struct sockaddr *, struct sockaddr **); |
|
static void fetchifs(void); |
|
|
/* |
/* |
* Print a description of the network interfaces. |
* Print a description of the network interfaces. |
|
|
* which is a TAILQ_HEAD. |
* which is a TAILQ_HEAD. |
*/ |
*/ |
void |
void |
intpr(int interval, u_long ifnetaddr) |
intpr(int interval) |
{ |
{ |
struct ifnet ifnet; |
struct if_msghdr ifm; |
union { |
int mib[6] = { CTL_NET, AF_ROUTE, 0, 0, NET_RT_IFLIST, 0 }; |
struct ifaddr ifa; |
char name[IFNAMSIZ + 1]; /* + 1 for the '*' */ |
struct in_ifaddr in; |
char *buf, *next, *lim, *cp; |
struct in6_ifaddr in6; |
struct rt_msghdr *rtm; |
} ifaddr; |
struct ifa_msghdr *ifam; |
u_int64_t total; |
struct if_data *ifd; |
u_long ifaddraddr; |
struct sockaddr *sa, *rti_info[RTAX_MAX]; |
struct sockaddr *sa; |
struct sockaddr_dl *sdl; |
struct ifnet_head ifhead; /* TAILQ_HEAD */ |
u_int64_t total = 0; |
char name[IFNAMSIZ]; |
size_t len; |
|
|
if (ifnetaddr == 0) { |
|
printf("ifnet: symbol not defined\n"); |
|
return; |
|
} |
|
if (interval) { |
if (interval) { |
sidewaysintpr((unsigned)interval, ifnetaddr); |
sidewaysintpr((unsigned)interval); |
return; |
return; |
} |
} |
|
|
/* |
if (sysctl(mib, 6, NULL, &len, NULL, 0) == -1) |
* Find the pointer to the first ifnet structure. Replace |
err(1, "sysctl"); |
* the pointer to the TAILQ_HEAD with the actual pointer |
if ((buf = malloc(len)) == NULL) |
* to the first list element. |
err(1, NULL); |
*/ |
if (sysctl(mib, 6, buf, &len, NULL, 0) == -1) |
if (kread(ifnetaddr, &ifhead, sizeof ifhead)) |
err(1, "sysctl"); |
return; |
|
ifnetaddr = (u_long)TAILQ_FIRST(&ifhead); |
|
|
|
printf("%-7.7s %-5.5s %-11.11s %-17.17s ", |
printf("%-7.7s %-5.5s %-11.11s %-17.17s ", |
"Name", "Mtu", "Network", "Address"); |
"Name", "Mtu", "Network", "Address"); |
|
|
if (dflag) |
if (dflag) |
printf(" %s", "Drop"); |
printf(" %s", "Drop"); |
putchar('\n'); |
putchar('\n'); |
ifaddraddr = 0; |
|
while (ifnetaddr || ifaddraddr) { |
|
struct sockaddr_in *sin; |
|
struct sockaddr_in6 *sin6; |
|
char *cp; |
|
int n, m; |
|
|
|
if (ifaddraddr == 0) { |
lim = buf + len; |
if (kread(ifnetaddr, &ifnet, sizeof ifnet)) |
for (next = buf; next < lim; next += rtm->rtm_msglen) { |
return; |
rtm = (struct rt_msghdr *)next; |
bcopy(ifnet.if_xname, name, IFNAMSIZ); |
if (rtm->rtm_version != RTM_VERSION) |
name[IFNAMSIZ - 1] = '\0'; /* sanity */ |
continue; |
ifnetaddr = (u_long)TAILQ_NEXT(&ifnet, if_list); |
switch (rtm->rtm_type) { |
|
case RTM_IFINFO: |
|
total = 0; |
|
bcopy(next, &ifm, sizeof ifm); |
|
ifd = &ifm.ifm_data; |
|
|
|
sa = (struct sockaddr *)(next + rtm->rtm_hdrlen); |
|
get_rtaddrs(ifm.ifm_addrs, sa, rti_info); |
|
|
|
sdl = (struct sockaddr_dl *)rti_info[RTAX_IFP]; |
|
if (sdl == NULL || sdl->sdl_family != AF_LINK) |
|
continue; |
|
bzero(name, sizeof(name)); |
|
if (sdl->sdl_nlen >= IFNAMSIZ) |
|
memcpy(name, sdl->sdl_data, IFNAMSIZ - 1); |
|
else if (sdl->sdl_nlen > 0) |
|
memcpy(name, sdl->sdl_data, sdl->sdl_nlen); |
|
|
if (interface != 0 && strcmp(name, interface) != 0) |
if (interface != 0 && strcmp(name, interface) != 0) |
continue; |
continue; |
|
|
|
/* mark inactive interfaces with a '*' */ |
cp = strchr(name, '\0'); |
cp = strchr(name, '\0'); |
if ((ifnet.if_flags & IFF_UP) == 0) |
if ((ifm.ifm_flags & IFF_UP) == 0) |
*cp++ = '*'; |
*cp++ = '*'; |
*cp = '\0'; |
*cp = '\0'; |
ifaddraddr = (u_long)TAILQ_FIRST(&ifnet.if_addrlist); |
|
} |
|
|
|
if (qflag) { |
if (qflag) { |
total = ifnet.if_ibytes + ifnet.if_obytes + |
total = ifd->ifi_ibytes + ifd->ifi_obytes + |
ifnet.if_ipackets + ifnet.if_ierrors + |
ifd->ifi_ipackets + ifd->ifi_ierrors + |
ifnet.if_opackets + ifnet.if_oerrors + |
ifd->ifi_opackets + ifd->ifi_oerrors + |
ifnet.if_collisions; |
ifd->ifi_collisions; |
if (tflag) |
if (tflag) |
total += ifnet.if_timer; |
total += 0; // XXX ifnet.if_timer; |
if (dflag) |
if (dflag) |
total += ifnet.if_snd.ifq_drops; |
total += 0; // XXX ifnet.if_snd.ifq_drops; |
if (total == 0) { |
if (total == 0) |
ifaddraddr = 0; |
continue; |
continue; |
|
} |
} |
} |
|
|
|
printf("%-7s %-5ld ", name, ifnet.if_mtu); |
printf("%-7s %-5ld ", name, ifd->ifi_mtu); |
if (ifaddraddr == 0) { |
print_addr(rti_info[RTAX_IFP], rti_info, ifd); |
printf("%-11.11s ", "none"); |
break; |
printf("%-17.17s ", "none"); |
case RTM_NEWADDR: |
} else { |
if (qflag && total == 0) |
if (kread(ifaddraddr, &ifaddr, sizeof ifaddr)) { |
|
ifaddraddr = 0; |
|
continue; |
continue; |
} |
ifam = (struct ifa_msghdr *)next; |
#define CP(x) ((char *)(x)) |
if ((ifam->ifam_addrs & (RTA_NETMASK | RTA_IFA | |
cp = (CP(ifaddr.ifa.ifa_addr) - CP(ifaddraddr)) + |
RTA_BRD)) == 0) |
CP(&ifaddr); sa = (struct sockaddr *)cp; |
|
switch (sa->sa_family) { |
|
case AF_UNSPEC: |
|
printf("%-11.11s ", "none"); |
|
printf("%-17.17s ", "none"); |
|
break; |
break; |
case AF_INET: |
|
sin = (struct sockaddr_in *)sa; |
|
#ifdef notdef |
|
/* can't use inet_makeaddr because kernel |
|
* keeps nets unshifted. |
|
*/ |
|
in = inet_makeaddr(ifaddr.in.ia_subnet, |
|
INADDR_ANY); |
|
cp = netname4(in.s_addr, |
|
ifaddr.in.ia_subnetmask); |
|
#else |
|
cp = netname4(ifaddr.in.ia_subnet, |
|
ifaddr.in.ia_subnetmask); |
|
#endif |
|
if (vflag) |
|
n = strlen(cp) < 11 ? 11 : strlen(cp); |
|
else |
|
n = 11; |
|
printf("%-*.*s ", n, n, cp); |
|
cp = routename4(sin->sin_addr.s_addr); |
|
if (vflag) |
|
n = strlen(cp) < 17 ? 17 : strlen(cp); |
|
else |
|
n = 17; |
|
printf("%-*.*s ", n, n, cp); |
|
|
|
if (aflag) { |
sa = (struct sockaddr *)(next + rtm->rtm_hdrlen); |
u_long multiaddr; |
get_rtaddrs(ifam->ifam_addrs, sa, rti_info); |
struct in_multi inm; |
|
|
|
multiaddr = (u_long)LIST_FIRST(&ifaddr.in.ia_multiaddrs); |
printf("%-7s %-5ld ", name, ifd->ifi_mtu); |
while (multiaddr != 0) { |
print_addr(rti_info[RTAX_IFA], rti_info, ifd); |
kread(multiaddr, &inm, sizeof inm); |
break; |
printf("\n%25s %-17.17s ", "", |
} |
routename4(inm.inm_addr.s_addr)); |
} |
multiaddr = (u_long)LIST_NEXT(&inm, inm_list); |
} |
} |
|
} |
static void |
break; |
print_addr(struct sockaddr *sa, struct sockaddr **rtinfo, struct if_data *ifd) |
case AF_INET6: |
{ |
sin6 = (struct sockaddr_in6 *)sa; |
struct sockaddr_dl *sdl; |
|
struct sockaddr_in *sin; |
|
struct sockaddr_in6 *sin6; |
|
char *cp; |
|
int m, n; |
|
|
|
switch (sa->sa_family) { |
|
case AF_UNSPEC: |
|
printf("%-11.11s ", "none"); |
|
printf("%-17.17s ", "none"); |
|
break; |
|
case AF_INET: |
|
sin = (struct sockaddr_in *)sa; |
|
cp = netname4(sin->sin_addr.s_addr, |
|
((struct sockaddr_in *)rtinfo[RTAX_NETMASK])->sin_addr.s_addr); |
|
if (vflag) |
|
n = strlen(cp) < 11 ? 11 : strlen(cp); |
|
else |
|
n = 11; |
|
printf("%-*.*s ", n, n, cp); |
|
cp = routename4(sin->sin_addr.s_addr); |
|
if (vflag) |
|
n = strlen(cp) < 17 ? 17 : strlen(cp); |
|
else |
|
n = 17; |
|
printf("%-*.*s ", n, n, cp); |
|
|
|
#if 0 |
|
if (aflag) { |
|
u_long multiaddr; |
|
struct in_multi inm; |
|
|
|
multiaddr = (u_long)LIST_FIRST(&ifaddr.in.ia_multiaddrs); |
|
while (multiaddr != 0) { |
|
kread(multiaddr, &inm, sizeof inm); |
|
printf("\n%25s %-17.17s ", "", |
|
routename4(inm.inm_addr.s_addr)); |
|
multiaddr = (u_long)LIST_NEXT(&inm, inm_list); |
|
} |
|
} |
|
#endif |
|
break; |
|
case AF_INET6: |
|
sin6 = (struct sockaddr_in6 *)sa; |
#ifdef __KAME__ |
#ifdef __KAME__ |
if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { |
if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { |
sin6->sin6_scope_id = |
sin6->sin6_scope_id = |
|
ntohs(*(u_int16_t *) |
|
&sin6->sin6_addr.s6_addr[2]); |
|
sin6->sin6_addr.s6_addr[2] = 0; |
|
sin6->sin6_addr.s6_addr[3] = 0; |
|
} |
|
#endif |
|
cp = netname6(sin6, |
|
(struct sockaddr_in6 *)rtinfo[RTAX_NETMASK]); |
|
if (vflag) |
|
n = strlen(cp) < 11 ? 11 : strlen(cp); |
|
else |
|
n = 11; |
|
printf("%-*.*s ", n, n, cp); |
|
cp = routename6(sin6); |
|
if (vflag) |
|
n = strlen(cp) < 17 ? 17 : strlen(cp); |
|
else |
|
n = 17; |
|
printf("%-*.*s ", n, n, cp); |
|
#if 0 |
|
if (aflag) { |
|
u_long multiaddr; |
|
struct in6_multi inm; |
|
struct sockaddr_in6 m6; |
|
|
|
multiaddr = (u_long)LIST_FIRST(&ifaddr.in6.ia6_multiaddrs); |
|
while (multiaddr != 0) { |
|
kread(multiaddr, &inm, sizeof inm); |
|
memset(&m6, 0, sizeof(m6)); |
|
m6.sin6_len = sizeof(struct sockaddr_in6); |
|
m6.sin6_family = AF_INET6; |
|
m6.sin6_addr = inm.in6m_addr; |
|
#ifdef __KAME__ |
|
if (IN6_IS_ADDR_MC_LINKLOCAL(&m6.sin6_addr) || |
|
IN6_IS_ADDR_MC_INTFACELOCAL(&m6.sin6_addr)) { |
|
m6.sin6_scope_id = |
ntohs(*(u_int16_t *) |
ntohs(*(u_int16_t *) |
&sin6->sin6_addr.s6_addr[2]); |
&m6.sin6_addr.s6_addr[2]); |
sin6->sin6_addr.s6_addr[2] = 0; |
m6.sin6_addr.s6_addr[2] = 0; |
sin6->sin6_addr.s6_addr[3] = 0; |
m6.sin6_addr.s6_addr[3] = 0; |
} |
} |
#endif |
#endif |
cp = netname6(&ifaddr.in6.ia_addr, |
cp = routename6(&m6); |
&ifaddr.in6.ia_prefixmask); |
|
if (vflag) |
if (vflag) |
n = strlen(cp) < 11 ? 11 : strlen(cp); |
|
else |
|
n = 11; |
|
printf("%-*.*s ", n, n, cp); |
|
cp = routename6(sin6); |
|
if (vflag) |
|
n = strlen(cp) < 17 ? 17 : strlen(cp); |
n = strlen(cp) < 17 ? 17 : strlen(cp); |
else |
else |
n = 17; |
n = 17; |
printf("%-*.*s ", n, n, cp); |
printf("\n%25s %-*.*s ", "", |
if (aflag) { |
n, n, cp); |
u_long multiaddr; |
multiaddr = (u_long)LIST_NEXT(&inm, in6m_entry); |
struct in6_multi inm; |
|
struct sockaddr_in6 m6; |
|
|
|
multiaddr = (u_long)LIST_FIRST(&ifaddr.in6.ia6_multiaddrs); |
|
while (multiaddr != 0) { |
|
kread(multiaddr, &inm, sizeof inm); |
|
memset(&m6, 0, sizeof(m6)); |
|
m6.sin6_len = sizeof(struct sockaddr_in6); |
|
m6.sin6_family = AF_INET6; |
|
m6.sin6_addr = inm.in6m_addr; |
|
#ifdef __KAME__ |
|
if (IN6_IS_ADDR_MC_LINKLOCAL(&m6.sin6_addr) || |
|
IN6_IS_ADDR_MC_INTFACELOCAL(&m6.sin6_addr)) { |
|
m6.sin6_scope_id = |
|
ntohs(*(u_int16_t *) |
|
&m6.sin6_addr.s6_addr[2]); |
|
m6.sin6_addr.s6_addr[2] = 0; |
|
m6.sin6_addr.s6_addr[3] = 0; |
|
} |
|
#endif |
|
cp = routename6(&m6); |
|
if (vflag) |
|
n = strlen(cp) < 17 ? 17 : strlen(cp); |
|
else |
|
n = 17; |
|
printf("\n%25s %-*.*s ", "", |
|
n, n, cp); |
|
multiaddr = (u_long)LIST_NEXT(&inm, in6m_entry); |
|
} |
|
} |
|
break; |
|
case AF_APPLETALK: |
|
printf("atlk:%-12s",atalk_print(sa,0x10) ); |
|
printf("%-12s ",atalk_print(sa,0x0b) ); |
|
break; |
|
case AF_LINK: |
|
{ |
|
struct sockaddr_dl *sdl = |
|
(struct sockaddr_dl *)sa; |
|
m = printf("%-11.11s ", "<Link>"); |
|
if (sdl->sdl_type == IFT_ETHER || |
|
sdl->sdl_type == IFT_CARP || |
|
sdl->sdl_type == IFT_FDDI || |
|
sdl->sdl_type == IFT_ISO88025) |
|
printf("%-17.17s ", |
|
ether_ntoa((struct ether_addr *)LLADDR(sdl))); |
|
else { |
|
cp = (char *)LLADDR(sdl); |
|
n = sdl->sdl_alen; |
|
goto hexprint; |
|
} |
|
} |
|
break; |
|
default: |
|
m = printf("(%d)", sa->sa_family); |
|
for (cp = sa->sa_len + (char *)sa; |
|
--cp > sa->sa_data && (*cp == 0);) {} |
|
n = cp - sa->sa_data + 1; |
|
cp = sa->sa_data; |
|
hexprint: |
|
while (--n >= 0) |
|
m += printf("%x%c", *cp++ & 0xff, |
|
n > 0 ? '.' : ' '); |
|
m = 30 - m; |
|
while (m-- > 0) |
|
putchar(' '); |
|
break; |
|
} |
} |
ifaddraddr = (u_long)TAILQ_NEXT(&ifaddr.ifa, ifa_list); |
|
} |
} |
if (bflag) |
#endif |
printf("%10llu %10llu", |
break; |
ifnet.if_ibytes, ifnet.if_obytes); |
case AF_APPLETALK: |
else |
printf("atlk:%-12s",atalk_print(sa,0x10) ); |
printf("%8llu %5llu %8llu %5llu %5llu", |
printf("%-12s ",atalk_print(sa,0x0b) ); |
ifnet.if_ipackets, ifnet.if_ierrors, |
break; |
ifnet.if_opackets, ifnet.if_oerrors, |
case AF_LINK: |
ifnet.if_collisions); |
sdl = (struct sockaddr_dl *)sa; |
if (tflag) |
m = printf("%-11.11s ", "<Link>"); |
printf(" %4d", ifnet.if_timer); |
if (sdl->sdl_type == IFT_ETHER || |
if (dflag) |
sdl->sdl_type == IFT_CARP || |
printf(" %4d", ifnet.if_snd.ifq_drops); |
sdl->sdl_type == IFT_FDDI || |
putchar('\n'); |
sdl->sdl_type == IFT_ISO88025) |
|
printf("%-17.17s ", |
|
ether_ntoa((struct ether_addr *)LLADDR(sdl))); |
|
else { |
|
cp = (char *)LLADDR(sdl); |
|
n = sdl->sdl_alen; |
|
goto hexprint; |
|
} |
|
break; |
|
default: |
|
m = printf("(%d)", sa->sa_family); |
|
for (cp = sa->sa_len + (char *)sa; |
|
--cp > sa->sa_data && (*cp == 0);) {} |
|
n = cp - sa->sa_data + 1; |
|
cp = sa->sa_data; |
|
hexprint: |
|
while (--n >= 0) |
|
m += printf("%x%c", *cp++ & 0xff, |
|
n > 0 ? '.' : ' '); |
|
m = 30 - m; |
|
while (m-- > 0) |
|
putchar(' '); |
|
break; |
} |
} |
|
if (bflag) |
|
printf("%10llu %10llu", |
|
ifd->ifi_ibytes, ifd->ifi_obytes); |
|
else |
|
printf("%8llu %5llu %8llu %5llu %5llu", |
|
ifd->ifi_ipackets, ifd->ifi_ierrors, |
|
ifd->ifi_opackets, ifd->ifi_oerrors, |
|
ifd->ifi_collisions); |
|
if (tflag) |
|
printf(" %4d", 0 /* XXX ifnet.if_timer */); |
|
if (dflag) |
|
printf(" %4d", 0 /* XXX ifnet.if_snd.ifq_drops */); |
|
putchar('\n'); |
} |
} |
|
|
#define MAXIF 100 |
|
struct iftot { |
struct iftot { |
char ift_name[IFNAMSIZ]; /* interface name */ |
char ift_name[IFNAMSIZ]; /* interface name */ |
u_int64_t ift_ip; /* input packets */ |
u_int64_t ift_ip; /* input packets */ |
|
|
u_int64_t ift_oe; /* output errors */ |
u_int64_t ift_oe; /* output errors */ |
u_int64_t ift_co; /* collisions */ |
u_int64_t ift_co; /* collisions */ |
u_int64_t ift_dr; /* drops */ |
u_int64_t ift_dr; /* drops */ |
} iftot[MAXIF]; |
} ip_cur, ip_old, sum_cur, sum_old; |
|
|
volatile sig_atomic_t signalled; /* set if alarm goes off "early" */ |
volatile sig_atomic_t signalled; /* set if alarm goes off "early" */ |
|
|
|
|
* First line printed at top of screen is always cumulative. |
* First line printed at top of screen is always cumulative. |
*/ |
*/ |
static void |
static void |
sidewaysintpr(unsigned int interval, u_long off) |
sidewaysintpr(unsigned int interval) |
{ |
{ |
struct ifnet ifnet; |
struct ifnet ifnet; |
u_long firstifnet; |
|
struct iftot *ip, *total; |
|
int line; |
|
struct iftot *lastif, *sum, *interesting; |
|
struct ifnet_head ifhead; /* TAILQ_HEAD */ |
|
sigset_t emptyset; |
sigset_t emptyset; |
|
int line; |
|
|
/* |
fetchifs(); |
* Find the pointer to the first ifnet structure. Replace |
if (ip_cur.ift_name[0] == '\0') { |
* the pointer to the TAILQ_HEAD with the actual pointer |
|
* to the first list element. |
|
*/ |
|
if (kread(off, &ifhead, sizeof ifhead)) |
|
return; |
|
firstifnet = (u_long)TAILQ_FIRST(&ifhead); |
|
|
|
lastif = iftot; |
|
sum = iftot + MAXIF - 1; |
|
total = sum - 1; |
|
interesting = (interface == NULL) ? iftot : NULL; |
|
for (off = firstifnet, ip = iftot; off;) { |
|
if (kread(off, &ifnet, sizeof ifnet)) |
|
break; |
|
bzero(ip->ift_name, sizeof(ip->ift_name)); |
|
snprintf(ip->ift_name, IFNAMSIZ, "%s", ifnet.if_xname); |
|
if (interface && strcmp(ifnet.if_xname, interface) == 0) |
|
interesting = ip; |
|
ip++; |
|
if (ip >= iftot + MAXIF - 2) |
|
break; |
|
off = (u_long)TAILQ_NEXT(&ifnet, if_list); |
|
} |
|
if (interesting == NULL) { |
|
fprintf(stderr, "%s: %s: unknown interface\n", |
fprintf(stderr, "%s: %s: unknown interface\n", |
__progname, interface); |
__progname, interface); |
exit(1); |
exit(1); |
} |
} |
lastif = ip; |
|
|
|
(void)signal(SIGALRM, catchalarm); |
(void)signal(SIGALRM, catchalarm); |
signalled = NO; |
signalled = 0; |
(void)alarm(interval); |
(void)alarm(interval); |
banner: |
banner: |
if (bflag) |
if (bflag) |
printf("%7.7s in %8.8s %6.6s out %5.5s", |
printf("%7.7s in %8.8s %6.6s out %5.5s", |
interesting->ift_name, " ", |
ip_cur.ift_name, " ", |
interesting->ift_name, " "); |
ip_cur.ift_name, " "); |
else |
else |
printf("%5.5s in %5.5s%5.5s out %5.5s %5.5s", |
printf("%5.5s in %5.5s%5.5s out %5.5s %5.5s", |
interesting->ift_name, " ", |
ip_cur.ift_name, " ", |
interesting->ift_name, " ", " "); |
ip_cur.ift_name, " ", " "); |
if (dflag) |
if (dflag) |
printf(" %5.5s", " "); |
printf(" %5.5s", " "); |
if (lastif - iftot > 0) { |
|
if (bflag) |
if (bflag) |
printf(" %7.7s in %8.8s %6.6s out %5.5s", |
printf(" %7.7s in %8.8s %6.6s out %5.5s", |
"total", " ", "total", " "); |
"total", " ", "total", " "); |
else |
else |
printf(" %5.5s in %5.5s%5.5s out %5.5s %5.5s", |
printf(" %5.5s in %5.5s%5.5s out %5.5s %5.5s", |
"total", " ", "total", " ", " "); |
"total", " ", "total", " ", " "); |
if (dflag) |
if (dflag) |
printf(" %5.5s", " "); |
printf(" %5.5s", " "); |
} |
|
for (ip = iftot; ip < iftot + MAXIF; ip++) { |
|
ip->ift_ip = 0; |
|
ip->ift_ib = 0; |
|
ip->ift_ie = 0; |
|
ip->ift_op = 0; |
|
ip->ift_ob = 0; |
|
ip->ift_oe = 0; |
|
ip->ift_co = 0; |
|
ip->ift_dr = 0; |
|
} |
|
putchar('\n'); |
putchar('\n'); |
if (bflag) |
if (bflag) |
printf("%10.10s %8.8s %10.10s %5.5s", |
printf("%10.10s %8.8s %10.10s %5.5s", |
|
|
"packets", "errs", "packets", "errs", "colls"); |
"packets", "errs", "packets", "errs", "colls"); |
if (dflag) |
if (dflag) |
printf(" %5.5s", "drops"); |
printf(" %5.5s", "drops"); |
if (lastif - iftot > 0) { |
|
if (bflag) |
if (bflag) |
printf(" %10.10s %8.8s %10.10s %5.5s", |
printf(" %10.10s %8.8s %10.10s %5.5s", |
"bytes", " ", "bytes", " "); |
"bytes", " ", "bytes", " "); |
else |
else |
printf(" %8.8s %5.5s %8.8s %5.5s %5.5s", |
printf(" %8.8s %5.5s %8.8s %5.5s %5.5s", |
"packets", "errs", "packets", "errs", "colls"); |
"packets", "errs", "packets", "errs", "colls"); |
if (dflag) |
if (dflag) |
printf(" %5.5s", "drops"); |
printf(" %5.5s", "drops"); |
} |
|
putchar('\n'); |
putchar('\n'); |
fflush(stdout); |
fflush(stdout); |
line = 0; |
line = 0; |
|
bzero(&ip_old, sizeof(ip_old)); |
|
bzero(&sum_old, sizeof(sum_old)); |
loop: |
loop: |
sum->ift_ip = 0; |
bzero(&sum_cur, sizeof(sum_cur)); |
sum->ift_ib = 0; |
|
sum->ift_ie = 0; |
fetchifs(); |
sum->ift_op = 0; |
|
sum->ift_ob = 0; |
if (bflag) |
sum->ift_oe = 0; |
printf("%10llu %8.8s %10llu %5.5s", |
sum->ift_co = 0; |
ip_cur.ift_ib - ip_old.ift_ib, " ", |
sum->ift_dr = 0; |
ip_cur.ift_ob - ip_old.ift_ob, " "); |
for (off = firstifnet, ip = iftot; off && ip < lastif; ip++) { |
else |
if (kread(off, &ifnet, sizeof ifnet)) { |
printf("%8llu %5llu %8llu %5llu %5llu", |
off = 0; |
ip_cur.ift_ip - ip_old.ift_ip, |
continue; |
ip_cur.ift_ie - ip_old.ift_ie, |
} |
ip_cur.ift_op - ip_old.ift_op, |
if (ip == interesting) { |
ip_cur.ift_oe - ip_old.ift_oe, |
if (bflag) |
ip_cur.ift_co - ip_old.ift_co); |
printf("%10llu %8.8s %10llu %5.5s", |
if (dflag) |
ifnet.if_ibytes - ip->ift_ib, " ", |
printf(" %5llu", |
ifnet.if_obytes - ip->ift_ob, " "); |
/* XXX ifnet.if_snd.ifq_drops - ip->ift_dr); */ |
else |
0); |
printf("%8llu %5llu %8llu %5llu %5llu", |
|
ifnet.if_ipackets - ip->ift_ip, |
ip_old = ip_cur; |
ifnet.if_ierrors - ip->ift_ie, |
|
ifnet.if_opackets - ip->ift_op, |
if (bflag) |
ifnet.if_oerrors - ip->ift_oe, |
printf(" %10llu %8.8s %10llu %5.5s", |
ifnet.if_collisions - ip->ift_co); |
sum_cur.ift_ib - sum_old.ift_ib, " ", |
if (dflag) |
sum_cur.ift_ob - sum_old.ift_ob, " "); |
printf(" %5llu", |
else |
ifnet.if_snd.ifq_drops - ip->ift_dr); |
printf(" %8llu %5llu %8llu %5llu %5llu", |
} |
sum_cur.ift_ip - sum_old.ift_ip, |
ip->ift_ip = ifnet.if_ipackets; |
sum_cur.ift_ie - sum_old.ift_ie, |
ip->ift_ib = ifnet.if_ibytes; |
sum_cur.ift_op - sum_old.ift_op, |
ip->ift_ie = ifnet.if_ierrors; |
sum_cur.ift_oe - sum_old.ift_oe, |
ip->ift_op = ifnet.if_opackets; |
sum_cur.ift_co - sum_old.ift_co); |
ip->ift_ob = ifnet.if_obytes; |
if (dflag) |
ip->ift_oe = ifnet.if_oerrors; |
printf(" %5llu", sum_cur.ift_dr - sum_old.ift_dr); |
ip->ift_co = ifnet.if_collisions; |
|
ip->ift_dr = ifnet.if_snd.ifq_drops; |
sum_old = sum_cur; |
sum->ift_ip += ip->ift_ip; |
|
sum->ift_ib += ip->ift_ib; |
|
sum->ift_ie += ip->ift_ie; |
|
sum->ift_op += ip->ift_op; |
|
sum->ift_ob += ip->ift_ob; |
|
sum->ift_oe += ip->ift_oe; |
|
sum->ift_co += ip->ift_co; |
|
sum->ift_dr += ip->ift_dr; |
|
off = (u_long)TAILQ_NEXT(&ifnet, if_list); |
|
} |
|
if (lastif - iftot > 0) { |
|
if (bflag) |
|
printf(" %10llu %8.8s %10llu %5.5s", |
|
sum->ift_ib - total->ift_ib, " ", |
|
sum->ift_ob - total->ift_ob, " "); |
|
else |
|
printf(" %8llu %5llu %8llu %5llu %5llu", |
|
sum->ift_ip - total->ift_ip, |
|
sum->ift_ie - total->ift_ie, |
|
sum->ift_op - total->ift_op, |
|
sum->ift_oe - total->ift_oe, |
|
sum->ift_co - total->ift_co); |
|
if (dflag) |
|
printf(" %5llu", sum->ift_dr - total->ift_dr); |
|
} |
|
*total = *sum; |
|
putchar('\n'); |
putchar('\n'); |
fflush(stdout); |
fflush(stdout); |
line++; |
line++; |
sigemptyset(&emptyset); |
sigemptyset(&emptyset); |
if (!signalled) |
if (!signalled) |
sigsuspend(&emptyset); |
sigsuspend(&emptyset); |
signalled = NO; |
signalled = 0; |
(void)alarm(interval); |
(void)alarm(interval); |
if (line == 21) |
if (line == 21) |
goto banner; |
goto banner; |
|
|
static void |
static void |
catchalarm(int signo) |
catchalarm(int signo) |
{ |
{ |
signalled = YES; |
signalled = 1; |
|
} |
|
|
|
static void |
|
get_rtaddrs(int addrs, struct sockaddr *sa, struct sockaddr **rti_info) |
|
{ |
|
int i; |
|
|
|
for (i = 0; i < RTAX_MAX; i++) { |
|
if (addrs & (1 << i)) { |
|
rti_info[i] = sa; |
|
sa = (struct sockaddr *)((char *)(sa) + |
|
roundup(sa->sa_len, sizeof(long))); |
|
} else |
|
rti_info[i] = NULL; |
|
} |
|
} |
|
|
|
static void |
|
fetchifs(void) |
|
{ |
|
struct if_msghdr ifm; |
|
int mib[6] = { CTL_NET, AF_ROUTE, 0, 0, NET_RT_IFLIST, 0 }; |
|
struct rt_msghdr *rtm; |
|
struct if_data *ifd; |
|
struct sockaddr *sa, *rti_info[RTAX_MAX]; |
|
struct sockaddr_dl *sdl; |
|
char *buf, *next, *lim; |
|
char name[IFNAMSIZ]; |
|
size_t len; |
|
|
|
if (sysctl(mib, 6, NULL, &len, NULL, 0) == -1) |
|
err(1, "sysctl"); |
|
if ((buf = malloc(len)) == NULL) |
|
err(1, NULL); |
|
if (sysctl(mib, 6, buf, &len, NULL, 0) == -1) |
|
err(1, "sysctl"); |
|
|
|
lim = buf + len; |
|
for (next = buf; next < lim; next += rtm->rtm_msglen) { |
|
rtm = (struct rt_msghdr *)next; |
|
if (rtm->rtm_version != RTM_VERSION) |
|
continue; |
|
switch (rtm->rtm_type) { |
|
case RTM_IFINFO: |
|
bcopy(next, &ifm, sizeof ifm); |
|
ifd = &ifm.ifm_data; |
|
|
|
sa = (struct sockaddr *)(next + rtm->rtm_hdrlen); |
|
get_rtaddrs(ifm.ifm_addrs, sa, rti_info); |
|
|
|
sdl = (struct sockaddr_dl *)rti_info[RTAX_IFP]; |
|
if (sdl == NULL || sdl->sdl_family != AF_LINK) |
|
continue; |
|
bzero(name, sizeof(name)); |
|
if (sdl->sdl_nlen >= IFNAMSIZ) |
|
memcpy(name, sdl->sdl_data, IFNAMSIZ - 1); |
|
else if (sdl->sdl_nlen > 0) |
|
memcpy(name, sdl->sdl_data, sdl->sdl_nlen); |
|
|
|
if (interface != 0 && !strcmp(name, interface)) { |
|
strlcpy(ip_cur.ift_name, name, |
|
sizeof(ip_cur.ift_name)); |
|
ip_cur.ift_ip = ifd->ifi_ipackets; |
|
ip_cur.ift_ib = ifd->ifi_ibytes; |
|
ip_cur.ift_ie = ifd->ifi_ierrors; |
|
ip_cur.ift_op = ifd->ifi_opackets; |
|
ip_cur.ift_ob = ifd->ifi_obytes; |
|
ip_cur.ift_oe = ifd->ifi_oerrors; |
|
ip_cur.ift_co = ifd->ifi_collisions; |
|
ip_cur.ift_dr = 0; |
|
/* XXX ifnet.if_snd.ifq_drops */ |
|
} |
|
|
|
sum_cur.ift_ip += ifd->ifi_ipackets; |
|
sum_cur.ift_ib += ifd->ifi_ibytes; |
|
sum_cur.ift_ie += ifd->ifi_ierrors; |
|
sum_cur.ift_op += ifd->ifi_opackets; |
|
sum_cur.ift_ob += ifd->ifi_obytes; |
|
sum_cur.ift_oe += ifd->ifi_oerrors; |
|
sum_cur.ift_co += ifd->ifi_collisions; |
|
sum_cur.ift_dr += 0; /* XXX ifnet.if_snd.ifq_drops */ |
|
break; |
|
} |
|
} |
|
if (interface == NULL) { |
|
strlcpy(ip_cur.ift_name, name, |
|
sizeof(ip_cur.ift_name)); |
|
ip_cur.ift_ip = ifd->ifi_ipackets; |
|
ip_cur.ift_ib = ifd->ifi_ibytes; |
|
ip_cur.ift_ie = ifd->ifi_ierrors; |
|
ip_cur.ift_op = ifd->ifi_opackets; |
|
ip_cur.ift_ob = ifd->ifi_obytes; |
|
ip_cur.ift_oe = ifd->ifi_oerrors; |
|
ip_cur.ift_co = ifd->ifi_collisions; |
|
ip_cur.ift_dr = 0; |
|
/* XXX ifnet.if_snd.ifq_drops */ |
|
} |
} |
} |