diff options
Diffstat (limited to 'sbin/route/route.c')
-rw-r--r-- | sbin/route/route.c | 784 |
1 files changed, 390 insertions, 394 deletions
diff --git a/sbin/route/route.c b/sbin/route/route.c index 48f90a7..e575c71 100644 --- a/sbin/route/route.c +++ b/sbin/route/route.c @@ -70,7 +70,7 @@ __FBSDID("$FreeBSD$"); #include <unistd.h> #include <ifaddrs.h> -struct keytab { +static struct keytab { const char *kt_cp; int kt_i; } keywords[] = { @@ -78,42 +78,33 @@ struct keytab { {0, 0} }; -union sockunion { - struct sockaddr sa; - struct sockaddr_in sin; -#ifdef INET6 - struct sockaddr_in6 sin6; -#endif - struct sockaddr_at sat; - struct sockaddr_dl sdl; - struct sockaddr_storage ss; /* added to avoid memory overrun */ -} so_dst, so_gate, so_mask, so_genmask, so_ifa, so_ifp; - -typedef union sockunion *sup; -int pid, rtm_addrs; -int s; -int forcehost, forcenet, doflush, nflag, af, qflag, tflag; -int verbose, aflen = sizeof (struct sockaddr_in); -int locking, lockrest, debugonly; -struct rt_metrics rt_metrics; -u_long rtm_inits; -uid_t uid; +static struct sockaddr_storage so[RTAX_MAX]; +static int pid, rtm_addrs; +static int s; +static int forcehost, forcenet, nflag, af, qflag, tflag; +static int verbose, aflen; +static int locking, lockrest, debugonly; +static struct rt_metrics rt_metrics; +static u_long rtm_inits; +static uid_t uid; static int defaultfib; static int numfibs; static int atalk_aton(const char *, struct at_addr *); static char *atalk_ntoa(struct at_addr); -static void bprintf(FILE *, int, u_char *); +static void printb(int, const char *); static void flushroutes(int argc, char *argv[]); static int flushroutes_fib(int); static int getaddr(int, char *, struct hostent **, int); static int keyword(const char *); -static void inet_makenetandmask(u_long, struct sockaddr_in *, u_long); +#ifdef INET +static void inet_makenetandmask(u_long, struct sockaddr_in *, + struct sockaddr_in *, u_long); +#endif #ifdef INET6 -static int inet6_makenetandmask(struct sockaddr_in6 *, const char *); +static int inet6_makenetandmask(struct sockaddr_in6 *, const char *); #endif static void interfaces(void); -static void mask_addr(void); static void monitor(int, char*[]); static const char *netname(struct sockaddr *); static void newroute(int, char **); @@ -127,10 +118,8 @@ static const char *routename(struct sockaddr *); static int rtmsg(int, int, int); static void set_metric(char *, int); static int set_sofib(int); -static int set_procfib(int); -static void sockaddr(char *, struct sockaddr *); -static void sodump(sup, const char *); -extern char *iso_ntoa(void); +static void sockaddr(char *, struct sockaddr *, size_t); +static void sodump(struct sockaddr *, const char *); struct fibl { TAILQ_ENTRY(fibl) fl_next; @@ -139,21 +128,19 @@ struct fibl { int fl_error; int fl_errno; }; -TAILQ_HEAD(fibl_head_t, fibl) fibl_head; +static TAILQ_HEAD(fibl_head_t, fibl) fibl_head; static int fiboptlist_csv(const char *, struct fibl_head_t *); static int fiboptlist_range(const char *, struct fibl_head_t *); static void usage(const char *) __dead2; -void +static void usage(const char *cp) { if (cp != NULL) warnx("bad keyword: %s", cp); - (void) fprintf(stderr, - "usage: route [-dnqtv] command [[modifiers] args]\n"); - exit(EX_USAGE); + errx(EX_USAGE, "usage: route [-dnqtv] command [[modifiers] args]"); /* NOTREACHED */ } @@ -247,15 +234,6 @@ set_sofib(int fib) } static int -set_procfib(int fib) -{ - - if (fib < 0) - return (0); - return (setfib(fib)); -} - -static int fiboptlist_range(const char *arg, struct fibl_head_t *flh) { struct fibl *fl; @@ -313,6 +291,7 @@ fiboptlist_csv(const char *arg, struct fibl_head_t *flh) char *str0, *str, *token, *endptr; int fib, error; + str0 = str = NULL; if (strcmp("all", arg) == 0) { str = calloc(1, ALLSTRLEN); if (str == NULL) { @@ -362,7 +341,8 @@ fiboptlist_csv(const char *arg, struct fibl_head_t *flh) } } fiboptlist_csv_ret: - free(str0); + if (str0 != NULL) + free(str0); return (error); } @@ -376,9 +356,8 @@ flushroutes(int argc, char *argv[]) struct fibl *fl; int error; - if (uid != 0 && !debugonly && !tflag) { + if (uid != 0 && !debugonly && !tflag) errx(EX_NOPERM, "must be root to alter routing table"); - } shutdown(s, SHUT_RD); /* Don't want to read back our messages */ TAILQ_INIT(&fibl_head); @@ -388,9 +367,11 @@ flushroutes(int argc, char *argv[]) if (**argv != '-') usage(*argv); switch (keyword(*argv + 1)) { +#ifdef INET case K_INET: af = AF_INET; break; +#endif #ifdef INET6 case K_INET6: af = AF_INET6; @@ -428,11 +409,10 @@ flushroutes_fib(int fib) struct rt_msghdr *rtm; size_t needed; char *buf, *next, *lim; - int mib[6], rlen, seqno, count = 0; + int mib[7], rlen, seqno, count = 0; int error; error = set_sofib(fib); - error += set_procfib(fib); if (error) { warn("fib number %d is ignored", fib); return (error); @@ -442,14 +422,15 @@ retry: mib[0] = CTL_NET; mib[1] = PF_ROUTE; mib[2] = 0; /* protocol */ - mib[3] = 0; /* wildcard address family */ + mib[3] = AF_UNSPEC; mib[4] = NET_RT_DUMP; mib[5] = 0; /* no flags */ - if (sysctl(mib, 6, NULL, &needed, NULL, 0) < 0) + mib[6] = fib; + if (sysctl(mib, nitems(mib), NULL, &needed, NULL, 0) < 0) err(EX_OSERR, "route-sysctl-estimate"); if ((buf = malloc(needed)) == NULL) errx(EX_OSERR, "malloc failed"); - if (sysctl(mib, 6, buf, &needed, NULL, 0) < 0) { + if (sysctl(mib, nitems(mib), buf, &needed, NULL, 0) < 0) { if (errno == ENOMEM && count++ < 10) { warnx("Routing table grew, retrying"); sleep(1); @@ -460,10 +441,10 @@ retry: } lim = buf + needed; if (verbose) - (void) printf("Examining routing table from sysctl\n"); + (void)printf("Examining routing table from sysctl\n"); seqno = 0; /* ??? */ for (next = buf; next < lim; next += rtm->rtm_msglen) { - rtm = (struct rt_msghdr *)next; + rtm = (struct rt_msghdr *)(void *)next; if (verbose) print_rtmsg(rtm, rtm->rtm_msglen); if ((rtm->rtm_flags & RTF_GATEWAY) == 0) @@ -483,7 +464,7 @@ retry: err(1, "write to routing socket"); if (rlen < (int)rtm->rtm_msglen) { warn("write to routing socket"); - (void) printf("got only %d for rlen\n", rlen); + (void)printf("got only %d for rlen\n", rlen); free(buf); goto retry; break; @@ -508,12 +489,12 @@ retry: return (error); } -const char * +static const char * routename(struct sockaddr *sa) { + struct sockaddr_dl *sdl; const char *cp; - static char line[MAXHOSTNAMELEN + 1]; - struct hostent *hp; + static char line[NI_MAXHOST]; static char domain[MAXHOSTNAMELEN + 1]; static int first = 1, n; @@ -522,73 +503,99 @@ routename(struct sockaddr *sa) if (gethostname(domain, MAXHOSTNAMELEN) == 0 && (cp = strchr(domain, '.'))) { domain[MAXHOSTNAMELEN] = '\0'; - (void) strcpy(domain, cp + 1); + (void)strcpy(domain, cp + 1); } else - domain[0] = 0; + domain[0] = '\0'; } - if (sa->sa_len == 0) - strcpy(line, "default"); - else switch (sa->sa_family) { - + /* If the address is zero-filled, use "default". */ + if (sa->sa_len == 0 && nflag == 0) + return ("default"); +#if defined(INET) || defined(INET6) + switch (sa->sa_family) { +#ifdef INET case AF_INET: - { struct in_addr in; - in = ((struct sockaddr_in *)sa)->sin_addr; - - cp = NULL; - if (in.s_addr == INADDR_ANY || sa->sa_len < 4) - cp = "default"; - if (cp == NULL && !nflag) { - hp = gethostbyaddr((char *)&in, sizeof (struct in_addr), - AF_INET); - if (hp != NULL) { - char *cptr; - cptr = strchr(hp->h_name, '.'); - if (cptr != NULL && - strcmp(cptr + 1, domain) == 0) - *cptr = '\0'; - cp = hp->h_name; - } - } - if (cp != NULL) { - strncpy(line, cp, sizeof(line) - 1); - line[sizeof(line) - 1] = '\0'; - } else - (void) sprintf(line, "%s", inet_ntoa(in)); + /* If the address is zero-filled, use "default". */ + if (nflag == 0 && + ((struct sockaddr_in *)(void *)sa)->sin_addr.s_addr == + INADDR_ANY) + return("default"); break; - } +#endif +#ifdef INET6 + case AF_INET6: + /* If the address is zero-filled, use "default". */ + if (nflag == 0 && + IN6_IS_ADDR_UNSPECIFIED(&((struct sockaddr_in6 *)(void *)sa)->sin6_addr)) + return("default"); + break; +#endif + } +#endif + switch (sa->sa_family) { +#if defined(INET) || defined(INET6) +#ifdef INET + case AF_INET: +#endif #ifdef INET6 case AF_INET6: +#endif { - struct sockaddr_in6 sin6; /* use static var for safety */ - int niflags = 0; + struct sockaddr_storage ss; + int error; + char *p; - memset(&sin6, 0, sizeof(sin6)); - memcpy(&sin6, sa, sa->sa_len); - sin6.sin6_len = sizeof(struct sockaddr_in6); - sin6.sin6_family = AF_INET6; - if (nflag) - niflags |= NI_NUMERICHOST; - if (getnameinfo((struct sockaddr *)&sin6, sin6.sin6_len, - line, sizeof(line), NULL, 0, niflags) != 0) + memset(&ss, 0, sizeof(ss)); + if (sa->sa_len == 0) + ss.ss_family = sa->sa_family; + else + memcpy(&ss, sa, sa->sa_len); + /* Expand sa->sa_len because it could be shortened. */ + if (sa->sa_family == AF_INET) + ss.ss_len = sizeof(struct sockaddr_in); + else if (sa->sa_family == AF_INET6) + ss.ss_len = sizeof(struct sockaddr_in6); + error = getnameinfo((struct sockaddr *)&ss, ss.ss_len, + line, sizeof(line), NULL, 0, + (nflag == 0) ? 0 : NI_NUMERICHOST); + if (error) { + warnx("getnameinfo(): %s", gai_strerror(error)); strncpy(line, "invalid", sizeof(line)); + } - return(line); + /* Remove the domain part if any. */ + p = strchr(line, '.'); + if (p != NULL && strcmp(p + 1, domain) == 0) + *p = '\0'; + + return (line); + break; } #endif - case AF_APPLETALK: - (void) snprintf(line, sizeof(line), "atalk %s", - atalk_ntoa(((struct sockaddr_at *)sa)->sat_addr)); + (void)snprintf(line, sizeof(line), "atalk %s", + atalk_ntoa(((struct sockaddr_at *)(void *)sa)->sat_addr)); break; case AF_LINK: - return (link_ntoa((struct sockaddr_dl *)sa)); + sdl = (struct sockaddr_dl *)(void *)sa; + + if (sdl->sdl_nlen == 0 && + sdl->sdl_alen == 0 && + sdl->sdl_slen == 0) { + n = snprintf(line, sizeof(line), "link#%d", + sdl->sdl_index); + if (n > (int)sizeof(line)) + line[0] = '\0'; + return (line); + } else + return (link_ntoa(sdl)); + break; default: { - u_short *sp = (u_short *)sa; + u_short *sp = (u_short *)(void *)sa; u_short *splim = sp + ((sa->sa_len + 1) >> 1); char *cps = line + sprintf(line, "(%d)", sa->sa_family); char *cpe = line + sizeof(line); @@ -608,21 +615,25 @@ routename(struct sockaddr *sa) * Return the name of the network whose address is given. * The address is assumed to be that of a net, not a host. */ -const char * +static const char * netname(struct sockaddr *sa) { - const char *cp = NULL; + struct sockaddr_dl *sdl; static char line[MAXHOSTNAMELEN + 1]; + int n; +#ifdef INET struct netent *np = NULL; + const char *cp = NULL; u_long i; - int n; +#endif switch (sa->sa_family) { - +#ifdef INET case AF_INET: - { struct in_addr in; - in = ((struct sockaddr_in *)sa)->sin_addr; + { + struct in_addr in; + in = ((struct sockaddr_in *)(void *)sa)->sin_addr; i = in.s_addr = ntohl(in.s_addr); if (in.s_addr == 0) cp = "default"; @@ -635,30 +646,30 @@ netname(struct sockaddr *sa) if (cp != NULL) strncpy(line, cp, sizeof(line)); else if ((in.s_addr & 0xffffff) == 0) - (void) sprintf(line, "%u", C(in.s_addr >> 24)); + (void)sprintf(line, "%u", C(in.s_addr >> 24)); else if ((in.s_addr & 0xffff) == 0) - (void) sprintf(line, "%u.%u", C(in.s_addr >> 24), + (void)sprintf(line, "%u.%u", C(in.s_addr >> 24), C(in.s_addr >> 16)); else if ((in.s_addr & 0xff) == 0) - (void) sprintf(line, "%u.%u.%u", C(in.s_addr >> 24), + (void)sprintf(line, "%u.%u.%u", C(in.s_addr >> 24), C(in.s_addr >> 16), C(in.s_addr >> 8)); else - (void) sprintf(line, "%u.%u.%u.%u", C(in.s_addr >> 24), + (void)sprintf(line, "%u.%u.%u.%u", C(in.s_addr >> 24), C(in.s_addr >> 16), C(in.s_addr >> 8), C(in.s_addr)); #undef C break; - } - + } +#endif #ifdef INET6 case AF_INET6: { - struct sockaddr_in6 sin6; /* use static var for safety */ + struct sockaddr_in6 sin6; int niflags = 0; memset(&sin6, 0, sizeof(sin6)); memcpy(&sin6, sa, sa->sa_len); - sin6.sin6_len = sizeof(struct sockaddr_in6); + sin6.sin6_len = sizeof(sin6); sin6.sin6_family = AF_INET6; if (nflag) niflags |= NI_NUMERICHOST; @@ -671,17 +682,28 @@ netname(struct sockaddr *sa) #endif case AF_APPLETALK: - (void) snprintf(line, sizeof(line), "atalk %s", - atalk_ntoa(((struct sockaddr_at *)sa)->sat_addr)); + (void)snprintf(line, sizeof(line), "atalk %s", + atalk_ntoa(((struct sockaddr_at *)(void *)sa)->sat_addr)); break; case AF_LINK: - return (link_ntoa((struct sockaddr_dl *)sa)); - + sdl = (struct sockaddr_dl *)(void *)sa; + + if (sdl->sdl_nlen == 0 && + sdl->sdl_alen == 0 && + sdl->sdl_slen == 0) { + n = snprintf(line, sizeof(line), "link#%d", + sdl->sdl_index); + if (n > (int)sizeof(line)) + line[0] = '\0'; + return (line); + } else + return (link_ntoa(sdl)); + break; default: { - u_short *sp = (u_short *)sa->sa_data; + u_short *sp = (u_short *)(void *)sa->sa_data; u_short *splim = sp + ((sa->sa_len + 1)>>1); char *cps = line + sprintf(line, "af %d:", sa->sa_family); char *cpe = line + sizeof(line); @@ -738,10 +760,8 @@ newroute(int argc, char **argv) const char *dest, *gateway, *errmsg; int key, error, flags, nrflags, fibnum; - if (uid != 0 && !debugonly && !tflag) { + if (uid != 0 && !debugonly && !tflag) errx(EX_NOPERM, "must be root to alter routing table"); - } - dest = NULL; gateway = NULL; flags = RTF_STATIC; @@ -752,7 +772,6 @@ newroute(int argc, char **argv) cmd = argv[0]; if (*cmd != 'g' && *cmd != 's') shutdown(s, SHUT_RD); /* Don't want to read back our messages */ - while (--argc > 0) { if (**(++argv)== '-') { switch (key = keyword(1 + *argv)) { @@ -760,10 +779,12 @@ newroute(int argc, char **argv) af = AF_LINK; aflen = sizeof(struct sockaddr_dl); break; +#ifdef INET case K_INET: af = AF_INET; aflen = sizeof(struct sockaddr_in); break; +#endif #ifdef INET6 case K_INET6: af = AF_INET6; @@ -776,7 +797,7 @@ newroute(int argc, char **argv) break; case K_SA: af = PF_ROUTE; - aflen = sizeof(union sockunion); + aflen = sizeof(struct sockaddr_storage); break; case K_IFACE: case K_INTERFACE: @@ -832,34 +853,35 @@ newroute(int argc, char **argv) case K_IFA: if (!--argc) usage(NULL); - getaddr(RTA_IFA, *++argv, 0, nrflags); + getaddr(RTAX_IFA, *++argv, 0, nrflags); break; case K_IFP: if (!--argc) usage(NULL); - getaddr(RTA_IFP, *++argv, 0, nrflags); + getaddr(RTAX_IFP, *++argv, 0, nrflags); break; case K_GENMASK: if (!--argc) usage(NULL); - getaddr(RTA_GENMASK, *++argv, 0, nrflags); + getaddr(RTAX_GENMASK, *++argv, 0, nrflags); break; case K_GATEWAY: if (!--argc) usage(NULL); - getaddr(RTA_GATEWAY, *++argv, 0, nrflags); + getaddr(RTAX_GATEWAY, *++argv, 0, nrflags); + gateway = *argv; break; case K_DST: if (!--argc) usage(NULL); - if (getaddr(RTA_DST, *++argv, &hp, nrflags)) + if (getaddr(RTAX_DST, *++argv, &hp, nrflags)) nrflags |= F_ISHOST; dest = *argv; break; case K_NETMASK: if (!--argc) usage(NULL); - getaddr(RTA_NETMASK, *++argv, 0, nrflags); + getaddr(RTAX_NETMASK, *++argv, 0, nrflags); /* FALLTHROUGH */ case K_NET: nrflags |= F_FORCENET; @@ -894,13 +916,13 @@ newroute(int argc, char **argv) } else { if ((rtm_addrs & RTA_DST) == 0) { dest = *argv; - if (getaddr(RTA_DST, *argv, &hp, nrflags)) + if (getaddr(RTAX_DST, *argv, &hp, nrflags)) nrflags |= F_ISHOST; } else if ((rtm_addrs & RTA_GATEWAY) == 0) { gateway = *argv; - getaddr(RTA_GATEWAY, *argv, &hp, nrflags); + getaddr(RTAX_GATEWAY, *argv, &hp, nrflags); } else { - getaddr(RTA_NETMASK, *argv, 0, nrflags); + getaddr(RTAX_NETMASK, *argv, 0, nrflags); nrflags |= F_FORCENET; } } @@ -911,7 +933,7 @@ newroute(int argc, char **argv) #ifdef INET6 if (af == AF_INET6) { rtm_addrs &= ~RTA_NETMASK; - memset((void *)&so_mask, 0, sizeof(so_mask)); + memset(&so[RTAX_NETMASK], 0, sizeof(so[RTAX_NETMASK])); } #endif } @@ -1034,11 +1056,12 @@ newroute_fib(int fib, char *cmd, int flags) return (error); } +#ifdef INET static void -inet_makenetandmask(u_long net, struct sockaddr_in *sin, u_long bits) +inet_makenetandmask(u_long net, struct sockaddr_in *sin, + struct sockaddr_in *sin_mask, u_long bits) { u_long mask = 0; - char *cp; rtm_addrs |= RTA_NETMASK; @@ -1055,7 +1078,8 @@ inet_makenetandmask(u_long net, struct sockaddr_in *sin, u_long bits) */ if ((bits == 0) && (net != 0)) { u_long i, j; - for(i=0,j=0xff; i<4; i++) { + + for(i = 0, j = 0xff; i < 4; i++) { if (net & j) { break; } @@ -1068,15 +1092,11 @@ inet_makenetandmask(u_long net, struct sockaddr_in *sin, u_long bits) mask = 0xffffffff << (32 - bits); sin->sin_addr.s_addr = htonl(net); - sin = &so_mask.sin; - sin->sin_addr.s_addr = htonl(mask); - sin->sin_len = 0; - sin->sin_family = 0; - cp = (char *)(&sin->sin_addr + 1); - while (*--cp == 0 && cp > (char *)sin) - ; - sin->sin_len = 1 + cp - (char *)sin; + sin_mask->sin_addr.s_addr = htonl(mask); + sin_mask->sin_len = sizeof(struct sockaddr_in); + sin_mask->sin_family = AF_INET; } +#endif #ifdef INET6 /* @@ -1113,33 +1133,50 @@ inet6_makenetandmask(struct sockaddr_in6 *sin6, const char *plen) * returning 1 if a host address, 0 if a network address. */ static int -getaddr(int which, char *str, struct hostent **hpp, int nrflags) +getaddr(int idx, char *str, struct hostent **hpp, int nrflags) { - sup su; + struct sockaddr *sa; +#if defined(INET) + struct sockaddr_in *sin; struct hostent *hp; struct netent *np; u_long val; char *q; - int afamily; /* local copy of af so we can change it */ +#elif defined(INET6) + char *q; +#endif + if (idx < 0 || idx >= RTAX_MAX) + usage("internal error"); if (af == 0) { +#if defined(INET) af = AF_INET; aflen = sizeof(struct sockaddr_in); +#elif defined(INET6) + af = AF_INET6; + aflen = sizeof(struct sockaddr_in6); +#else + af = AF_LINK; + aflen = sizeof(struct sockaddr_dl); +#endif } - afamily = af; - rtm_addrs |= which; - switch (which) { - case RTA_DST: - su = &so_dst; - break; - case RTA_GATEWAY: - su = &so_gate; +#ifndef INET + hpp = NULL; +#endif + rtm_addrs |= (1 << idx); + sa = (struct sockaddr *)&so[idx]; + sa->sa_family = af; + sa->sa_len = aflen; + + switch (idx) { + case RTAX_GATEWAY: if (nrflags & F_INTERFACE) { struct ifaddrs *ifap, *ifa; + struct sockaddr_dl *sdl0 = (struct sockaddr_dl *)(void *)sa; struct sockaddr_dl *sdl = NULL; if (getifaddrs(&ifap)) - err(1, "getifaddrs"); + err(EX_OSERR, "getifaddrs"); for (ifa = ifap; ifa != NULL; ifa = ifa->ifa_next) { if (ifa->ifa_addr->sa_family != AF_LINK) @@ -1148,63 +1185,38 @@ getaddr(int which, char *str, struct hostent **hpp, int nrflags) if (strcmp(str, ifa->ifa_name) != 0) continue; - sdl = (struct sockaddr_dl *)ifa->ifa_addr; + sdl = (struct sockaddr_dl *)(void *)ifa->ifa_addr; } /* If we found it, then use it */ if (sdl != NULL) { /* - * Copy is safe since we have a - * sockaddr_storage member in sockunion{}. * Note that we need to copy before calling * freeifaddrs(). */ - memcpy(&su->sdl, sdl, sdl->sdl_len); + memcpy(sdl0, sdl, sdl->sdl_len); } freeifaddrs(ifap); if (sdl != NULL) return(1); } break; - case RTA_NETMASK: - su = &so_mask; + case RTAX_IFP: + sa->sa_family = AF_LINK; break; - case RTA_GENMASK: - su = &so_genmask; - break; - case RTA_IFP: - su = &so_ifp; - afamily = AF_LINK; - break; - case RTA_IFA: - su = &so_ifa; - break; - default: - usage("internal error"); - /*NOTREACHED*/ } - su->sa.sa_len = aflen; - su->sa.sa_family = afamily; /* cases that don't want it have left already */ if (strcmp(str, "default") == 0) { /* * Default is net 0.0.0.0/0 */ - switch (which) { - case RTA_DST: + switch (idx) { + case RTAX_DST: forcenet++; -#if 0 - bzero(su, sizeof(*su)); /* for readability */ -#endif - getaddr(RTA_NETMASK, str, 0, nrflags); + getaddr(RTAX_NETMASK, str, 0, nrflags); break; -#if 0 - case RTA_NETMASK: - case RTA_GENMASK: - bzero(su, sizeof(*su)); /* for readability */ -#endif } return (0); } - switch (afamily) { + switch (sa->sa_family) { #ifdef INET6 case AF_INET6: { @@ -1212,89 +1224,93 @@ getaddr(int which, char *str, struct hostent **hpp, int nrflags) int ecode; q = NULL; - if (which == RTA_DST && (q = strchr(str, '/')) != NULL) + if (idx == RTAX_DST && (q = strchr(str, '/')) != NULL) *q = '\0'; memset(&hints, 0, sizeof(hints)); - hints.ai_family = afamily; /*AF_INET6*/ - hints.ai_socktype = SOCK_DGRAM; /*dummy*/ + hints.ai_family = sa->sa_family; + hints.ai_socktype = SOCK_DGRAM; ecode = getaddrinfo(str, NULL, &hints, &res); if (ecode != 0 || res->ai_family != AF_INET6 || - res->ai_addrlen != sizeof(su->sin6)) { - (void) fprintf(stderr, "%s: %s\n", str, - gai_strerror(ecode)); - exit(1); - } - memcpy(&su->sin6, res->ai_addr, sizeof(su->sin6)); + res->ai_addrlen != sizeof(struct sockaddr_in6)) + errx(EX_OSERR, "%s: %s", str, gai_strerror(ecode)); + memcpy(sa, res->ai_addr, res->ai_addrlen); freeaddrinfo(res); if (q != NULL) *q++ = '/'; - if (which == RTA_DST) - return (inet6_makenetandmask(&su->sin6, q)); + if (idx == RTAX_DST) + return (inet6_makenetandmask((struct sockaddr_in6 *)(void *)sa, q)); return (0); } #endif /* INET6 */ case AF_APPLETALK: - if (!atalk_aton(str, &su->sat.sat_addr)) + { + struct sockaddr_at *sat = (struct sockaddr_at *)(void *)sa; + + if (!atalk_aton(str, &sat->sat_addr)) errx(EX_NOHOST, "bad address: %s", str); rtm_addrs |= RTA_NETMASK; - return(forcehost || su->sat.sat_addr.s_node != 0); - + return(forcehost || sat->sat_addr.s_node != 0); + } case AF_LINK: - link_addr(str, &su->sdl); + link_addr(str, (struct sockaddr_dl *)(void *)sa); return (1); - case PF_ROUTE: - su->sa.sa_len = sizeof(*su); - sockaddr(str, &su->sa); + sockaddr(str, sa, sizeof(struct sockaddr_storage)); return (1); - +#ifdef INET case AF_INET: +#endif default: break; } +#ifdef INET + sin = (struct sockaddr_in *)(void *)sa; if (hpp == NULL) hpp = &hp; *hpp = NULL; q = strchr(str,'/'); - if (q != NULL && which == RTA_DST) { + if (q != NULL && idx == RTAX_DST) { *q = '\0'; if ((val = inet_network(str)) != INADDR_NONE) { - inet_makenetandmask( - val, &su->sin, strtoul(q+1, 0, 0)); + inet_makenetandmask(val, sin, + (struct sockaddr_in *)&so[RTAX_NETMASK], + strtoul(q+1, 0, 0)); return (0); } *q = '/'; } - if ((which != RTA_DST || forcenet == 0) && - inet_aton(str, &su->sin.sin_addr)) { - val = su->sin.sin_addr.s_addr; - if (which != RTA_DST || forcehost || - inet_lnaof(su->sin.sin_addr) != INADDR_ANY) + if ((idx != RTAX_DST || forcenet == 0) && + inet_aton(str, &sin->sin_addr)) { + val = sin->sin_addr.s_addr; + if (idx != RTAX_DST || forcehost || + inet_lnaof(sin->sin_addr) != INADDR_ANY) return (1); else { val = ntohl(val); goto netdone; } } - if (which == RTA_DST && forcehost == 0 && + if (idx == RTAX_DST && forcehost == 0 && ((val = inet_network(str)) != INADDR_NONE || ((np = getnetbyname(str)) != NULL && (val = np->n_net) != 0))) { netdone: - inet_makenetandmask(val, &su->sin, 0); + inet_makenetandmask(val, sin, + (struct sockaddr_in *)&so[RTAX_NETMASK], 0); return (0); } hp = gethostbyname(str); if (hp != NULL) { *hpp = hp; - su->sin.sin_family = hp->h_addrtype; - memmove((char *)&su->sin.sin_addr, hp->h_addr, - MIN((size_t)hp->h_length, sizeof(su->sin.sin_addr))); + sin->sin_family = hp->h_addrtype; + memmove((char *)&sin->sin_addr, hp->h_addr, + MIN((size_t)hp->h_length, sizeof(sin->sin_addr))); return (1); } +#endif errx(EX_NOHOST, "bad address: %s", str); } @@ -1309,28 +1325,39 @@ prefixlen(const char *str) switch (af) { #ifdef INET6 case AF_INET6: + { + struct sockaddr_in6 *sin6 = + (struct sockaddr_in6 *)&so[RTAX_NETMASK]; + max = 128; - p = (char *)&so_mask.sin6.sin6_addr; + p = (char *)&sin6->sin6_addr; + sin6->sin6_family = AF_INET6; + sin6->sin6_len = sizeof(*sin6); break; + } #endif +#ifdef INET case AF_INET: + { + struct sockaddr_in *sin = + (struct sockaddr_in *)&so[RTAX_NETMASK]; + max = 32; - p = (char *)&so_mask.sin.sin_addr; + p = (char *)&sin->sin_addr; + sin->sin_family = AF_INET; + sin->sin_len = sizeof(*sin); break; + } +#endif default: - fprintf(stderr, "prefixlen not supported in this af\n"); - exit(1); + errx(EX_OSERR, "prefixlen not supported in this af"); } - if (len < 0 || max < len) { - fprintf(stderr, "%s: bad value\n", str); - exit(1); - } + if (len < 0 || max < len) + errx(EX_USAGE, "%s: invalid prefixlen", str); q = len >> 3; r = len & 7; - so_mask.sa.sa_family = af; - so_mask.sa.sa_len = aflen; memset((void *)p, 0, max / 8); if (q > 0) memset((void *)p, 0xff, q); @@ -1354,14 +1381,14 @@ retry2: mib[0] = CTL_NET; mib[1] = PF_ROUTE; mib[2] = 0; /* protocol */ - mib[3] = 0; /* wildcard address family */ + mib[3] = AF_UNSPEC; mib[4] = NET_RT_IFLIST; mib[5] = 0; /* no flags */ - if (sysctl(mib, 6, NULL, &needed, NULL, 0) < 0) + if (sysctl(mib, nitems(mib), NULL, &needed, NULL, 0) < 0) err(EX_OSERR, "route-sysctl-estimate"); if ((buf = malloc(needed)) == NULL) errx(EX_OSERR, "malloc failed"); - if (sysctl(mib, 6, buf, &needed, NULL, 0) < 0) { + if (sysctl(mib, nitems(mib), buf, &needed, NULL, 0) < 0) { if (errno == ENOMEM && count++ < 10) { warnx("Routing table grew, retrying"); sleep(1); @@ -1372,7 +1399,7 @@ retry2: } lim = buf + needed; for (next = buf; next < lim; next += rtm->rtm_msglen) { - rtm = (struct rt_msghdr *)next; + rtm = (struct rt_msghdr *)(void *)next; print_rtmsg(rtm, rtm->rtm_msglen); } } @@ -1421,12 +1448,12 @@ monitor(int argc, char *argv[]) time_t now; n = read(s, msg, 2048); now = time(NULL); - (void) printf("\ngot message of size %d on %s", n, ctime(&now)); - print_rtmsg((struct rt_msghdr *)msg, n); + (void)printf("\ngot message of size %d on %s", n, ctime(&now)); + print_rtmsg((struct rt_msghdr *)(void *)msg, n); } } -struct { +static struct { struct rt_msghdr m_rtm; char m_space[512]; } m_rtmsg; @@ -1439,10 +1466,16 @@ rtmsg(int cmd, int flags, int fib) char *cp = m_rtmsg.m_space; int l; -#define NEXTADDR(w, u) \ - if (rtm_addrs & (w)) {\ - l = SA_SIZE(&(u.sa)); memmove(cp, &(u), l); cp += l;\ - if (verbose) sodump(&(u),#u);\ +#define NEXTADDR(w, u) \ + if (rtm_addrs & (w)) { \ + l = (((struct sockaddr *)&(u))->sa_len == 0) ? \ + sizeof(long) : \ + 1 + ((((struct sockaddr *)&(u))->sa_len - 1) \ + | (sizeof(long) - 1)); \ + memmove(cp, (char *)&(u), l); \ + cp += l; \ + if (verbose) \ + sodump((struct sockaddr *)&(u), #w); \ } errno = 0; @@ -1453,9 +1486,9 @@ rtmsg(int cmd, int flags, int fib) cmd = RTM_CHANGE; else if (cmd == 'g' || cmd == 's') { cmd = RTM_GET; - if (so_ifp.sa.sa_family == 0) { - so_ifp.sa.sa_family = AF_LINK; - so_ifp.sa.sa_len = sizeof(struct sockaddr_dl); + if (so[RTAX_IFP].ss_family == 0) { + so[RTAX_IFP].ss_family = AF_LINK; + so[RTAX_IFP].ss_len = sizeof(struct sockaddr_dl); rtm_addrs |= RTA_IFP; } } else @@ -1469,14 +1502,12 @@ rtmsg(int cmd, int flags, int fib) rtm.rtm_rmx = rt_metrics; rtm.rtm_inits = rtm_inits; - if (rtm_addrs & RTA_NETMASK) - mask_addr(); - NEXTADDR(RTA_DST, so_dst); - NEXTADDR(RTA_GATEWAY, so_gate); - NEXTADDR(RTA_NETMASK, so_mask); - NEXTADDR(RTA_GENMASK, so_genmask); - NEXTADDR(RTA_IFP, so_ifp); - NEXTADDR(RTA_IFA, so_ifa); + NEXTADDR(RTA_DST, so[RTAX_DST]); + NEXTADDR(RTA_GATEWAY, so[RTAX_GATEWAY]); + NEXTADDR(RTA_NETMASK, so[RTAX_NETMASK]); + NEXTADDR(RTA_GENMASK, so[RTAX_GENMASK]); + NEXTADDR(RTA_IFP, so[RTAX_IFP]); + NEXTADDR(RTA_IFA, so[RTAX_IFA]); rtm.rtm_msglen = l = cp - (char *)&m_rtmsg; if (verbose) print_rtmsg(&rtm, l); @@ -1501,38 +1532,7 @@ rtmsg(int cmd, int flags, int fib) return (0); } -static void -mask_addr(void) -{ - int olen = so_mask.sa.sa_len; - char *cp1 = olen + (char *)&so_mask, *cp2; - - for (so_mask.sa.sa_len = 0; cp1 > (char *)&so_mask; ) - if (*--cp1 != 0) { - so_mask.sa.sa_len = 1 + cp1 - (char *)&so_mask; - break; - } - if ((rtm_addrs & RTA_DST) == 0) - return; - switch (so_dst.sa.sa_family) { - case AF_INET: -#ifdef INET6 - case AF_INET6: -#endif - case AF_APPLETALK: - case 0: - return; - } - cp1 = so_mask.sa.sa_len + 1 + (char *)&so_dst; - cp2 = so_dst.sa.sa_len + 1 + (char *)&so_dst; - while (cp2 > cp1) - *--cp2 = 0; - cp2 = so_mask.sa.sa_len + 1 + (char *)&so_mask; - while (cp1 > so_dst.sa.sa_data) - *--cp1 &= *--cp2; -} - -const char *msgtypes[] = { +static const char *msgtypes[] = { "", "RTM_ADD: Add Route", "RTM_DELETE: Delete Route", @@ -1554,23 +1554,23 @@ const char *msgtypes[] = { "RTM_IEEE80211: IEEE 802.11 wireless event", }; -char metricnames[] = -"\011weight\010rttvar\7rtt\6ssthresh\5sendpipe\4recvpipe\3expire" -"\1mtu"; -char routeflags[] = -"\1UP\2GATEWAY\3HOST\4REJECT\5DYNAMIC\6MODIFIED\7DONE" -"\012XRESOLVE\013LLINFO\014STATIC\015BLACKHOLE" -"\017PROTO2\020PROTO1\021PRCLONING\022WASCLONED\023PROTO3" -"\025PINNED\026LOCAL\027BROADCAST\030MULTICAST\035STICKY"; -char ifnetflags[] = -"\1UP\2BROADCAST\3DEBUG\4LOOPBACK\5PTP\6b6\7RUNNING\010NOARP" -"\011PPROMISC\012ALLMULTI\013OACTIVE\014SIMPLEX\015LINK0\016LINK1" -"\017LINK2\020MULTICAST"; -char addrnames[] = -"\1DST\2GATEWAY\3NETMASK\4GENMASK\5IFP\6IFA\7AUTHOR\010BRD"; +static const char metricnames[] = + "\011weight\010rttvar\7rtt\6ssthresh\5sendpipe\4recvpipe\3expire" + "\1mtu"; +static const char routeflags[] = + "\1UP\2GATEWAY\3HOST\4REJECT\5DYNAMIC\6MODIFIED\7DONE" + "\012XRESOLVE\013LLINFO\014STATIC\015BLACKHOLE" + "\017PROTO2\020PROTO1\021PRCLONING\022WASCLONED\023PROTO3" + "\025PINNED\026LOCAL\027BROADCAST\030MULTICAST\035STICKY"; +static const char ifnetflags[] = + "\1UP\2BROADCAST\3DEBUG\4LOOPBACK\5PTP\6b6\7RUNNING\010NOARP" + "\011PPROMISC\012ALLMULTI\013OACTIVE\014SIMPLEX\015LINK0\016LINK1" + "\017LINK2\020MULTICAST"; +static const char addrnames[] = + "\1DST\2GATEWAY\3NETMASK\4GENMASK\5IFP\6IFA\7AUTHOR\010BRD"; static const char errfmt[] = -"\n%s: truncated route message, only %zu bytes left\n"; + "\n%s: truncated route message, only %zu bytes left\n"; static void print_rtmsg(struct rt_msghdr *rtm, size_t msglen) @@ -1586,11 +1586,11 @@ print_rtmsg(struct rt_msghdr *rtm, size_t msglen) if (verbose == 0) return; if (rtm->rtm_version != RTM_VERSION) { - (void) printf("routing message version %d not understood\n", + (void)printf("routing message version %d not understood\n", rtm->rtm_version); return; } - if (rtm->rtm_type < sizeof(msgtypes) / sizeof(msgtypes[0])) + if (rtm->rtm_type < nitems(msgtypes)) (void)printf("%s: ", msgtypes[rtm->rtm_type]); else (void)printf("unknown type %d: ", rtm->rtm_type); @@ -1607,7 +1607,7 @@ print_rtmsg(struct rt_msghdr *rtm, size_t msglen) case RTM_IFINFO: REQUIRE(struct if_msghdr); ifm = (struct if_msghdr *)rtm; - (void) printf("if# %d, ", ifm->ifm_index); + (void)printf("if# %d, ", ifm->ifm_index); switch (ifm->ifm_data.ifi_link_state) { case LINK_STATE_DOWN: state = "down"; @@ -1619,16 +1619,16 @@ print_rtmsg(struct rt_msghdr *rtm, size_t msglen) state = "unknown"; break; } - (void) printf("link: %s, flags:", state); - bprintf(stdout, ifm->ifm_flags, ifnetflags); + (void)printf("link: %s, flags:", state); + printb(ifm->ifm_flags, ifnetflags); pmsg_addrs((char *)(ifm + 1), ifm->ifm_addrs, msglen); break; case RTM_NEWADDR: case RTM_DELADDR: REQUIRE(struct ifa_msghdr); ifam = (struct ifa_msghdr *)rtm; - (void) printf("metric %d, flags:", ifam->ifam_metric); - bprintf(stdout, ifam->ifam_flags, routeflags); + (void)printf("metric %d, flags:", ifam->ifam_metric); + printb(ifam->ifam_flags, routeflags); pmsg_addrs((char *)(ifam + 1), ifam->ifam_addrs, msglen); break; #ifdef RTM_NEWMADDR @@ -1642,10 +1642,10 @@ print_rtmsg(struct rt_msghdr *rtm, size_t msglen) case RTM_IFANNOUNCE: REQUIRE(struct if_announcemsghdr); ifan = (struct if_announcemsghdr *)rtm; - (void) printf("if# %d, what: ", ifan->ifan_index); + (void)printf("if# %d, what: ", ifan->ifan_index); switch (ifan->ifan_what) { case IFAN_ARRIVAL: - printf("arrival"); + (void)printf("arrival"); break; case IFAN_DEPARTURE: printf("departure"); @@ -1659,9 +1659,9 @@ print_rtmsg(struct rt_msghdr *rtm, size_t msglen) break; default: - (void) printf("pid: %ld, seq %d, errno %d, flags:", + printf("pid: %ld, seq %d, errno %d, flags:", (long)rtm->rtm_pid, rtm->rtm_seq, rtm->rtm_errno); - bprintf(stdout, rtm->rtm_flags, routeflags); + printb(rtm->rtm_flags, routeflags); pmsg_common(rtm, msglen); } @@ -1675,14 +1675,13 @@ badlen: static void print_getmsg(struct rt_msghdr *rtm, int msglen, int fib) { - struct sockaddr *dst = NULL, *gate = NULL, *mask = NULL; - struct sockaddr_dl *ifp = NULL; - struct sockaddr *sa; + struct sockaddr *sp[RTAX_MAX]; char *cp; int i; - (void) printf(" route to: %s\n", - routename((struct sockaddr *)&so_dst)); + memset(sp, 0, sizeof(sp)); + (void)printf(" route to: %s\n", + routename((struct sockaddr *)&so[RTAX_DST])); if (rtm->rtm_version != RTM_VERSION) { warnx("routing message version %d not understood", rtm->rtm_version); @@ -1691,6 +1690,7 @@ print_getmsg(struct rt_msghdr *rtm, int msglen, int fib) if (rtm->rtm_msglen > msglen) { warnx("message length mismatch, in packet %d, returned %d", rtm->rtm_msglen, msglen); + return; } if (rtm->rtm_errno) { errno = rtm->rtm_errno; @@ -1698,54 +1698,36 @@ print_getmsg(struct rt_msghdr *rtm, int msglen, int fib) return; } cp = ((char *)(rtm + 1)); - if (rtm->rtm_addrs) - for (i = 1; i; i <<= 1) - if (i & rtm->rtm_addrs) { - sa = (struct sockaddr *)cp; - switch (i) { - case RTA_DST: - dst = sa; - break; - case RTA_GATEWAY: - gate = sa; - break; - case RTA_NETMASK: - mask = sa; - break; - case RTA_IFP: - if (sa->sa_family == AF_LINK && - ((struct sockaddr_dl *)sa)->sdl_nlen) - ifp = (struct sockaddr_dl *)sa; - break; - } - cp += SA_SIZE(sa); - } - if (dst && mask) - mask->sa_family = dst->sa_family; /* XXX */ - if (dst) - (void)printf("destination: %s\n", routename(dst)); - if (mask) { - int savenflag = nflag; - - nflag = 1; - (void)printf(" mask: %s\n", routename(mask)); - nflag = savenflag; - } - if (gate && rtm->rtm_flags & RTF_GATEWAY) - (void)printf(" gateway: %s\n", routename(gate)); + for (i = 0; i < RTAX_MAX; i++) + if (rtm->rtm_addrs & (1 << i)) { + sp[i] = (struct sockaddr *)cp; + cp += SA_SIZE((struct sockaddr *)cp); + } + if ((rtm->rtm_addrs & RTA_IFP) && + (sp[RTAX_IFP]->sa_family != AF_LINK || + ((struct sockaddr_dl *)(void *)sp[RTAX_IFP])->sdl_nlen == 0)) + sp[RTAX_IFP] = NULL; + if (sp[RTAX_DST] && sp[RTAX_NETMASK]) + sp[RTAX_NETMASK]->sa_family = sp[RTAX_DST]->sa_family; /* XXX */ + if (sp[RTAX_DST]) + (void)printf("destination: %s\n", routename(sp[RTAX_DST])); + if (sp[RTAX_NETMASK]) + (void)printf(" mask: %s\n", routename(sp[RTAX_NETMASK])); + if (sp[RTAX_GATEWAY] && (rtm->rtm_flags & RTF_GATEWAY)) + (void)printf(" gateway: %s\n", routename(sp[RTAX_GATEWAY])); if (fib >= 0) (void)printf(" fib: %u\n", (unsigned int)fib); - if (ifp) + if (sp[RTAX_IFP]) (void)printf(" interface: %.*s\n", - ifp->sdl_nlen, ifp->sdl_data); + ((struct sockaddr_dl *)(void *)sp[RTAX_IFP])->sdl_nlen, + ((struct sockaddr_dl *)(void *)sp[RTAX_IFP])->sdl_data); (void)printf(" flags: "); - bprintf(stdout, rtm->rtm_flags, routeflags); + printb(rtm->rtm_flags, routeflags); #define lock(f) ((rtm->rtm_rmx.rmx_locks & __CONCAT(RTV_,f)) ? 'L' : ' ') #define msec(u) (((u) + 500) / 1000) /* usec to msec */ - - (void) printf("\n%s\n", "\ - recvpipe sendpipe ssthresh rtt,msec mtu weight expire"); + printf("\n%9s %9s %9s %9s %9s %10s %9s\n", "recvpipe", + "sendpipe", "ssthresh", "rtt,msec", "mtu ", "weight", "expire"); printf("%8ld%c ", rtm->rtm_rmx.rmx_recvpipe, lock(RPIPE)); printf("%8ld%c ", rtm->rtm_rmx.rmx_sendpipe, lock(SPIPE)); printf("%8ld%c ", rtm->rtm_rmx.rmx_ssthresh, lock(SSTHRESH)); @@ -1761,8 +1743,8 @@ print_getmsg(struct rt_msghdr *rtm, int msglen, int fib) if (verbose) pmsg_common(rtm, msglen); else if (rtm->rtm_addrs &~ RTA_IGN) { - (void) printf("sockaddrs: "); - bprintf(stdout, rtm->rtm_addrs, addrnames); + (void)printf("sockaddrs: "); + printb(rtm->rtm_addrs, addrnames); putchar('\n'); } #undef RTA_IGN @@ -1771,15 +1753,16 @@ print_getmsg(struct rt_msghdr *rtm, int msglen, int fib) static void pmsg_common(struct rt_msghdr *rtm, size_t msglen) { - (void) printf("\nlocks: "); - bprintf(stdout, rtm->rtm_rmx.rmx_locks, metricnames); - (void) printf(" inits: "); - bprintf(stdout, rtm->rtm_inits, metricnames); + + (void)printf("\nlocks: "); + printb(rtm->rtm_rmx.rmx_locks, metricnames); + (void)printf(" inits: "); + printb(rtm->rtm_inits, metricnames); if (msglen > sizeof(struct rt_msghdr)) pmsg_addrs(((char *)(rtm + 1)), rtm->rtm_addrs, msglen - sizeof(struct rt_msghdr)); else - (void) fflush(stdout); + (void)fflush(stdout); } static void @@ -1789,29 +1772,29 @@ pmsg_addrs(char *cp, int addrs, size_t len) int i; if (addrs == 0) { - (void) putchar('\n'); + (void)putchar('\n'); return; } - (void) printf("\nsockaddrs: "); - bprintf(stdout, addrs, addrnames); - (void) putchar('\n'); - for (i = 1; i != 0; i <<= 1) - if (i & addrs) { + (void)printf("\nsockaddrs: "); + printb(addrs, addrnames); + putchar('\n'); + for (i = 0; i < RTAX_MAX; i++) + if (addrs & (1 << i)) { sa = (struct sockaddr *)cp; if (len == 0 || len < SA_SIZE(sa)) { - (void) printf(errfmt, __func__, len); + (void)printf(errfmt, __func__, len); break; } - (void) printf(" %s", routename(sa)); + (void)printf(" %s", routename(sa)); len -= SA_SIZE(sa); cp += SA_SIZE(sa); } - (void) putchar('\n'); - (void) fflush(stdout); + (void)putchar('\n'); + (void)fflush(stdout); } static void -bprintf(FILE *fp, int b, u_char *str) +printb(int b, const char *str) { int i; int gotsome = 0; @@ -1824,16 +1807,16 @@ bprintf(FILE *fp, int b, u_char *str) i = '<'; else i = ','; - (void) putc(i, fp); + putchar(i); gotsome = 1; for (; (i = *str) > 32; str++) - (void) putc(i, fp); + putchar(i); } else while (*str > 32) str++; } if (gotsome) - (void) putc('>', fp); + putchar('>'); } int @@ -1847,23 +1830,36 @@ keyword(const char *cp) } static void -sodump(sup su, const char *which) +sodump(struct sockaddr *sa, const char *which) { - switch (su->sa.sa_family) { +#ifdef INET6 + char nbuf[INET6_ADDRSTRLEN]; +#endif + + switch (sa->sa_family) { case AF_LINK: - (void) printf("%s: link %s; ", - which, link_ntoa(&su->sdl)); + (void)printf("%s: link %s; ", which, + link_ntoa((struct sockaddr_dl *)(void *)sa)); break; +#ifdef INET case AF_INET: - (void) printf("%s: inet %s; ", - which, inet_ntoa(su->sin.sin_addr)); + (void)printf("%s: inet %s; ", which, + inet_ntoa(((struct sockaddr_in *)(void *)sa)->sin_addr)); break; +#endif +#ifdef INET6 + case AF_INET6: + (void)printf("%s: inet6 %s; ", which, inet_ntop(sa->sa_family, + &((struct sockaddr_in6 *)(void *)sa)->sin6_addr, nbuf, + sizeof(nbuf))); + break; +#endif case AF_APPLETALK: - (void) printf("%s: atalk %s; ", - which, atalk_ntoa(su->sat.sat_addr)); + (void)printf("%s: atalk %s; ", which, + atalk_ntoa(((struct sockaddr_at *)(void *)sa)->sat_addr)); break; } - (void) fflush(stdout); + (void)fflush(stdout); } /* States*/ @@ -1876,10 +1872,9 @@ sodump(sup su, const char *which) #define DELIM (4*2) static void -sockaddr(char *addr, struct sockaddr *sa) +sockaddr(char *addr, struct sockaddr *sa, size_t size) { char *cp = (char *)sa; - int size = sa->sa_len; char *cplim = cp + size; int byte = 0, state = VIRGIN, new = 0 /* foil gcc */; @@ -1935,6 +1930,7 @@ atalk_ntoa(struct at_addr at) { static char buf[20]; - (void) snprintf(buf, sizeof(buf), "%u.%u", ntohs(at.s_net), at.s_node); + (void)snprintf(buf, sizeof(buf), "%u.%u", ntohs(at.s_net), at.s_node); + buf[sizeof(buf) - 1] = '\0'; return(buf); } |