Date: Mon, 1 Nov 2004 22:36:21 GMT From: Sam Leffler <sam@FreeBSD.org> To: Perforce Change Reviews <perforce@freebsd.org> Subject: PERFORCE change 64066 for review Message-ID: <200411012236.iA1MaLWA065623@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://perforce.freebsd.org/chv.cgi?CH=64066 Change 64066 by sam@sam_ebb on 2004/11/01 22:35:57 checkpoint new ifconfig Affected files ... .. //depot/projects/wifi/sbin/ifconfig/Makefile#2 edit .. //depot/projects/wifi/sbin/ifconfig/af_atalk.c#1 add .. //depot/projects/wifi/sbin/ifconfig/af_inet.c#1 add .. //depot/projects/wifi/sbin/ifconfig/af_inet6.c#1 add .. //depot/projects/wifi/sbin/ifconfig/af_ipx.c#1 add .. //depot/projects/wifi/sbin/ifconfig/af_link.c#1 add .. //depot/projects/wifi/sbin/ifconfig/ifclone.c#1 add .. //depot/projects/wifi/sbin/ifconfig/ifconfig.c#2 edit .. //depot/projects/wifi/sbin/ifconfig/ifconfig.h#2 edit .. //depot/projects/wifi/sbin/ifconfig/ifieee80211.c#2 edit .. //depot/projects/wifi/sbin/ifconfig/ifmac.c#2 edit .. //depot/projects/wifi/sbin/ifconfig/ifmedia.c#2 edit .. //depot/projects/wifi/sbin/ifconfig/ifvlan.c#2 edit Differences ... ==== //depot/projects/wifi/sbin/ifconfig/Makefile#2 (text+ko) ==== @@ -2,35 +2,36 @@ # $FreeBSD: src/sbin/ifconfig/Makefile,v 1.25 2004/02/23 20:13:52 johan Exp $ PROG= ifconfig -SRCS= ifconfig.c -#comment out to exclude SIOC[GS]IFMEDIA support -SRCS+= ifmedia.c -CFLAGS+=-DUSE_IF_MEDIA -CFLAGS+=-DINET6 +SRCS= ifconfig.c # base support -#comment out to exclude SIOC[GS]ETVLAN support -SRCS+= ifvlan.c -CFLAGS+=-DUSE_VLANS +# +# NB: The order here defines the order in which the constructors +# are called. This in turn defines the default order in which +# status is displayed. Probably should add a priority mechanism +# to the registration process so we don't depend on this aspect +# of the toolchain. +# +SRCS+= af_link.c # LLC support +SRCS+= af_inet.c # IPv4 support +SRCS+= af_inet6.c # IPv6 support +SRCS+= af_atalk.c # AppleTalk support -#comment out to exclude SIOC[GS]IEEE80211 support -SRCS+= ifieee80211.c -CFLAGS+=-DUSE_IEEE80211 +SRCS+= ifclone.c # clone device support +SRCS+= ifmac.c # MAC support +SRCS+= ifmedia.c # SIOC[GS]IFMEDIA support +SRCS+= ifvlan.c # SIOC[GS]ETVLAN support +SRCS+= ifieee80211.c # SIOC[GS]IEEE80211 support -#comment out to exclude MAC support -SRCS+= ifmac.c -CFLAGS+=-DUSE_MAC - -MAN= ifconfig.8 - -.if defined(RELEASE_CRUNCH) -CFLAGS+=-DNO_IPX -.else +.if !defined(RELEASE_CRUNCH) +SRCS+= af_ipx.c # IPX support DPADD= ${LIBIPX} LDADD= -lipx .endif -CFLAGS+=-DNS -Wall -Wmissing-prototypes -Wcast-qual -Wwrite-strings \ +MAN= ifconfig.8 + +CFLAGS+= -g -Wall -Wmissing-prototypes -Wcast-qual -Wwrite-strings \ -Wnested-externs -I.. WARNS?= 0 ==== //depot/projects/wifi/sbin/ifconfig/ifconfig.c#2 (text+ko) ==== @@ -62,21 +62,6 @@ #include <arpa/inet.h> #include <netdb.h> -#ifdef INET6 -#include <netinet6/nd6.h> /* Define ND6_INFINITE_LIFETIME */ -#endif - -#ifndef NO_IPX -/* IPX */ -#define IPXIP -#define IPTUNNEL -#include <netipx/ipx.h> -#include <netipx/ipx_if.h> -#endif - -/* Appletalk */ -#include <netatalk/at.h> - #include <ctype.h> #include <err.h> #include <errno.h> @@ -85,34 +70,18 @@ #include <stdlib.h> #include <string.h> #include <unistd.h> -#include <ifaddrs.h> #include "ifconfig.h" -/* wrapper for KAME-special getnameinfo() */ -#ifndef NI_WITHSCOPEID -#define NI_WITHSCOPEID 0 -#endif - /* * Since "struct ifreq" is composed of various union members, callers * should pay special attention to interprete the value. * (.e.g. little/big endian difference in the structure.) */ -struct ifreq ifr, ridreq; -struct ifaliasreq addreq; -#ifdef INET6 -struct in6_ifreq in6_ridreq; -struct in6_aliasreq in6_addreq = - { { 0 }, - { 0 }, - { 0 }, - { 0 }, - 0, - { 0, 0, ND6_INFINITE_LIFETIME, ND6_INFINITE_LIFETIME } }; -#endif -struct sockaddr_in netmask; -struct netrange at_nr; /* AppleTalk net range */ +struct ifreq ifr; +struct ifreq ridreq; +struct ifaliasreq addreq; +struct sockaddr_in netmask; char name[IFNAMSIZ]; int flags; @@ -122,27 +91,13 @@ int doalias; int clearaddr; int newaddr = 1; -#ifdef INET6 -static int ip6lifetime; -#endif - -struct afswtch; +int verbose; int supmedia = 0; int listcloners = 0; int printname = 0; /* Print the name of the created interface. */ -#ifdef INET6 -char addr_buf[MAXHOSTNAMELEN *2 + 1]; /*for getnameinfo()*/ -#endif - -void Perror(const char *cmd); -void checkatrange(struct sockaddr_at *); int ifconfig(int argc, char *const *argv, const struct afswtch *afp); -void notealias(const char *, int, int, const struct afswtch *afp); -void list_cloners(void); -void printb(const char *s, unsigned value, const char *bits); -void rt_xaddrs(caddr_t, caddr_t, struct rt_addrinfo *); void status(const struct afswtch *afp, int addrcount, struct sockaddr_dl *sdl, struct if_msghdr *ifm, struct ifa_msghdr *ifam); @@ -150,252 +105,10 @@ void usage(void); void ifmaybeload(char *name); -#ifdef INET6 -void in6_fillscopeid(struct sockaddr_in6 *sin6); -int prefix(void *, int); -static char *sec2str(time_t); -int explicit_prefix = 0; -#endif +static struct afswtch *af_getbyname(const char *name); +static struct afswtch *af_getbyfamily(int af); +static void af_all_status(int, const struct rt_addrinfo *sdl); -typedef void c_func(const char *cmd, int arg, int s, const struct afswtch *afp); -typedef void c_func2(const char *arg, const char *arg2, int s, const struct afswtch *afp); -c_func setatphase, setatrange; -c_func setifaddr, setifbroadaddr, setifdstaddr, setifnetmask; -c_func2 settunnel; -c_func deletetunnel; -#ifdef INET6 -c_func setifprefixlen; -c_func setip6flags; -c_func setip6pltime; -c_func setip6vltime; -c_func2 setip6lifetime; -c_func setip6eui64; -#endif -c_func setifipdst; -c_func setifflags, setifmetric, setifmtu, setifcap; -c_func clone_destroy; -c_func setifname; - - -void clone_create(void); - - -#define NEXTARG 0xffffff -#define NEXTARG2 0xfffffe - -const -struct cmd { - const char *c_name; - int c_parameter; /* NEXTARG means next argv */ - void (*c_func)(const char *, int, int, const struct afswtch *afp); - void (*c_func2)(const char *, const char *, int, const struct afswtch *afp); -} cmds[] = { - { "up", IFF_UP, setifflags } , - { "down", -IFF_UP, setifflags }, - { "arp", -IFF_NOARP, setifflags }, - { "-arp", IFF_NOARP, setifflags }, - { "debug", IFF_DEBUG, setifflags }, - { "-debug", -IFF_DEBUG, setifflags }, - { "promisc", IFF_PPROMISC, setifflags }, - { "-promisc", -IFF_PPROMISC, setifflags }, - { "add", IFF_UP, notealias }, - { "alias", IFF_UP, notealias }, - { "-alias", -IFF_UP, notealias }, - { "delete", -IFF_UP, notealias }, - { "remove", -IFF_UP, notealias }, -#ifdef notdef -#define EN_SWABIPS 0x1000 - { "swabips", EN_SWABIPS, setifflags }, - { "-swabips", -EN_SWABIPS, setifflags }, -#endif - { "netmask", NEXTARG, setifnetmask }, -#ifdef INET6 - { "prefixlen", NEXTARG, setifprefixlen }, - { "anycast", IN6_IFF_ANYCAST, setip6flags }, - { "tentative", IN6_IFF_TENTATIVE, setip6flags }, - { "-tentative", -IN6_IFF_TENTATIVE, setip6flags }, - { "deprecated", IN6_IFF_DEPRECATED, setip6flags }, - { "-deprecated", -IN6_IFF_DEPRECATED, setip6flags }, - { "autoconf", IN6_IFF_AUTOCONF, setip6flags }, - { "-autoconf", -IN6_IFF_AUTOCONF, setip6flags }, - { "pltime", NEXTARG, setip6pltime }, - { "vltime", NEXTARG, setip6vltime }, - { "eui64", 0, setip6eui64 }, -#endif - { "range", NEXTARG, setatrange }, - { "phase", NEXTARG, setatphase }, - { "metric", NEXTARG, setifmetric }, - { "broadcast", NEXTARG, setifbroadaddr }, - { "ipdst", NEXTARG, setifipdst }, - { "tunnel", NEXTARG2, NULL, settunnel }, - { "deletetunnel", 0, deletetunnel }, - { "link0", IFF_LINK0, setifflags }, - { "-link0", -IFF_LINK0, setifflags }, - { "link1", IFF_LINK1, setifflags }, - { "-link1", -IFF_LINK1, setifflags }, - { "link2", IFF_LINK2, setifflags }, - { "-link2", -IFF_LINK2, setifflags }, - { "monitor", IFF_MONITOR, setifflags }, - { "-monitor", -IFF_MONITOR, setifflags }, - { "staticarp", IFF_STATICARP, setifflags }, - { "-staticarp", -IFF_STATICARP, setifflags }, -#ifdef USE_IF_MEDIA - { "media", NEXTARG, setmedia }, - { "mode", NEXTARG, setmediamode }, - { "mediaopt", NEXTARG, setmediaopt }, - { "-mediaopt", NEXTARG, unsetmediaopt }, -#endif -#ifdef USE_VLANS - { "vlan", NEXTARG, setvlantag }, - { "vlandev", NEXTARG, setvlandev }, - { "-vlandev", NEXTARG, unsetvlandev }, -#endif -#if 0 - /* XXX `create' special-cased below */ - {"create", 0, clone_create }, - {"plumb", 0, clone_create }, -#endif - {"destroy", 0, clone_destroy }, - {"unplumb", 0, clone_destroy }, -#ifdef USE_IEEE80211 - { "ssid", NEXTARG, set80211ssid }, - { "nwid", NEXTARG, set80211ssid }, - { "stationname", NEXTARG, set80211stationname }, - { "station", NEXTARG, set80211stationname }, /* BSD/OS */ - { "channel", NEXTARG, set80211channel }, - { "authmode", NEXTARG, set80211authmode }, - { "powersavemode", NEXTARG, set80211powersavemode }, - { "powersave", 1, set80211powersave }, - { "-powersave", 0, set80211powersave }, - { "powersavesleep", NEXTARG, set80211powersavesleep }, - { "wepmode", NEXTARG, set80211wepmode }, - { "wep", 1, set80211wep }, - { "-wep", 0, set80211wep }, - { "weptxkey", NEXTARG, set80211weptxkey }, - { "wepkey", NEXTARG, set80211wepkey }, - { "nwkey", NEXTARG, set80211nwkey }, /* NetBSD */ - { "-nwkey", 0, set80211wep }, /* NetBSD */ - { "rtsthreshold",NEXTARG, set80211rtsthreshold }, - { "protmode", NEXTARG, set80211protmode }, - { "txpower", NEXTARG, set80211txpower }, -#endif -#ifdef USE_MAC - { "maclabel", NEXTARG, setifmaclabel }, -#endif - { "rxcsum", IFCAP_RXCSUM, setifcap }, - { "-rxcsum", -IFCAP_RXCSUM, setifcap }, - { "txcsum", IFCAP_TXCSUM, setifcap }, - { "-txcsum", -IFCAP_TXCSUM, setifcap }, - { "netcons", IFCAP_NETCONS, setifcap }, - { "-netcons", -IFCAP_NETCONS, setifcap }, - { "polling", IFCAP_POLLING, setifcap }, - { "-polling", -IFCAP_POLLING, setifcap }, - { "vlanmtu", IFCAP_VLAN_MTU, setifcap }, - { "-vlanmtu", -IFCAP_VLAN_MTU, setifcap }, - { "vlanhwtag", IFCAP_VLAN_HWTAGGING, setifcap }, - { "-vlanhwtag", -IFCAP_VLAN_HWTAGGING, setifcap }, - { "normal", -IFF_LINK0, setifflags }, - { "compress", IFF_LINK0, setifflags }, - { "noicmp", IFF_LINK1, setifflags }, - { "mtu", NEXTARG, setifmtu }, - { "name", NEXTARG, setifname }, - { 0, 0, setifaddr }, - { 0, 0, setifdstaddr }, -}; - -/* - * XNS support liberally adapted from code written at the University of - * Maryland principally by James O'Toole and Chris Torek. - */ -typedef void af_status(int, struct rt_addrinfo *); -typedef void af_getaddr(const char *, int); -typedef void af_getprefix(const char *, int); - -af_status in_status, at_status, link_status; -af_getaddr in_getaddr, at_getaddr, link_getaddr; - -#ifndef NO_IPX -af_status ipx_status; -af_getaddr ipx_getaddr; -#endif - -#ifdef INET6 -af_status in6_status; -af_getaddr in6_getaddr; -af_getprefix in6_getprefix; -#endif /*INET6*/ - -/* Known address families */ -const -struct afswtch { - const char *af_name; - short af_af; - af_status *af_status; - af_getaddr *af_getaddr; - af_getprefix *af_getprefix; - u_long af_difaddr; - u_long af_aifaddr; - caddr_t af_ridreq; - caddr_t af_addreq; -} afs[] = { -#define C(x) ((caddr_t) &x) - { "inet", AF_INET, in_status, in_getaddr, NULL, - SIOCDIFADDR, SIOCAIFADDR, C(ridreq), C(addreq) }, -#ifdef INET6 - { "inet6", AF_INET6, in6_status, in6_getaddr, in6_getprefix, - SIOCDIFADDR_IN6, SIOCAIFADDR_IN6, - C(in6_ridreq), C(in6_addreq) }, -#endif /*INET6*/ -#ifndef NO_IPX - { "ipx", AF_IPX, ipx_status, ipx_getaddr, NULL, - SIOCDIFADDR, SIOCAIFADDR, C(ridreq), C(addreq) }, -#endif - { "atalk", AF_APPLETALK, at_status, at_getaddr, NULL, - SIOCDIFADDR, SIOCAIFADDR, C(addreq), C(addreq) }, - { "link", AF_LINK, link_status, link_getaddr, NULL, - 0, SIOCSIFLLADDR, NULL, C(ridreq) }, - { "ether", AF_LINK, link_status, link_getaddr, NULL, - 0, SIOCSIFLLADDR, NULL, C(ridreq) }, - { "lladdr", AF_LINK, link_status, link_getaddr, NULL, - 0, SIOCSIFLLADDR, NULL, C(ridreq) }, -#if 0 /* XXX conflicts with the media command */ -#ifdef USE_IF_MEDIA - { "media", AF_UNSPEC, media_status, NULL, NULL, }, /* XXX not real!! */ -#endif -#ifdef USE_VLANS - { "vlan", AF_UNSPEC, vlan_status, NULL, NULL, }, /* XXX not real!! */ -#endif -#ifdef USE_IEEE80211 - { "ieee80211", AF_UNSPEC, ieee80211_status, NULL, NULL, }, /* XXX not real!! */ -#endif -#ifdef USE_MAC - { "maclabel", AF_UNSPEC, maclabel_status, NULL, NULL, }, -#endif -#endif - { 0, 0, 0, 0 } -}; - -/* - * Expand the compacted form of addresses as returned via the - * configuration read via sysctl(). - */ - -void -rt_xaddrs(caddr_t cp, caddr_t cplim, struct rt_addrinfo *rtinfo) -{ - struct sockaddr *sa; - int i; - - memset(rtinfo->rti_info, 0, sizeof(rtinfo->rti_info)); - for (i = 0; (i < RTAX_MAX) && (cp < cplim); i++) { - if ((rtinfo->rti_addrs & (1 << i)) == 0) - continue; - rtinfo->rti_info[i] = sa = (struct sockaddr *)cp; - cp += SA_SIZE(sa); - } -} - - void usage(void) { @@ -437,8 +150,8 @@ int mib[6]; /* Parse leading line options */ - all = downonly = uponly = namesonly = 0; - while ((c = getopt(argc, argv, "adlmuC" + all = downonly = uponly = namesonly = verbose = 0; + while ((c = getopt(argc, argv, "adlmuvC" #ifdef INET6 "L" #endif @@ -467,6 +180,9 @@ ip6lifetime++; /* print IPv6 address lifetime */ break; #endif + case 'v': + verbose++; + break; default: usage(); break; @@ -504,13 +220,11 @@ ifindex = 0; if (argc == 1) { - for (afp = afs; afp->af_name; afp++) - if (strcmp(afp->af_name, *argv) == 0) { - argc--, argv++; - break; - } - if (afp->af_name == NULL) + afp = af_getbyname(*argv); + if (afp == NULL) usage(); + if (afp->af_name != NULL) + argc--, argv++; /* leave with afp non-zero */ } } else { @@ -543,13 +257,9 @@ /* Check for address family */ if (argc > 0) { - for (afp = afs; afp->af_name; afp++) - if (strcmp(afp->af_name, *argv) == 0) { - argc--, argv++; - break; - } - if (afp->af_name == NULL) - afp = NULL; /* not a family, NULL */ + afp = af_getbyname(*argv); + if (afp != NULL) + argc--, argv++; } retry: @@ -630,9 +340,8 @@ if (flags & IFF_UP) continue; /* not down */ if (namesonly) { - if (afp == NULL || - afp->af_status != link_status || - sdl->sdl_type == IFT_ETHER) { + if (afp == NULL || afp->af_af != AF_LINK || + sdl->sdl_type == IFT_ETHER) { if (need_nl) putchar(' '); fputs(name, stdout); @@ -658,69 +367,155 @@ exit (0); } +static struct afswtch *afs = NULL; + +void +af_register(struct afswtch *p) +{ + p->af_next = afs; + afs = p; +} + +static struct afswtch * +af_getbyname(const char *name) +{ + struct afswtch *afp; + + for (afp = afs; afp != NULL; afp = afp->af_next) + if (strcmp(afp->af_name, name) == 0) + return afp; + return NULL; +} + +static struct afswtch * +af_getbyfamily(int af) +{ + struct afswtch *afp; + + for (afp = afs; afp != NULL; afp = afp->af_next) + if (afp->af_af == af) + return afp; + return NULL; +} + +static void +af_all_status(int s, const struct rt_addrinfo *sdl) +{ + struct afswtch *afp; + uint8_t afmask[howmany(AF_MAX, NBBY)]; + + memset(afmask, 0, sizeof(afmask)); + for (afp = afs; afp != NULL; afp = afp->af_next) { + if (afp->af_status == NULL) + continue; + if (afp->af_af != AF_UNSPEC && isset(afmask, afp->af_af)) + continue; + afp->af_status(s, sdl); + setbit(afmask, afp->af_af); + } +} + +static void +af_all_tunnel_status(int s) +{ + struct afswtch *afp; + uint8_t afmask[howmany(AF_MAX, NBBY)]; + + memset(afmask, 0, sizeof(afmask)); + for (afp = afs; afp != NULL; afp = afp->af_next) { + if (afp->af_status_tunnel == NULL) + continue; + if (afp->af_af != AF_UNSPEC && isset(afmask, afp->af_af)) + continue; + afp->af_status_tunnel(s); + setbit(afmask, afp->af_af); + } +} + +static struct cmd *cmds = NULL; + +void +cmd_register(struct cmd *p) +{ + p->next = cmds; + cmds = p; +} + +static const struct cmd * +cmd_lookup(const char *name) +{ +#define N(a) (sizeof(a)/sizeof(a[0])) + const struct cmd *p; + + for (p = cmds; p != NULL; p = p->next) + if (strcmp(name, p->c_name) == 0) + return p; + return NULL; +#undef N +} + +/* specially-handled comamnds */ +static void setifaddr(const char *, int, int, const struct afswtch *); +static const struct cmd setifaddr_cmd = { "ifaddr", 0, setifaddr }; + +static void setifdstaddr(const char *, int, int, const struct afswtch *); +static const struct cmd setifdstaddr_cmd = { "ifdstaddr", 0, setifdstaddr }; + int ifconfig(int argc, char *const *argv, const struct afswtch *afp) { - int af, s; + int s; if (afp == NULL) - afp = &afs[0]; - af = afp->af_af == AF_LINK ? AF_INET : afp->af_af; - ifr.ifr_addr.sa_family = af; + afp = af_getbyname("inet"); + ifr.ifr_addr.sa_family = afp->af_af == AF_LINK ? AF_INET : afp->af_af; strncpy(ifr.ifr_name, name, sizeof ifr.ifr_name); - if ((s = socket(af, SOCK_DGRAM, 0)) < 0) + if ((s = socket(ifr.ifr_addr.sa_family, SOCK_DGRAM, 0)) < 0) err(1, "socket"); while (argc > 0) { const struct cmd *p; - for (p = cmds; p->c_name; p++) - if (strcmp(*argv, p->c_name) == 0) - break; - if (p->c_name == 0 && setaddr) - p++; /* got src, do dst */ + p = cmd_lookup(*argv); + if (p == NULL) { + /* + * Not a recognized command, choose between setting + * the interface address and the dst address. + */ + p = (setaddr ? &setifdstaddr_cmd : &setifaddr_cmd); + } if (p->c_func || p->c_func2) { if (p->c_parameter == NEXTARG) { if (argv[1] == NULL) errx(1, "'%s' requires argument", p->c_name); - (*p->c_func)(argv[1], 0, s, afp); + p->c_func(argv[1], 0, s, afp); argc--, argv++; + } else if (p->c_parameter == OPTARG) { + p->c_func(argv[1], 0, s, afp); + if (argv[1] != NULL) + argc--, argv++; } else if (p->c_parameter == NEXTARG2) { if (argc < 3) errx(1, "'%s' requires 2 arguments", p->c_name); - (*p->c_func2)(argv[1], argv[2], s, afp); + p->c_func2(argv[1], argv[2], s, afp); argc -= 2, argv += 2; } else - (*p->c_func)(*argv, p->c_parameter, s, afp); + p->c_func(*argv, p->c_parameter, s, afp); } argc--, argv++; } -#ifdef INET6 - if (af == AF_INET6 && explicit_prefix == 0) { - /* Aggregatable address architecture defines all prefixes - are 64. So, it is convenient to set prefixlen to 64 if - it is not specified. */ - setifprefixlen("64", 0, s, afp); - /* in6_getprefix("64", MASK) if MASK is available here... */ - } -#endif -#ifndef NO_IPX - if (setipdst && af == AF_IPX) { - struct ipxip_req rq; - int size = sizeof(rq); - rq.rq_ipx = addreq.ifra_addr; - rq.rq_ip = addreq.ifra_dstaddr; - - if (setsockopt(s, 0, SO_IPXIP_ROUTE, &rq, size) < 0) - Perror("Encapsulation Routing"); - } -#endif - if (af == AF_APPLETALK) - checkatrange((struct sockaddr_at *) &addreq.ifra_addr); + /* + * Do any post argument processing required by the address family. + */ + if (afp->af_postproc != NULL) + afp->af_postproc(s, afp); + /* + * Do deferred operations. + */ if (clearaddr) { if (afp->af_ridreq == NULL || afp->af_difaddr == 0) { warnx("interface %s cannot change %s addresses!", @@ -731,7 +526,8 @@ if (clearaddr) { int ret; strncpy(afp->af_ridreq, name, sizeof ifr.ifr_name); - if ((ret = ioctl(s, afp->af_difaddr, afp->af_ridreq)) < 0) { + ret = ioctl(s, afp->af_difaddr, afp->af_ridreq); + if (ret < 0) { if (errno == EADDRNOTAVAIL && (doalias >= 0)) { /* means no previous address for interface */ } else @@ -753,16 +549,12 @@ close(s); return(0); } -#define RIDADDR 0 -#define ADDR 1 -#define MASK 2 -#define DSTADDR 3 /*ARGSUSED*/ -void +static void setifaddr(const char *addr, int param, int s, const struct afswtch *afp) { - if (*afp->af_getaddr == NULL) + if (afp->af_getaddr == NULL) return; /* * Delay the ioctl to set the interface addr until flags are all set. @@ -772,21 +564,20 @@ setaddr++; if (doalias == 0 && afp->af_af != AF_LINK) clearaddr = 1; - (*afp->af_getaddr)(addr, (doalias >= 0 ? ADDR : RIDADDR)); + afp->af_getaddr(addr, (doalias >= 0 ? ADDR : RIDADDR)); } -void +static void settunnel(const char *src, const char *dst, int s, const struct afswtch *afp) { - struct addrinfo hints, *srcres, *dstres; - struct ifaliasreq addreq; + struct addrinfo *srcres, *dstres; int ecode; -#ifdef INET6 - struct in6_aliasreq in6_addreq; -#endif - memset(&hints, 0, sizeof(hints)); - hints.ai_family = afp->af_af; + if (afp->af_settunnel == NULL) { + warn("address family %s does not support tunnel setup", + afp->af_name); + return; + } if ((ecode = getaddrinfo(src, NULL, NULL, &srcres)) != 0) errx(1, "error in parsing address string: %s", @@ -800,43 +591,14 @@ errx(1, "source and destination address families do not match"); - switch (srcres->ai_addr->sa_family) { - case AF_INET: - memset(&addreq, 0, sizeof(addreq)); - strncpy(addreq.ifra_name, name, IFNAMSIZ); - memcpy(&addreq.ifra_addr, srcres->ai_addr, - srcres->ai_addr->sa_len); - memcpy(&addreq.ifra_dstaddr, dstres->ai_addr, - dstres->ai_addr->sa_len); + afp->af_settunnel(s, srcres, dstres); - if (ioctl(s, SIOCSIFPHYADDR, &addreq) < 0) - warn("SIOCSIFPHYADDR"); - break; - -#ifdef INET6 - case AF_INET6: - memset(&in6_addreq, 0, sizeof(in6_addreq)); - strncpy(in6_addreq.ifra_name, name, IFNAMSIZ); - memcpy(&in6_addreq.ifra_addr, srcres->ai_addr, - srcres->ai_addr->sa_len); - memcpy(&in6_addreq.ifra_dstaddr, dstres->ai_addr, - dstres->ai_addr->sa_len); - - if (ioctl(s, SIOCSIFPHYADDR_IN6, &in6_addreq) < 0) - warn("SIOCSIFPHYADDR_IN6"); - break; -#endif /* INET6 */ - - default: - warn("address family not supported"); - } - freeaddrinfo(srcres); freeaddrinfo(dstres); } /* ARGSUSED */ -void +static void deletetunnel(const char *vname, int param, int s, const struct afswtch *afp) { @@ -844,133 +606,43 @@ err(1, "SIOCDIFPHYADDR"); } -void +static void setifnetmask(const char *addr, int dummy __unused, int s, const struct afswtch *afp) { - if (*afp->af_getaddr == NULL) - return; - setmask++; - (*afp->af_getaddr)(addr, MASK); -} - -#ifdef INET6 -void -setifprefixlen(const char *addr, int dummy __unused, int s, - const struct afswtch *afp) -{ - if (*afp->af_getprefix) - (*afp->af_getprefix)(addr, MASK); - explicit_prefix = 1; -} - -void -setip6flags(const char *dummyaddr __unused, int flag, int dummysoc __unused, - const struct afswtch *afp) -{ - if (afp->af_af != AF_INET6) - err(1, "address flags can be set only for inet6 addresses"); - - if (flag < 0) - in6_addreq.ifra_flags &= ~(-flag); - else - in6_addreq.ifra_flags |= flag; -} - -void -setip6pltime(const char *seconds, int dummy __unused, int s, - const struct afswtch *afp) -{ - setip6lifetime("pltime", seconds, s, afp); -} - -void -setip6vltime(const char *seconds, int dummy __unused, int s, - const struct afswtch *afp) -{ - setip6lifetime("vltime", seconds, s, afp); -} - -void -setip6lifetime(const char *cmd, const char *val, int s, - const struct afswtch *afp) -{ - time_t newval, t; - char *ep; - - t = time(NULL); - newval = (time_t)strtoul(val, &ep, 0); - if (val == ep) - errx(1, "invalid %s", cmd); - if (afp->af_af != AF_INET6) - errx(1, "%s not allowed for the AF", cmd); - if (strcmp(cmd, "vltime") == 0) { - in6_addreq.ifra_lifetime.ia6t_expire = t + newval; - in6_addreq.ifra_lifetime.ia6t_vltime = newval; - } else if (strcmp(cmd, "pltime") == 0) { - in6_addreq.ifra_lifetime.ia6t_preferred = t + newval; - in6_addreq.ifra_lifetime.ia6t_pltime = newval; + if (afp->af_getaddr != NULL) { + setmask++; + afp->af_getaddr(addr, MASK); } } -void -setip6eui64(const char *cmd, int dummy __unused, int s, - const struct afswtch *afp) -{ - struct ifaddrs *ifap, *ifa; - const struct sockaddr_in6 *sin6 = NULL; - const struct in6_addr *lladdr = NULL; - struct in6_addr *in6; - - if (afp->af_af != AF_INET6) - errx(EXIT_FAILURE, "%s not allowed for the AF", cmd); - in6 = (struct in6_addr *)&in6_addreq.ifra_addr.sin6_addr; - if (memcmp(&in6addr_any.s6_addr[8], &in6->s6_addr[8], 8) != 0) - errx(EXIT_FAILURE, "interface index is already filled"); - if (getifaddrs(&ifap) != 0) - err(EXIT_FAILURE, "getifaddrs"); - for (ifa = ifap; ifa; ifa = ifa->ifa_next) { - if (ifa->ifa_addr->sa_family == AF_INET6 && - strcmp(ifa->ifa_name, name) == 0) { - sin6 = (const struct sockaddr_in6 *)ifa->ifa_addr; - if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr)) { - lladdr = &sin6->sin6_addr; - break; - } - } - } - if (!lladdr) - errx(EXIT_FAILURE, "could not determine link local address"); - - memcpy(&in6->s6_addr[8], &lladdr->s6_addr[8], 8); - - freeifaddrs(ifap); -} -#endif - -void +static void setifbroadaddr(const char *addr, int dummy __unused, int s, const struct afswtch *afp) { - if (*afp->af_getaddr == NULL) - return; - (*afp->af_getaddr)(addr, DSTADDR); + if (afp->af_getaddr != NULL) + afp->af_getaddr(addr, DSTADDR); } -void +static void setifipdst(const char *addr, int dummy __unused, int s, const struct afswtch *afp) { - in_getaddr(addr, DSTADDR); + const struct afswtch *inet; + + inet = af_getbyname("inet"); + if (inet == NULL) + return; + inet->af_getaddr(addr, DSTADDR); setipdst++; clearaddr = 0; newaddr = 0; } -#define rqtosa(x) (&(((struct ifreq *)(afp->x))->ifr_addr)) -void +static void notealias(const char *addr, int param, int s, const struct afswtch *afp) { +#define rqtosa(x) (&(((struct ifreq *)(afp->x))->ifr_addr)) if (setaddr && doalias == 0 && param < 0) if (afp->af_addreq != NULL && afp->af_ridreq != NULL) bcopy((caddr_t)rqtosa(af_addreq), @@ -982,16 +654,16 @@ newaddr = 0; } else clearaddr = 0; +#undef rqtosa } /*ARGSUSED*/ -void +static void setifdstaddr(const char *addr, int param __unused, int s, const struct afswtch *afp) { - if (*afp->af_getaddr == NULL) - return; - (*afp->af_getaddr)(addr, DSTADDR); + if (afp->af_getaddr != NULL) + afp->af_getaddr(addr, DSTADDR); } /* @@ -999,7 +671,7 @@ * of the ifreq structure, which may confuse other parts of ifconfig. * Make a private copy so we can avoid that. */ -void +static void setifflags(const char *vname, int value, int s, const struct afswtch *afp) { struct ifreq my_ifr; @@ -1043,7 +715,7 @@ Perror(vname); } -void +static void setifmetric(const char *val, int dummy __unused, int s, const struct afswtch *afp) { @@ -1053,7 +725,7 @@ warn("ioctl (set metric)"); } -void +static void setifmtu(const char *val, int dummy __unused, int s, const struct afswtch *afp) { @@ -1063,14 +735,17 @@ warn("ioctl (set mtu)"); } -void +static void setifname(const char *val, int dummy __unused, int s, >>> TRUNCATED FOR MAIL (1000 lines) <<<
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200411012236.iA1MaLWA065623>