summaryrefslogtreecommitdiffstats
path: root/sbin/ifconfig
diff options
context:
space:
mode:
authorume <ume@FreeBSD.org>2002-06-15 15:35:24 +0000
committerume <ume@FreeBSD.org>2002-06-15 15:35:24 +0000
commit5d491107087efa8a27bf20b95a62726cd4cd9ce2 (patch)
tree07a726df50b1efdac1e685534a6ebb799463b1d8 /sbin/ifconfig
parent04a334b0ceba34a98d340bcfdc7f4d357d4c174e (diff)
downloadFreeBSD-src-5d491107087efa8a27bf20b95a62726cd4cd9ce2.zip
FreeBSD-src-5d491107087efa8a27bf20b95a62726cd4cd9ce2.tar.gz
Add eui64 option which fills interface index (lowermost 64bit of
an IPv6 address) automatically. This should obsolete prefix(8). Obtained from: NetBSD MFC after: 2 weeks
Diffstat (limited to 'sbin/ifconfig')
-rw-r--r--sbin/ifconfig/ifconfig.85
-rw-r--r--sbin/ifconfig/ifconfig.c37
2 files changed, 42 insertions, 0 deletions
diff --git a/sbin/ifconfig/ifconfig.8 b/sbin/ifconfig/ifconfig.8
index 0870e65..9fee24e 100644
--- a/sbin/ifconfig/ifconfig.8
+++ b/sbin/ifconfig/ifconfig.8
@@ -248,6 +248,11 @@ the system will not attempt to
transmit messages through that interface.
If possible, the interface will be reset to disable reception as well.
This action does not automatically disable routes using the interface.
+.It Cm eui64
+(Inet6 only.)
+Fill interface index
+.Pq lowermost 64bit of an IPv6 address
+automatically.
.\" .It Cm ipdst
.\" This is used to specify an Internet host who is willing to receive
.\" ip packets encapsulating NS packets bound for a remote network.
diff --git a/sbin/ifconfig/ifconfig.c b/sbin/ifconfig/ifconfig.c
index 62ccdc2..9f37f99 100644
--- a/sbin/ifconfig/ifconfig.c
+++ b/sbin/ifconfig/ifconfig.c
@@ -98,6 +98,7 @@ static const char rcsid[] =
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
+#include <ifaddrs.h>
#include "ifconfig.h"
@@ -175,6 +176,7 @@ 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;
@@ -222,6 +224,7 @@ struct cmd {
{ "-autoconf", -IN6_IFF_AUTOCONF, setip6flags },
{ "pltime", NEXTARG, setip6pltime },
{ "vltime", NEXTARG, setip6vltime },
+ { "eui64", 0, setip6eui64 },
#endif
{ "range", NEXTARG, setatrange },
{ "phase", NEXTARG, setatphase },
@@ -898,6 +901,40 @@ setip6lifetime(const char *cmd, const char *val, int s,
in6_addreq.ifra_lifetime.ia6t_pltime = newval;
}
}
+
+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
OpenPOWER on IntegriCloud