Sat Dec 10 19:14:29 2011 UTC ()
Add RDNSS and DNSSL support, RFC6106.
Replace custom lists with TAILQ lists.
Clean up plently of signed vs unsigned warnings and set WARNS=4.

Adapted from FreeBSD.


(roy)
diff -r1.43 -r1.44 src/sys/netinet/icmp6.h
diff -r1.15 -r1.16 src/usr.sbin/rtadvd/Makefile
diff -r1.12 -r1.13 src/usr.sbin/rtadvd/advcap.c
diff -r1.6 -r1.7 src/usr.sbin/rtadvd/advcap.h
diff -r1.6 -r1.7 src/usr.sbin/rtadvd/config.h
diff -r1.6 -r1.7 src/usr.sbin/rtadvd/timer.h
diff -r1.25 -r1.26 src/usr.sbin/rtadvd/config.c
diff -r1.8 -r1.9 src/usr.sbin/rtadvd/dump.c
diff -r1.1 -r1.2 src/usr.sbin/rtadvd/dump.h
diff -r1.18 -r1.19 src/usr.sbin/rtadvd/if.c
diff -r1.7 -r1.8 src/usr.sbin/rtadvd/if.h
diff -r1.13 -r1.14 src/usr.sbin/rtadvd/rrenum.c
diff -r1.4 -r1.5 src/usr.sbin/rtadvd/rrenum.h
diff -r1.35 -r1.36 src/usr.sbin/rtadvd/rtadvd.c
diff -r1.14 -r1.15 src/usr.sbin/rtadvd/rtadvd.conf.5
diff -r1.10 -r1.11 src/usr.sbin/rtadvd/rtadvd.h
diff -r1.9 -r1.10 src/usr.sbin/rtadvd/timer.c

cvs diff -r1.43 -r1.44 src/sys/netinet/icmp6.h (expand / switch to context diff)
--- src/sys/netinet/icmp6.h 2011/11/11 15:09:32 1.43
+++ src/sys/netinet/icmp6.h 2011/12/10 19:14:29 1.44
@@ -1,4 +1,4 @@
-/*	$NetBSD: icmp6.h,v 1.43 2011/11/11 15:09:32 gdt Exp $	*/
+/*	$NetBSD: icmp6.h,v 1.44 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: icmp6.h,v 1.84 2003/04/23 10:26:51 itojun Exp $	*/
 
 
@@ -300,11 +300,10 @@
 #define ND_OPT_HOMEAGENT_INFO		8
 #define ND_OPT_SOURCE_ADDRLIST		9
 #define ND_OPT_TARGET_ADDRLIST		10
-/* RFC5380 */
-#define ND_OPT_MAP			23
-/* RFC4191 */
-#define ND_OPT_ROUTE_INFO		24
-#define ND_OPT_RDNSS			25
+#define ND_OPT_MAP			23	/* RFC 5380 */
+#define ND_OPT_ROUTE_INFO		24	/* RFC 4191 */
+#define ND_OPT_RDNSS			25	/* RFC 6016 */
+#define ND_OPT_DNSSL			31	/* RFC 6016 */
 
 struct nd_opt_route_info {	/* route info */
 	u_int8_t	nd_opt_rti_type;
@@ -344,11 +343,19 @@
 	u_int32_t	nd_opt_mtu_mtu;
 } __packed;
 
-struct nd_opt_rdnss {		/* RDNSS option RFC 5006 */
+struct nd_opt_rdnss {		/* RDNSS option RFC 6106 */
 	u_int8_t	nd_opt_rdnss_type;
 	u_int8_t	nd_opt_rdnss_len;
 	u_int16_t	nd_opt_rdnss_reserved;
 	u_int32_t	nd_opt_rdnss_lifetime;
+	/* followed by list of IP prefixes */
+} __packed;
+
+struct nd_opt_dnssl {		/* DNSSL option RFC 6106 */
+	u_int8_t	nd_opt_dnssl_type;
+	u_int8_t	nd_opt_dnssl_len;
+	u_int16_t	nd_opt_dnssl_reserved;
+	u_int32_t	nd_opt_dnssl_lifetime;
 	/* followed by list of IP prefixes */
 } __packed;
 

cvs diff -r1.15 -r1.16 src/usr.sbin/rtadvd/Makefile (expand / switch to context diff)
--- src/usr.sbin/rtadvd/Makefile 2011/06/20 07:44:04 1.15
+++ src/usr.sbin/rtadvd/Makefile 2011/12/10 19:14:29 1.16
@@ -1,6 +1,6 @@
-# $NetBSD: Makefile,v 1.15 2011/06/20 07:44:04 mrg Exp $
+# $NetBSD: Makefile,v 1.16 2011/12/10 19:14:29 roy Exp $
 
-WARNS?=	2	# XXX -Wcast-qual -Wsign-compare
+WARNS?=	4
 
 .include <bsd.own.mk>
 
@@ -9,7 +9,7 @@
 PROG=	rtadvd
 SRCS=	rtadvd.c rrenum.c advcap.c if.c config.c timer.c dump.c
 
-CPPFLAGS+=-DINET6 -DROUTEINFO
+CPPFLAGS+=-DINET6
 MAN=	rtadvd.8 rtadvd.conf.5
 LDADD+=	-lutil
 DPADD+=	${LIBUTIL}

cvs diff -r1.12 -r1.13 src/usr.sbin/rtadvd/advcap.c (expand / switch to context diff)
--- src/usr.sbin/rtadvd/advcap.c 2006/03/18 22:07:15 1.12
+++ src/usr.sbin/rtadvd/advcap.c 2011/12/10 19:14:29 1.13
@@ -1,4 +1,4 @@
-/*	$NetBSD: advcap.c,v 1.12 2006/03/18 22:07:15 dan Exp $	*/
+/*	$NetBSD: advcap.c,v 1.13 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: advcap.c,v 1.11 2003/05/19 09:46:50 keiichi Exp $	*/
 
 /*
@@ -87,15 +87,15 @@
 
 extern char *conffile;
 
-int tgetent __P((char *, char *));
-int getent __P((char *, char *, char *));
-int tnchktc __P((void));
-int tnamatch __P((char *));
-static char *tskip __P((char *));
-int64_t tgetnum __P((char *));
-int tgetflag __P((char *));
-char *tgetstr __P((char *, char **));
-static char *tdecode __P((char *, char **));
+int tgetent(char *, char *);
+int getent(char *, char *, char *);
+int tnchktc(void);
+int tnamatch(char *);
+static char *tskip(char *);
+int64_t tgetnum(char *);
+int tgetflag(char *);
+char *tgetstr(char *, char **);
+static char *tdecode(char *, char **);
 
 /*
  * Get an entry for terminal name in buffer bp,
@@ -103,18 +103,16 @@
  * we just notice escaped newlines.
  */
 int
-tgetent(bp, name)
-	char *bp, *name;
+tgetent(char *bp, char *name)
 {
 	char *cp;
 
-	remotefile = cp = conffile ? conffile : _PATH_RTADVDCONF;
+	remotefile = cp = conffile ? conffile : __UNCONST(_PATH_RTADVDCONF);
 	return (getent(bp, name, cp));
 }
 
 int
-getent(bp, name, cp)
-	char *bp, *name, *cp;
+getent(char *bp, char *name, char *cp)
 {
 	int c;
 	int i = 0, cnt = 0;
@@ -183,7 +181,7 @@
  * Note that this works because of the left to right scan.
  */
 int
-tnchktc()
+tnchktc(void)
 {
 	char *p, *q;
 	char tcname[16];	/* name of similar terminal */
@@ -232,8 +230,7 @@
  * name (before the first field) stops us.
  */
 int
-tnamatch(np)
-	char *np;
+tnamatch(char *np)
 {
 	char *Np, *Bp;
 
@@ -259,8 +256,7 @@
  * into the termcap file in octal.
  */
 static char *
-tskip(bp)
-	char *bp;
+tskip(char *bp)
 {
 	int dquote;
 
@@ -304,8 +300,7 @@
  * Note that we handle octal numbers beginning with 0.
  */
 int64_t
-tgetnum(id)
-	char *id;
+tgetnum(char *id)
 {
 	int64_t i;
 	int base;
@@ -340,8 +335,7 @@
  * not given.
  */
 int
-tgetflag(id)
-	char *id;
+tgetflag(char *id)
 {
 	char *bp = tbuf;
 
@@ -368,8 +362,7 @@
  * No checking on area overflow.
  */
 char *
-tgetstr(id, area)
-	char *id, **area;
+tgetstr(char *id, char **area)
 {
 	char *bp = tbuf;
 
@@ -394,13 +387,11 @@
  * string capability escapes.
  */
 static char *
-tdecode(str, area)
-	char *str;
-	char **area;
+tdecode(char *str, char **area)
 {
 	char *cp;
 	int c;
-	char *dp;
+	const char *dps = "E\033^^\\\\::n\nr\rt\tb\bf\f\"\"", *dp;
 	int i;
 	char term;
 
@@ -419,7 +410,7 @@
 			break;
 
 		case '\\':
-			dp = "E\033^^\\\\::n\nr\rt\tb\bf\f\"\"";
+			dp = dps; 
 			c = *str++;
 nextc:
 			if (*dp++ == c) {

cvs diff -r1.6 -r1.7 src/usr.sbin/rtadvd/advcap.h (expand / switch to context diff)
--- src/usr.sbin/rtadvd/advcap.h 2006/03/05 23:47:08 1.6
+++ src/usr.sbin/rtadvd/advcap.h 2011/12/10 19:14:29 1.7
@@ -1,4 +1,4 @@
-/*	$NetBSD: advcap.h,v 1.6 2006/03/05 23:47:08 rpaulo Exp $	*/
+/*	$NetBSD: advcap.h,v 1.7 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: advcap.h,v 1.5 2003/06/09 05:40:54 t-momose Exp $	*/
 
 /*
@@ -36,10 +36,10 @@
 
 __BEGIN_DECLS
 
-extern int agetent __P((char *, const char *));
-extern int agetflag __P((const char *));
-extern int64_t agetnum __P((const char *));
-extern char *agetstr __P((const char *, char **));
+extern int agetent(char *, const char *);
+extern int agetflag(const char *);
+extern int64_t agetnum(const char *);
+extern char *agetstr(const char *, char **);
 
 __END_DECLS
 

cvs diff -r1.6 -r1.7 src/usr.sbin/rtadvd/config.h (expand / switch to context diff)
--- src/usr.sbin/rtadvd/config.h 2006/03/05 23:47:08 1.6
+++ src/usr.sbin/rtadvd/config.h 2011/12/10 19:14:29 1.7
@@ -1,4 +1,4 @@
-/*	$NetBSD: config.h,v 1.6 2006/03/05 23:47:08 rpaulo Exp $	*/
+/*	$NetBSD: config.h,v 1.7 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: config.h,v 1.9 2003/08/06 04:19:40 ono Exp $	*/
 
 /*
@@ -30,18 +30,19 @@
  * SUCH DAMAGE.
  */
 
-extern void getconfig __P((char *));
-extern void delete_prefix __P((struct prefix *));
-extern void invalidate_prefix __P((struct prefix *));
-extern void update_prefix __P((struct prefix *));
-extern void make_prefix __P((struct rainfo *, int, struct in6_addr *, int));
-extern void make_packet __P((struct rainfo *));
-extern void get_prefix __P((struct rainfo *));
+extern void getconfig(char *);
+extern void delete_prefix(struct prefix *);
+extern void invalidate_prefix(struct prefix *);
+extern void update_prefix(struct prefix *);
+extern void make_prefix(struct rainfo *, int, struct in6_addr *, int);
+extern void make_packet(struct rainfo *);
+extern void get_prefix(struct rainfo *);
 
-
 /*
- * it is highly unlikely to have 100 prefix information options,
+ * it is highly unlikely to have 100 information options,
  * so it should be okay to limit it
  */
 #define MAXPREFIX	100
 #define MAXROUTE	100
+#define MAXRDNSS	100
+#define MAXDNSSL	100

cvs diff -r1.6 -r1.7 src/usr.sbin/rtadvd/timer.h (expand / switch to context diff)
--- src/usr.sbin/rtadvd/timer.h 2006/03/05 23:47:08 1.6
+++ src/usr.sbin/rtadvd/timer.h 2011/12/10 19:14:29 1.7
@@ -1,4 +1,4 @@
-/*	$NetBSD: timer.h,v 1.6 2006/03/05 23:47:08 rpaulo Exp $	*/
+/*	$NetBSD: timer.h,v 1.7 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: timer.h,v 1.5 2002/05/31 13:30:38 jinmei Exp $	*/
 
 /*
@@ -40,26 +40,26 @@
 			   (((a).tv_sec == (b).tv_sec) &&\
  			    ((a).tv_usec <= (b).tv_usec)))
 
+extern TAILQ_HEAD(rtadvd_timer_head_t, rtadvd_timer) ra_timer;
 struct rtadvd_timer {
-	struct rtadvd_timer *next;
-	struct rtadvd_timer *prev;
+	TAILQ_ENTRY(rtadvd_timer) next;
 	struct rainfo *rai;
 	struct timeval tm;
 
-	struct rtadvd_timer *(*expire) __P((void *));	/* expiration function */
+	struct rtadvd_timer *(*expire) (void *); /* expiration function */
 	void *expire_data;
 	void (*update) __P((void *, struct timeval *));	/* update function */
 	void *update_data;
 };
 
-void rtadvd_timer_init __P((void));
+void rtadvd_timer_init(void);
-struct rtadvd_timer *rtadvd_add_timer __P((struct rtadvd_timer *(*) __P((void *)),
+struct rtadvd_timer *rtadvd_add_timer(struct rtadvd_timer *(*) (void *),
-		void (*) __P((void *, struct timeval *)), void *, void *));
+		void (*) (void *, struct timeval *), void *, void *);
-void rtadvd_set_timer __P((struct timeval *, struct rtadvd_timer *));
+void rtadvd_set_timer(struct timeval *, struct rtadvd_timer *);
-void rtadvd_remove_timer __P((struct rtadvd_timer **));
+void rtadvd_remove_timer(struct rtadvd_timer **);
-struct timeval * rtadvd_check_timer __P((void));
+struct timeval * rtadvd_check_timer(void);
-struct timeval * rtadvd_timer_rest __P((struct rtadvd_timer *));
+struct timeval * rtadvd_timer_rest(struct rtadvd_timer *);
-void TIMEVAL_ADD __P((struct timeval *, struct timeval *,
+void TIMEVAL_ADD(struct timeval *, struct timeval *,
-		      struct timeval *));
+		      struct timeval *);
-void TIMEVAL_SUB __P((struct timeval *, struct timeval *,
+void TIMEVAL_SUB(struct timeval *, struct timeval *,
-		      struct timeval *));
+		      struct timeval *);

cvs diff -r1.25 -r1.26 src/usr.sbin/rtadvd/config.c (expand / switch to context diff)
--- src/usr.sbin/rtadvd/config.c 2006/05/11 08:35:47 1.25
+++ src/usr.sbin/rtadvd/config.c 2011/12/10 19:14:29 1.26
@@ -1,4 +1,4 @@
-/*	$NetBSD: config.c,v 1.25 2006/05/11 08:35:47 mrg Exp $	*/
+/*	$NetBSD: config.c,v 1.26 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: config.c,v 1.93 2005/10/17 14:40:02 suz Exp $	*/
 
 /*
@@ -66,25 +66,45 @@
 
 static time_t prefix_timo = (60 * 120);	/* 2 hours.
 					 * XXX: should be configurable. */
-extern struct rainfo *ralist;
+static struct rtadvd_timer *prefix_timeout(void *);
+static void makeentry(char *, size_t, int, const char *);
+static int getinet6sysctl(int);
 
-static struct rtadvd_timer *prefix_timeout __P((void *));
-static void makeentry __P((char *, size_t, int, char *));
-static int getinet6sysctl __P((int));
+static size_t
+encode_domain(char *dst, const char *src)
+{
+	ssize_t len;
+	char *odst, *p;
 
+	odst = dst;
+	while (src && (len = strlen(src)) != 0) {
+		p = strchr(src, '.');
+		*dst++ = len = MIN(63, p == NULL ? len : p - src);
+		memcpy(dst, src, len);
+		dst += len;
+		if (p == NULL)
+			break;
+		src = p + 1;
+	}
+	*dst++ = '\0';
+	
+	return dst - odst;
+}
+
 void
 getconfig(intface)
 	char *intface;
 {
-	int stat, i;
+	int stat, c, i;
 	char tbuf[BUFSIZ];
 	struct rainfo *tmp;
-	long val;
+	int32_t val;
 	int64_t val64;
 	char buf[BUFSIZ];
 	char *bp = buf;
-	char *addr, *flagstr;
+	char *addr, *flagstr, *ap;
 	static int forwarding = -1;
+	char entbuf[256], abuf[256];
 
 #define MUSTHAVE(var, cap)	\
     do {								\
@@ -101,7 +121,18 @@
 	if ((var = agetnum(cap)) < 0)					\
 		var = def;						\
      } while (0)
+#define	ELM_MALLOC(p,error_action)					\
+	do {								\
+		p = malloc(sizeof(*p));					\
+		if (p == NULL) {					\
+			syslog(LOG_ERR, "<%s> malloc failed: %s",	\
+			    __func__, strerror(errno));			\
+			error_action;					\
+		}							\
+		memset(p, 0, sizeof(*p));				\
+	} while(0)
 
+
 	if ((stat = agetent(tbuf, intface)) <= 0) {
 		memset(tbuf, 0, sizeof(tbuf));
 		syslog(LOG_INFO,
@@ -111,17 +142,8 @@
 		        __func__, intface);
 	}
 
-	tmp = (struct rainfo *)malloc(sizeof(*ralist));
-	if (tmp == NULL) {
-		syslog(LOG_INFO, "<%s> %s: can't allocate enough memory",
-		    __func__, intface);
-		exit(1);
-	}
+	ELM_MALLOC(tmp, exit(1));
 	memset(tmp, 0, sizeof(*tmp));
-	tmp->prefix.next = tmp->prefix.prev = &tmp->prefix;
-#ifdef ROUTEINFO
-	tmp->route.next = tmp->route.prev = &tmp->route;
-#endif
 
 	/* check if we are allowed to forward packets (if not determined) */
 	if (forwarding < 0) {
@@ -158,22 +180,22 @@
 	MAYHAVE(val, "maxinterval", DEF_MAXRTRADVINTERVAL);
 	if (val < MIN_MAXINTERVAL || val > MAX_MAXINTERVAL) {
 		syslog(LOG_ERR,
-		       "<%s> maxinterval (%ld) on %s is invalid "
+		       "<%s> maxinterval (%d) on %s is invalid "
 		       "(must be between %u and %u)", __func__, val,
 		       intface, MIN_MAXINTERVAL, MAX_MAXINTERVAL);
 		exit(1);
 	}
-	tmp->maxinterval = (u_int)val;
+	tmp->maxinterval = val;
 	MAYHAVE(val, "mininterval", tmp->maxinterval/3);
 	if (val < MIN_MININTERVAL || val > (tmp->maxinterval * 3) / 4) {
 		syslog(LOG_ERR,
-		       "<%s> mininterval (%ld) on %s is invalid "
+		       "<%s> mininterval (%d) on %s is invalid "
 		       "(must be between %u and %d)",
 		       __func__, val, intface, MIN_MININTERVAL,
 		       (tmp->maxinterval * 3) / 4);
 		exit(1);
 	}
-	tmp->mininterval = (u_int)val;
+	tmp->mininterval = val;
 
 	MAYHAVE(val, "chlim", DEF_ADVCURHOPLIMIT);
 	tmp->hoplimit = val & 0xff;
@@ -213,7 +235,7 @@
 	MAYHAVE(val, "rltime", tmp->maxinterval * 3);
 	if (val && (val < tmp->maxinterval || val > MAXROUTERLIFETIME)) {
 		syslog(LOG_ERR,
-		       "<%s> router lifetime (%ld) on %s is invalid "
+		       "<%s> router lifetime (%d) on %s is invalid "
 		       "(must be 0 or between %d and %d)",
 		       __func__, val, intface,
 		       tmp->maxinterval, MAXROUTERLIFETIME);
@@ -240,12 +262,12 @@
 	MAYHAVE(val, "rtime", DEF_ADVREACHABLETIME);
 	if (val < 0 || val > MAXREACHABLETIME) {
 		syslog(LOG_ERR,
-		       "<%s> reachable time (%ld) on %s is invalid "
+		       "<%s> reachable time (%d) on %s is invalid "
 		       "(must be no greater than %d)",
 		       __func__, val, intface, MAXREACHABLETIME);
 		exit(1);
 	}
-	tmp->reachabletime = (u_int32_t)val;
+	tmp->reachabletime = (uint32_t)val;
 
 	MAYHAVE(val64, "retrans", DEF_ADVRETRANSTIMER);
 	if (val64 < 0 || val64 > 0xffffffff) {
@@ -253,7 +275,7 @@
 		       __func__, (long long)val64, intface);
 		exit(1);
 	}
-	tmp->retranstimer = (u_int32_t)val64;
+	tmp->retranstimer = (uint32_t)val64;
 
 	if (agetnum("hapref") != -1 || agetnum("hatime") != -1) {
 		syslog(LOG_ERR,
@@ -271,10 +293,10 @@
 	MAYHAVE(val, "clockskew", 0);
 	tmp->clockskew = val;
 
-	tmp->pfxs = 0;
+	tmp->pfxs++;
+	TAILQ_INIT(&tmp->prefix);
 	for (i = -1; i < MAXPREFIX; i++) {
 		struct prefix *pfx;
-		char entbuf[256];
 
 		makeentry(entbuf, sizeof(entbuf), i, "addr");
 		addr = (char *)agetstr(entbuf, &bp);
@@ -290,10 +312,9 @@
 		}
 		memset(pfx, 0, sizeof(*pfx));
 
-		/* link into chain */
-		insque(pfx, &tmp->prefix);
-		pfx->rainfo = tmp;
+		TAILQ_INSERT_TAIL(&tmp->prefix, pfx, next);
 		tmp->pfxs++;
+		pfx->rainfo = tmp;
 
 		pfx->origin = PREFIX_FROM_CONFIG;
 
@@ -319,7 +340,7 @@
 		makeentry(entbuf, sizeof(entbuf), i, "prefixlen");
 		MAYHAVE(val, entbuf, 64);
 		if (val < 0 || val > 128) {
-			syslog(LOG_ERR, "<%s> prefixlen (%ld) for %s "
+			syslog(LOG_ERR, "<%s> prefixlen (%d) for %s "
 			       "on %s out of range",
 			       __func__, val, addr, intface);
 			exit(1);
@@ -349,7 +370,7 @@
 			    addr, pfx->prefixlen, intface);
 			exit(1);
 		}
-		pfx->validlifetime = (u_int32_t)val64;
+		pfx->validlifetime = (uint32_t)val64;
 
 		makeentry(entbuf, sizeof(entbuf), i, "vltimedecr");
 		if (agetflag(entbuf)) {
@@ -369,7 +390,7 @@
 			    addr, pfx->prefixlen, intface);
 			exit(1);
 		}
-		pfx->preflifetime = (u_int32_t)val64;
+		pfx->preflifetime = (uint32_t)val64;
 
 		makeentry(entbuf, sizeof(entbuf), i, "pltimedecr");
 		if (agetflag(entbuf)) {
@@ -379,17 +400,17 @@
 				now.tv_sec + pfx->preflifetime;
 		}
 	}
-	if (tmp->pfxs == 0)
+	if (TAILQ_FIRST(&tmp->prefix) == NULL)
 		get_prefix(tmp);
 
-	MAYHAVE(val, "mtu", 0);
-	if (val < 0 || val > 0xffffffff) {
+	MAYHAVE(val64, "mtu", 0);
+	if (val64 < 0 || val64 > 0xffffffff) {
 		syslog(LOG_ERR,
-		       "<%s> mtu (%ld) on %s out of range",
-		       __func__, val, intface);
+		       "<%s> mtu (%" PRIi64 ") on %s out of range",
+		       __func__, val64, intface);
 		exit(1);
 	}
-	tmp->linkmtu = (u_int32_t)val;
+	tmp->linkmtu = (uint32_t)val64;
 	if (tmp->linkmtu == 0) {
 		char *mtustr;
 
@@ -399,9 +420,9 @@
 	}
 	else if (tmp->linkmtu < IPV6_MMTU || tmp->linkmtu > tmp->phymtu) {
 		syslog(LOG_ERR,
-		       "<%s> advertised link mtu (%lu) on %s is invalid (must "
+		       "<%s> advertised link mtu (%d) on %s is invalid (must "
 		       "be between least MTU (%d) and physical link MTU (%d)",
-		       __func__, (unsigned long)tmp->linkmtu, intface,
+		       __func__, tmp->linkmtu, intface,
 		       IPV6_MMTU, tmp->phymtu);
 		exit(1);
 	}
@@ -418,7 +439,7 @@
 		}
 		memset(&ndi, 0, sizeof(ndi));
 		strncpy(ndi.ifname, intface, IFNAMSIZ);
-		if (ioctl(s, SIOCGIFINFO_IN6, (caddr_t)&ndi) < 0) {
+		if (ioctl(s, SIOCGIFINFO_IN6, &ndi) < 0) {
 			syslog(LOG_INFO, "<%s> ioctl:SIOCGIFINFO_IN6 at %s: %s",
 			     __func__, intface, strerror(errno));
 		}
@@ -427,7 +448,7 @@
 		ndi.ndi.chlim = tmp->hoplimit;
 		ndi.ndi.retrans = tmp->retranstimer;
 		ndi.ndi.basereachable = tmp->reachabletime;
-		if (ioctl(s, SIOCSIFINFO_IN6, (caddr_t)&ndi) < 0) {
+		if (ioctl(s, SIOCSIFINFO_IN6, &ndi) < 0) {
 			syslog(LOG_INFO, "<%s> ioctl:SIOCSIFINFO_IN6 at %s: %s",
 			     __func__, intface, strerror(errno));
 		}
@@ -436,11 +457,10 @@
 #endif
 
 	/* route information */
-#ifdef ROUTEINFO
-	tmp->routes = 0;
+	TAILQ_INIT(&tmp->route);
 	for (i = -1; i < MAXROUTE; i++) {
 		struct rtinfo *rti;
-		char entbuf[256], oentbuf[256];
+		char oentbuf[256];
 
 		makeentry(entbuf, sizeof(entbuf), i, "rtprefix");
 		addr = (char *)agetstr(entbuf, &bp);
@@ -455,18 +475,11 @@
 		if (addr == NULL)
 			continue;
 
-		/* allocate memory to store prefix information */
-		if ((rti = malloc(sizeof(struct rtinfo))) == NULL) {
-			syslog(LOG_ERR,
-			       "<%s> can't allocate enough memory",
-			       __func__);
-			exit(1);
-		}
+		ELM_MALLOC(rti, exit(1));
 		memset(rti, 0, sizeof(*rti));
 
 		/* link into chain */
-		insque(rti, &tmp->route);
-		tmp->routes++;
+		TAILQ_INSERT_TAIL(&tmp->route, rti, next);
 
 		if (inet_pton(AF_INET6, addr, &rti->prefix) != 1) {
 			syslog(LOG_ERR, "<%s> inet_pton failed for %s",
@@ -510,7 +523,7 @@
 				val = 64;
 		}
 		if (val < 0 || val > 128) {
-			syslog(LOG_ERR, "<%s> prefixlen (%ld) for %s on %s "
+			syslog(LOG_ERR, "<%s> prefixlen (%d) for %s on %s "
 			       "out of range",
 			       __func__, val, addr, intface);
 			exit(1);
@@ -579,13 +592,89 @@
 			    (long long)val64, addr, rti->prefixlen, intface);
 			exit(1);
 		}
-		rti->ltime = (u_int32_t)val64;
+		rti->ltime = (uint32_t)val64;
 	}
-#endif
 
+	/* RDNSS */
+	TAILQ_INIT(&tmp->rdnss);
+	for (i = -1; i < MAXRDNSS; i++) {
+		struct rdnss *rdnss;
+		struct rdnss_addr *rdnsa;
+
+		makeentry(entbuf, sizeof(entbuf), i, "rdnss");
+		addr = (char *)agetstr(entbuf, &bp);
+		if (addr == NULL)
+			continue;
+
+		ELM_MALLOC(rdnss, exit(1));
+		TAILQ_INIT(&rdnss->list);
+
+		for (ap = addr; ap - addr < (ssize_t)strlen(addr); ap += c+1) {
+			c = strcspn(ap, ",");
+			strncpy(abuf, ap, c);
+			abuf[c] = '\0';
+			ELM_MALLOC(rdnsa, exit(1));
+			if (inet_pton(AF_INET6, abuf, &rdnsa->addr) != 1) {
+				syslog(LOG_ERR, "<%s> inet_pton failed for %s",
+			           __func__, addr);
+				exit(1);
+			}
+			TAILQ_INSERT_TAIL(&rdnss->list, rdnsa, next);
+		}
+
+		makeentry(entbuf, sizeof(entbuf), i, "rdnssltime");
+		MAYHAVE(val64, entbuf, tmp->maxinterval * 3 / 2);
+		if (val64 < tmp->maxinterval ||
+		    val64 > tmp->maxinterval * 2)
+		{
+			syslog(LOG_ERR, "<%s> %s (%lld) on %s is invalid",
+		    	     __func__, entbuf, (long long)val64, intface);
+			exit(1);
+		}
+		rdnss->lifetime = (uint32_t)val64;
+
+		TAILQ_INSERT_TAIL(&tmp->rdnss, rdnss, next);
+	}
+
+	/* DNSSL */
+	TAILQ_INIT(&tmp->dnssl);
+	for (i = -1; i < MAXDNSSL; i++) {
+		struct dnssl *dnssl;
+		struct dnssl_domain *dnsd;
+
+		makeentry(entbuf, sizeof(entbuf), i, "dnssl");
+		addr = (char *)agetstr(entbuf, &bp);
+		if (addr == NULL)
+			continue;
+
+		ELM_MALLOC(dnssl, exit(1));
+		TAILQ_INIT(&dnssl->list);
+
+		for (ap = addr; ap - addr < (ssize_t)strlen(addr); ap += c+1) {
+			c = strcspn(ap, ",");
+			strncpy(abuf, ap, c);
+			abuf[c] = '\0';
+			ELM_MALLOC(dnsd, exit(1));
+			dnsd->len = encode_domain(dnsd->domain, abuf);
+			TAILQ_INSERT_TAIL(&dnssl->list, dnsd, next);
+		}
+
+		makeentry(entbuf, sizeof(entbuf), i, "dnsslltime");
+		MAYHAVE(val64, entbuf, tmp->maxinterval * 3 / 2);
+		if (val64 < tmp->maxinterval ||
+		    val64 > tmp->maxinterval * 2)
+		{
+			syslog(LOG_ERR, "<%s> %s (%lld) on %s is invalid",
+		    	     __func__, entbuf, (long long)val64, intface);
+			exit(1);
+		}
+		dnssl->lifetime = (uint32_t)val64;
+
+		TAILQ_INSERT_TAIL(&tmp->dnssl, dnssl, next);
+	}
+
 	/* okey */
-	tmp->next = ralist;
-	ralist = tmp;
+	TAILQ_INSERT_TAIL(&ralist, tmp, next);
 
 	/* construct the sending packet */
 	make_packet(tmp);
@@ -603,7 +692,7 @@
 	struct ifaddrs *ifap, *ifa;
 	struct prefix *pp;
 	struct in6_addr *a;
-	u_char *p, *ep, *m, *lim;
+	unsigned char *p, *ep, *m, *lim;
 	char ntopbuf[INET6_ADDRSTRLEN];
 
 	if (getifaddrs(&ifap) < 0) {
@@ -624,8 +713,8 @@
 		if (IN6_IS_ADDR_LINKLOCAL(a))
 			continue;
 		/* get prefix length */
-		m = (u_char *)&((struct sockaddr_in6 *)ifa->ifa_netmask)->sin6_addr;
-		lim = (u_char *)(ifa->ifa_netmask) + ifa->ifa_netmask->sa_len;
+		m = (unsigned char *)&((struct sockaddr_in6 *)ifa->ifa_netmask)->sin6_addr;
+		lim = (unsigned char *)(ifa->ifa_netmask) + ifa->ifa_netmask->sa_len;
 		plen = prefixlen(m, lim);
 		if (plen <= 0 || plen > 128) {
 			syslog(LOG_ERR, "<%s> failed to get prefixlen "
@@ -654,8 +743,8 @@
 		memcpy(&pp->prefix, a, sizeof(*a));
 		if (1)
 		{
-			p = (u_char *)&pp->prefix;
-			ep = (u_char *)(&pp->prefix + 1);
+			p = (unsigned char *)&pp->prefix;
+			ep = (unsigned char *)(&pp->prefix + 1);
 			while (m < lim && p < ep)
 				*p++ &= *m++;
 			while (p < ep)
@@ -679,21 +768,14 @@
 		pp->rainfo = rai;
 
 		/* link into chain */
-		insque(pp, &rai->prefix);
-
-		/* counter increment */
-		rai->pfxs++;
+		TAILQ_INSERT_TAIL(&rai->prefix, pp, next);
 	}
 
 	freeifaddrs(ifap);
 }
 
 static void
-makeentry(buf, len, id, string)
-	char *buf;
-	size_t len;
-	int id;
-	char *string;
+makeentry(char *buf, size_t len, int id, const char *string)
 {
 
 	if (id < 0)
@@ -729,8 +811,9 @@
 	prefix->autoconfflg = ipr->ipr_raf_auto;
 	prefix->origin = PREFIX_FROM_DYNAMIC;
 
-	insque(prefix, &rai->prefix);
 	prefix->rainfo = rai;
+	TAILQ_INSERT_TAIL(&rai->prefix, prefix, next);
+	rai->pfxs++;
 
 	syslog(LOG_DEBUG, "<%s> new prefix %s/%d was added on %s",
 	       __func__, inet_ntop(AF_INET6, &ipr->ipr_prefix.sin6_addr,
@@ -742,7 +825,6 @@
 	rai->ra_data = NULL;
 
 	/* reconstruct the packet */
-	rai->pfxs++;
 	make_packet(rai);
 }
 
@@ -757,7 +839,8 @@
 	char ntopbuf[INET6_ADDRSTRLEN];
 	struct rainfo *rai = prefix->rainfo;
 
-	remque(prefix);
+	TAILQ_REMOVE(&rai->prefix, prefix, next);
+	rai->pfxs--;
 	syslog(LOG_DEBUG, "<%s> prefix %s/%d was deleted on %s",
 	       __func__, inet_ntop(AF_INET6, &prefix->prefix,
 				       ntopbuf, INET6_ADDRSTRLEN),
@@ -765,7 +848,6 @@
 	if (prefix->timer)
 		rtadvd_remove_timer(&prefix->timer);
 	free(prefix);
-	rai->pfxs--;
 }
 
 void
@@ -847,7 +929,7 @@
 		exit(1);
 	}
 
-	if (ioctl(s, SIOCGIFPREFIX_IN6, (caddr_t)ipr) < 0) {
+	if (ioctl(s, SIOCGIFPREFIX_IN6, ipr) < 0) {
 		syslog(LOG_INFO, "<%s> ioctl:SIOCGIFPREFIX %s", __func__,
 		       strerror(errno));
 
@@ -906,15 +988,20 @@
 make_packet(struct rainfo *rainfo)
 {
 	size_t packlen, lladdroptlen = 0;
-	u_char *buf;
+	char *buf;
 	struct nd_router_advert *ra;
 	struct nd_opt_prefix_info *ndopt_pi;
 	struct nd_opt_mtu *ndopt_mtu;
 	struct prefix *pfx;
-#ifdef ROUTEINFO
 	struct nd_opt_route_info *ndopt_rti;
 	struct rtinfo *rti;
-#endif
+	struct nd_opt_rdnss *ndopt_rdnss;
+	struct rdnss *rdns;
+	struct rdnss_addr *rdnsa;
+	struct nd_opt_dnssl *ndopt_dnssl;
+	struct dnssl *dnsl;
+	struct dnssl_domain *dnsd;
+	size_t len, plen;
 
 	/* calculate total length */
 	packlen = sizeof(struct nd_router_advert);
@@ -928,16 +1015,28 @@
 		}
 		packlen += lladdroptlen;
 	}
-	if (rainfo->pfxs)
+	if (TAILQ_FIRST(&rainfo->prefix) != NULL)
 		packlen += sizeof(struct nd_opt_prefix_info) * rainfo->pfxs;
 	if (rainfo->linkmtu)
 		packlen += sizeof(struct nd_opt_mtu);
-#ifdef ROUTEINFO
-	for (rti = rainfo->route.next; rti != &rainfo->route; rti = rti->next)
+	TAILQ_FOREACH(rti, &rainfo->route, next) 
 		packlen += sizeof(struct nd_opt_route_info) + 
 			   ((rti->prefixlen + 0x3f) >> 6) * 8;
-#endif
 
+	TAILQ_FOREACH(rdns, &rainfo->rdnss, next) {
+		packlen += sizeof(struct nd_opt_rdnss);
+		TAILQ_FOREACH(rdnsa, &rdns->list, next)
+			packlen += sizeof(rdnsa->addr);
+	}
+	TAILQ_FOREACH(dnsl, &rainfo->dnssl, next) {
+		packlen += sizeof(struct nd_opt_dnssl);
+		len = 0;
+		TAILQ_FOREACH(dnsd, &dnsl->list, next)
+			len += dnsd->len;
+		len += len % 8 ? 8 - len % 8 : 0;
+		packlen += len;
+	}
+
 	/* allocate memory for the packet */
 	if ((buf = malloc(packlen)) == NULL) {
 		syslog(LOG_ERR,
@@ -961,7 +1060,7 @@
 	ra->nd_ra_type = ND_ROUTER_ADVERT;
 	ra->nd_ra_code = 0;
 	ra->nd_ra_cksum = 0;
-	ra->nd_ra_curhoplimit = (u_int8_t)(0xff & rainfo->hoplimit);
+	ra->nd_ra_curhoplimit = (uint8_t)(0xff & rainfo->hoplimit);
 	ra->nd_ra_flags_reserved = 0; /* just in case */
 	/*
 	 * XXX: the router preference field, which is a 2-bit field, should be
@@ -991,11 +1090,8 @@
 		buf += sizeof(struct nd_opt_mtu);
 	}
 
-	
-	
-	for (pfx = rainfo->prefix.next;
-	     pfx != &rainfo->prefix; pfx = pfx->next) {
-		u_int32_t vltime, pltime;
+	TAILQ_FOREACH(pfx, &rainfo->prefix, next) {	
+		uint32_t vltime, pltime;
 		struct timeval now;
 
 		ndopt_pi = (struct nd_opt_prefix_info *)buf;
@@ -1044,9 +1140,8 @@
 		buf += sizeof(struct nd_opt_prefix_info);
 	}
 
-#ifdef ROUTEINFO
-	for (rti = rainfo->route.next; rti != &rainfo->route; rti = rti->next) {
-		u_int8_t psize = (rti->prefixlen + 0x3f) >> 6;
+	TAILQ_FOREACH(rti, &rainfo->route, next) {
+		uint8_t psize = (rti->prefixlen + 0x3f) >> 6;
 
 		ndopt_rti = (struct nd_opt_route_info *)buf;
 		ndopt_rti->nd_opt_rti_type = ND_OPT_ROUTE_INFO;
@@ -1057,9 +1152,41 @@
 		memcpy(ndopt_rti + 1, &rti->prefix, psize * 8);
 		buf += sizeof(struct nd_opt_route_info) + psize * 8;
 	}
-#endif
 
-	return;
+	TAILQ_FOREACH(rdns, &rainfo->rdnss, next) {
+		ndopt_rdnss = (struct nd_opt_rdnss *)buf;
+		ndopt_rdnss->nd_opt_rdnss_type = ND_OPT_RDNSS;
+		ndopt_rdnss->nd_opt_rdnss_len = 1;
+		ndopt_rdnss->nd_opt_rdnss_reserved = 0;
+		ndopt_rdnss->nd_opt_rdnss_lifetime = htonl(rdns->lifetime);
+		buf += sizeof(*ndopt_rdnss);
+	
+		TAILQ_FOREACH(rdnsa, &rdns->list, next) {
+			memcpy(buf, &rdnsa->addr, sizeof(rdnsa->addr));
+			ndopt_rdnss->nd_opt_rdnss_len += 2;
+			buf += sizeof(rdnsa->addr);
+		}
+	}
+
+	TAILQ_FOREACH(dnsl, &rainfo->dnssl, next) {
+		ndopt_dnssl = (struct nd_opt_dnssl *)buf;
+		ndopt_dnssl->nd_opt_dnssl_type = ND_OPT_DNSSL;
+		ndopt_dnssl->nd_opt_dnssl_len = 0;
+		ndopt_dnssl->nd_opt_dnssl_reserved = 0;
+		ndopt_dnssl->nd_opt_dnssl_lifetime = htonl(dnsl->lifetime);
+		buf += sizeof(*ndopt_dnssl);
+	
+		TAILQ_FOREACH(dnsd, &dnsl->list, next) {
+			memcpy(buf, dnsd->domain, dnsd->len);
+			buf += dnsd->len;
+		}
+		/* Ensure our length is padded correctly */
+		len = buf - (char *)ndopt_dnssl;
+		plen = len % 8 ? 8 - len % 8 : 0;
+		memset(buf, 0, plen);
+		buf += plen;
+		ndopt_dnssl->nd_opt_dnssl_len = (len + plen) / 8;
+	}
 }
 
 static int

cvs diff -r1.8 -r1.9 src/usr.sbin/rtadvd/dump.c (expand / switch to context diff)
--- src/usr.sbin/rtadvd/dump.c 2008/12/29 04:01:21 1.8
+++ src/usr.sbin/rtadvd/dump.c 2011/12/10 19:14:29 1.9
@@ -1,4 +1,4 @@
-/*	$NetBSD: dump.c,v 1.8 2008/12/29 04:01:21 christos Exp $	*/
+/*	$NetBSD: dump.c,v 1.9 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: dump.c,v 1.34 2004/06/14 05:35:59 itojun Exp $	*/
 
 /*
@@ -59,12 +59,10 @@
 
 static FILE *fp;
 
-extern struct rainfo *ralist;
+static char *ether_str(struct sockaddr_dl *);
+static void if_dump(void);
 
-static char *ether_str __P((struct sockaddr_dl *));
-static void if_dump __P((void));
-
-static char *rtpref_str[] = {
+static const char *rtpref_str[] = {
 	"medium",		/* 00 */
 	"high",			/* 01 */
 	"rsv",			/* 10 */
@@ -72,8 +70,7 @@
 };
 
 static char *
-ether_str(sdl)
-	struct sockaddr_dl *sdl;
+ether_str(struct sockaddr_dl *sdl)
 {
 	static char hbuf[NI_MAXHOST];
 
@@ -88,19 +85,21 @@
 }
 
 static void
-if_dump()
+if_dump(void)
 {
 	struct rainfo *rai;
 	struct prefix *pfx;
-#ifdef ROUTEINFO
 	struct rtinfo *rti;
-#endif
+	struct rdnss *rdns;
+	struct rdnss_addr *rdnsa;
+	struct dnssl *dnsl;
+	struct dnssl_domain *dnsd;
+	char *p, len;
 	char prefixbuf[INET6_ADDRSTRLEN];
-	int first;
 	struct timeval now;
 
 	gettimeofday(&now, NULL); /* XXX: unused in most cases */
-	for (rai = ralist; rai; rai = rai->next) {
+	TAILQ_FOREACH(rai, &ralist, next) {
 		fprintf(fp, "%s:\n", rai->ifname);
 
 		fprintf(fp, "  Status: %s\n",
@@ -151,14 +150,11 @@
 			"CurHopLimit: %d\n", rai->reachabletime,
 			rai->retranstimer, rai->hoplimit);
 		if (rai->clockskew)
-			fprintf(fp, "  Clock skew: %ldsec\n",
+			fprintf(fp, "  Clock skew: %dsec\n",
 			    rai->clockskew);
-		for (first = 1, pfx = rai->prefix.next; pfx != &rai->prefix;
-		     pfx = pfx->next) {
-			if (first) {
+		TAILQ_FOREACH(pfx, &rai->prefix, next) {
+			if (pfx == TAILQ_FIRST(&rai->prefix))
 				fprintf(fp, "  Prefixes:\n");
-				first = 0;
-			}
 			fprintf(fp, "    %s/%d(",
 			    inet_ntop(AF_INET6, &pfx->prefix, prefixbuf,
 			    sizeof(prefixbuf)), pfx->prefixlen);
@@ -210,13 +206,10 @@
 			}
 			fprintf(fp, ")\n");
 		}
-#ifdef ROUTEINFO
-		for (first = 1, rti = rai->route.next; rti != &rai->route;
-		     rti = rti->next) {
-			if (first) {
+
+		TAILQ_FOREACH(rti, &rai->route, next) {
+			if (rti == TAILQ_FIRST(&rai->route))
 				fprintf(fp, "  Route Information:\n");
-				first = 0;
-			}
 			fprintf(fp, "    %s/%d (",
 				inet_ntop(AF_INET6, &rti->prefix,
 					  prefixbuf, sizeof(prefixbuf)),
@@ -229,13 +222,46 @@
 				fprintf(fp, "lifetime: %ld", (long)rti->ltime);
 			fprintf(fp, ")\n");
 		}
-#endif
+
+		TAILQ_FOREACH(rdns, &rai->rdnss, next) {
+			fprintf(fp, "  Recursive DNS Servers:\n");
+			if (rdns->lifetime == ND6_INFINITE_LIFETIME)
+				fprintf(fp, "    lifetime: infinity\n");
+			else
+				fprintf(fp, "    lifetime: %ld\n",
+				    (long)rdns->lifetime);
+			TAILQ_FOREACH(rdnsa, &rdns->list, next)
+				fprintf(fp, "    %s\n",
+				    inet_ntop(AF_INET6, &rdnsa->addr,
+				    prefixbuf, sizeof(prefixbuf)));
+		}
+
+		TAILQ_FOREACH(dnsl, &rai->dnssl, next) {
+			fprintf(fp, "  DNS Search List:\n");
+			if (dnsl->lifetime == ND6_INFINITE_LIFETIME)
+				fprintf(fp, "    lifetime: infinity\n");
+			else
+				fprintf(fp, "    lifetime: %ld\n",
+				    (long)dnsl->lifetime);
+			TAILQ_FOREACH(dnsd, &dnsl->list, next) {
+				fprintf(fp, "    ");
+				for (p = dnsd->domain, len = *p++;
+				    len != 0;
+				    len = *p++)
+				{
+					if (p != dnsd->domain)
+					    fputc('.', fp);
+					while(len-- != 0)	
+					    fputc(*p++, fp);
+				}
+				fputc('\n', fp);
+			}
+		}
 	}
 }
 
 void
-rtadvd_dump_file(dumpfile)
-	char *dumpfile;
+rtadvd_dump_file(const char *dumpfile)
 {
 	syslog(LOG_DEBUG, "<%s> dump current status to %s", __func__,
 	    dumpfile);

cvs diff -r1.1 -r1.2 src/usr.sbin/rtadvd/dump.h (expand / switch to context diff)
--- src/usr.sbin/rtadvd/dump.h 2000/05/23 11:37:58 1.1
+++ src/usr.sbin/rtadvd/dump.h 2011/12/10 19:14:29 1.2
@@ -1,4 +1,4 @@
-/*	$NetBSD: dump.h,v 1.1 2000/05/23 11:37:58 itojun Exp $	*/
+/*	$NetBSD: dump.h,v 1.2 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: dump.h,v 1.1 2000/05/23 11:31:26 itojun Exp $	*/
 
 /*
@@ -30,4 +30,4 @@
  * SUCH DAMAGE.
  */
 
-extern void rtadvd_dump_file __P((char *));
+extern void rtadvd_dump_file(const char *);

cvs diff -r1.18 -r1.19 src/usr.sbin/rtadvd/if.c (expand / switch to context diff)
--- src/usr.sbin/rtadvd/if.c 2006/03/05 23:47:08 1.18
+++ src/usr.sbin/rtadvd/if.c 2011/12/10 19:14:29 1.19
@@ -1,4 +1,4 @@
-/*	$NetBSD: if.c,v 1.18 2006/03/05 23:47:08 rpaulo Exp $	*/
+/*	$NetBSD: if.c,v 1.19 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: if.c,v 1.36 2004/11/30 22:32:01 suz Exp $	*/
 
 /*
@@ -54,7 +54,7 @@
 	(((a) & ((size)-1)) ? (1 + ((a) | ((size)-1))) : (a))
 
 #define NEXT_SA(ap) (ap) = (struct sockaddr *) \
-	((caddr_t)(ap) + ((ap)->sa_len ? ROUNDUP((ap)->sa_len,\
+	((char *)(ap) + ((ap)->sa_len ? ROUNDUP((ap)->sa_len,\
 						 sizeof(u_long)) :\
 			  			 sizeof(u_long)))
 
@@ -63,9 +63,9 @@
 size_t ifblock_size;
 char *ifblock;
 
-static void get_iflist __P((char **buf, size_t *size));
-static void parse_iflist __P((struct if_msghdr ***ifmlist_p, char *buf,
-		       size_t bufsize));
+static void get_iflist(char **buf, size_t *size);
+static void parse_iflist(struct if_msghdr ***ifmlist_p, char *buf,
+		       size_t bufsize);
 
 static void
 get_rtaddrs(int addrs, struct sockaddr *sa, struct sockaddr **rti_info)
@@ -140,7 +140,7 @@
 		ifr.ifr_addr.sa_family = AF_INET6;
 		strncpy(ifr.ifr_name, name,
 			sizeof(ifr.ifr_name));
-		if (ioctl(s, SIOCGIFMTU, (caddr_t)&ifr) < 0) {
+		if (ioctl(s, SIOCGIFMTU, &ifr) < 0) {
 			close(s);
 			return(0);
 		}
@@ -167,7 +167,7 @@
 	}
 
 	if_indextoname(ifindex, ifr.ifr_name);
-	if (ioctl(s, SIOCGIFFLAGS, (caddr_t)&ifr) < 0) {
+	if (ioctl(s, SIOCGIFFLAGS, &ifr) < 0) {
 		syslog(LOG_ERR, "<%s> ioctl:SIOCGIFFLAGS: failed for %s",
 		       __func__, ifr.ifr_name);
 		close(s);
@@ -355,19 +355,19 @@
 {
 	struct rt_msghdr *rtm = (struct rt_msghdr *)buf;
 	struct sockaddr *sa, *rti_info[RTAX_MAX];
-	u_char *p, *lim;
+	unsigned char *p, *lim;
 	
 	sa = (struct sockaddr *)(rtm + 1);
 	get_rtaddrs(rtm->rtm_addrs, sa, rti_info);
 	sa = rti_info[RTAX_NETMASK];
 
-	p = (u_char *)(&SIN6(sa)->sin6_addr);
-	lim = (u_char *)sa + sa->sa_len;
+	p = (unsigned char *)(&SIN6(sa)->sin6_addr);
+	lim = (unsigned char *)sa + sa->sa_len;
 	return prefixlen(p, lim);
 }
 
 int
-prefixlen(u_char *p, u_char *lim)
+prefixlen(const unsigned char *p, const unsigned char *lim)
 {
 	int masklen;
 

cvs diff -r1.7 -r1.8 src/usr.sbin/rtadvd/if.h (expand / switch to context diff)
--- src/usr.sbin/rtadvd/if.h 2006/03/05 23:47:08 1.7
+++ src/usr.sbin/rtadvd/if.h 2011/12/10 19:14:29 1.8
@@ -1,4 +1,4 @@
-/*	$NetBSD: if.h,v 1.7 2006/03/05 23:47:08 rpaulo Exp $	*/
+/*	$NetBSD: if.h,v 1.8 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: if.h,v 1.12 2003/09/21 07:17:03 itojun Exp $	*/
 
 /*
@@ -37,21 +37,21 @@
 extern char *ifblock;
 
 struct nd_opt_hdr;
-struct sockaddr_dl *if_nametosdl __P((char *));
+struct sockaddr_dl *if_nametosdl(char *);
-int if_getmtu __P((char *));
+int if_getmtu(char *);
-int if_getflags __P((int, int));
+int if_getflags(int, int);
-int lladdropt_length __P((struct sockaddr_dl *));
+int lladdropt_length(struct sockaddr_dl *);
-void lladdropt_fill __P((struct sockaddr_dl *, struct nd_opt_hdr *));
+void lladdropt_fill(struct sockaddr_dl *, struct nd_opt_hdr *);
-char *get_next_msg __P((char *, char *, int, size_t *, int));
+char *get_next_msg(char *, char *, int, size_t *, int);
-struct in6_addr *get_addr __P((char *));
+struct in6_addr *get_addr(char *);
-int get_rtm_ifindex __P((char *));
+int get_rtm_ifindex(char *);
-int get_ifm_ifindex __P((char *));
+int get_ifm_ifindex(char *);
-int get_ifam_ifindex __P((char *));
+int get_ifam_ifindex(char *);
-int get_ifm_flags __P((char *));
+int get_ifm_flags(char *);
-int get_prefixlen __P((char *));
+int get_prefixlen(char *);
-int prefixlen __P((u_char *, u_char *));
+int prefixlen(const unsigned char *, const unsigned char *);
-int rtmsg_type __P((char *));
+int rtmsg_type(char *);
-int ifmsg_type __P((char *));
+int ifmsg_type(char *);
-int rtmsg_len __P((char *));
+int rtmsg_len(char *);
-int ifmsg_len __P((char *));
+int ifmsg_len(char *);
-void init_iflist __P((void));
+void init_iflist(void);

cvs diff -r1.13 -r1.14 src/usr.sbin/rtadvd/Attic/rrenum.c (expand / switch to context diff)
--- src/usr.sbin/rtadvd/Attic/rrenum.c 2006/05/11 08:35:47 1.13
+++ src/usr.sbin/rtadvd/Attic/rrenum.c 2011/12/10 19:14:29 1.14
@@ -1,4 +1,4 @@
-/*	$NetBSD: rrenum.c,v 1.13 2006/05/11 08:35:47 mrg Exp $	*/
+/*	$NetBSD: rrenum.c,v 1.14 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: rrenum.c,v 1.14 2004/06/14 05:36:00 itojun Exp $	*/
 
 /*
@@ -160,7 +160,7 @@
 		irr->irr_useprefix.sin6_len = 0; /* let it mean, no addition */
 		irr->irr_useprefix.sin6_family = 0;
 		irr->irr_useprefix.sin6_addr = in6addr_any;
-		if (ioctl(s, rrcmd2pco[rpm->rpm_code], (caddr_t)irr) < 0 &&
+		if (ioctl(s, rrcmd2pco[rpm->rpm_code], irr) < 0 &&
 		    errno != EADDRNOTAVAIL)
 			syslog(LOG_ERR, "<%s> ioctl: %s", __func__,
 			       strerror(errno));
@@ -192,7 +192,7 @@
 		irr->irr_useprefix.sin6_family = AF_INET6;
 		irr->irr_useprefix.sin6_addr = rpu->rpu_prefix;
 
-		if (ioctl(s, rrcmd2pco[rpm->rpm_code], (caddr_t)irr) < 0 &&
+		if (ioctl(s, rrcmd2pco[rpm->rpm_code], irr) < 0 &&
 		    errno != EADDRNOTAVAIL)
 			syslog(LOG_ERR, "<%s> ioctl: %s", __func__,
 			       strerror(errno));
@@ -205,8 +205,7 @@
 			if ((rai = if_indextorainfo(ifindex)) == NULL)
 				continue; /* non-advertising IF */
 
-			for (pp = rai->prefix.next; pp != &rai->prefix;
-			     pp = pp->next) {
+			TAILQ_FOREACH(pp, &rai->prefix, next) {
 				struct timeval now;
 
 				if (prefix_match(&pp->prefix, pp->prefixlen,
@@ -288,7 +287,7 @@
  * return 0 on success, 1 on failure
  */
 static int
-do_rr(int len, struct icmp6_router_renum *rr)
+do_rr(size_t len, struct icmp6_router_renum *rr)
 {
 	struct rr_pco_match *rpm;
 	char *cp, *lim;
@@ -301,12 +300,12 @@
 	init_iflist();
 
 	while (cp < lim) {
-		int rpmlen;
+		size_t rpmlen;
 
 		rpm = (struct rr_pco_match *)cp;
 		if (len < sizeof(struct rr_pco_match)) {
 		    tooshort:
-			syslog(LOG_ERR, "<%s> pkt too short. left len = %d. "
+			syslog(LOG_ERR, "<%s> pkt too short. left len = %zd. "
 			       "gabage at end of pkt?", __func__, len);
 			return 1;
 		}
@@ -332,8 +331,8 @@
  * return 0 on success, 1 on failure
  */
 static int
-rr_command_check(int len, struct icmp6_router_renum *rr, struct in6_addr *from,
-		 struct in6_addr *dst)
+rr_command_check(size_t len, struct icmp6_router_renum *rr,
+    struct in6_addr *from, struct in6_addr *dst)
 {
 	char ntopbuf[INET6_ADDRSTRLEN];
 
@@ -341,7 +340,7 @@
 	/* rr_command length check */
 	if (len < (sizeof(struct icmp6_router_renum) +
 		   sizeof(struct rr_pco_match))) {
-		syslog(LOG_ERR,	"<%s> rr_command len %d is too short",
+		syslog(LOG_ERR,	"<%s> rr_command len %zd is too short",
 		       __func__, len);
 		return 1;
 	}
@@ -359,7 +358,7 @@
 	if (rro.rro_seqnum > rr->rr_seqnum) {
 		syslog(LOG_WARNING,
 		       "<%s> rcvd old seqnum %d from %s",
-		       __func__, (u_int32_t)ntohl(rr->rr_seqnum),
+		       __func__, (uint32_t)ntohl(rr->rr_seqnum),
 		       inet_ntop(AF_INET6, from, ntopbuf, INET6_ADDRSTRLEN));
 		return 1;
 	}
@@ -415,7 +414,7 @@
 }
 
 void
-rr_input(int len, struct icmp6_router_renum *rr, struct in6_pktinfo *pi,
+rr_input(size_t len, struct icmp6_router_renum *rr, struct in6_pktinfo *pi,
 	 struct sockaddr_in6 *from, struct in6_addr *dst)
 {
 	char ntopbuf[2][INET6_ADDRSTRLEN], ifnamebuf[IFNAMSIZ];
@@ -431,7 +430,7 @@
 	/* packet validation based on Section 4.1 of RFC2894 */
 	if (len < sizeof(struct icmp6_router_renum)) {
 		syslog(LOG_NOTICE,
-		       "<%s>: RR short message (size %d) from %s to %s on %s",
+		       "<%s>: RR short message (size %zd) from %s to %s on %s",
 		       __func__, len,
 		       inet_ntop(AF_INET6, &from->sin6_addr,
 				 ntopbuf[0], INET6_ADDRSTRLEN),
@@ -449,7 +448,9 @@
 	 * check multicast destinations only.
 	 */
 	if (IN6_IS_ADDR_MULTICAST(&pi->ipi6_addr) &&
-	    !IN6_ARE_ADDR_EQUAL(&in6a_site_allrouters, &pi->ipi6_addr)) {
+	    !IN6_ARE_ADDR_EQUAL(&sin6_sitelocal_allrouters.sin6_addr,
+	    &pi->ipi6_addr))
+	{
 		syslog(LOG_NOTICE,
 		       "<%s>: RR message with invalid destination (%s) "
 		       "from %s on %s",

cvs diff -r1.4 -r1.5 src/usr.sbin/rtadvd/Attic/rrenum.h (expand / switch to context diff)
--- src/usr.sbin/rtadvd/Attic/rrenum.h 2001/01/21 15:39:33 1.4
+++ src/usr.sbin/rtadvd/Attic/rrenum.h 2011/12/10 19:14:29 1.5
@@ -1,4 +1,4 @@
-/*	$NetBSD: rrenum.h,v 1.4 2001/01/21 15:39:33 itojun Exp $	*/
+/*	$NetBSD: rrenum.h,v 1.5 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: rrenum.h,v 1.3 2001/01/21 15:37:14 itojun Exp $	*/
 
 /*
@@ -30,5 +30,5 @@
  * SUCH DAMAGE.
  */
 
-void rr_input __P((int, struct icmp6_router_renum *, struct in6_pktinfo *,
+void rr_input(size_t, struct icmp6_router_renum *, struct in6_pktinfo *,
-	struct sockaddr_in6 *, struct in6_addr *));
+	struct sockaddr_in6 *, struct in6_addr *);

cvs diff -r1.35 -r1.36 src/usr.sbin/rtadvd/rtadvd.c (expand / switch to context diff)
--- src/usr.sbin/rtadvd/rtadvd.c 2009/04/19 08:40:48 1.35
+++ src/usr.sbin/rtadvd/rtadvd.c 2011/12/10 19:14:29 1.36
@@ -1,4 +1,4 @@
-/*	$NetBSD: rtadvd.c,v 1.35 2009/04/19 08:40:48 lukem Exp $	*/
+/*	$NetBSD: rtadvd.c,v 1.36 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: rtadvd.c,v 1.92 2005/10/17 14:40:02 suz Exp $	*/
 
 /*
@@ -66,9 +66,9 @@
 #include "dump.h"
 
 struct msghdr rcvmhdr;
-static u_char *rcvcmsgbuf;
+static unsigned char *rcvcmsgbuf;
 static size_t rcvcmsgbuflen;
-static u_char *sndcmsgbuf = NULL;
+static unsigned char *sndcmsgbuf = NULL;
 static size_t sndcmsgbuflen;
 volatile sig_atomic_t do_dump;
 volatile sig_atomic_t do_die;
@@ -76,9 +76,7 @@
 struct iovec rcviov[2];
 struct iovec sndiov[2];
 struct sockaddr_in6 rcvfrom;
-struct sockaddr_in6 sin6_allnodes = {sizeof(sin6_allnodes), AF_INET6};
-struct in6_addr in6a_site_allrouters;
-static char *dumpfilename = "/var/run/rtadvd.dump"; /* XXX: should be configurable */
+static const char *dumpfilename = "/var/run/rtadvd.dump"; /* XXX configurable */
 static char *mcastif;
 int sock;
 int rtsock = -1;
@@ -87,9 +85,10 @@
 
 char *conffile = NULL;
 
-struct rainfo *ralist = NULL;
+struct ralist_head_t ralist = TAILQ_HEAD_INITIALIZER(ralist);
+
 struct nd_optlist {
-	struct nd_optlist *next;
+	TAILQ_ENTRY(nd_optlist) next;
 	struct nd_opt_hdr *opt;
 };
 union nd_opts {
@@ -101,7 +100,7 @@
 		struct nd_opt_prefix_info *pi;
 		struct nd_opt_rd_hdr *rh;
 		struct nd_opt_mtu *mtu;
-		struct nd_optlist *list;
+		TAILQ_HEAD(, nd_optlist) list;
 	} nd_opt_each;
 };
 #define nd_opts_src_lladdr	nd_opt_each.src_lladdr
@@ -111,41 +110,61 @@
 #define nd_opts_mtu		nd_opt_each.mtu
 #define nd_opts_list		nd_opt_each.list
 
-#define NDOPT_FLAG_SRCLINKADDR 0x1
-#define NDOPT_FLAG_TGTLINKADDR 0x2
-#define NDOPT_FLAG_PREFIXINFO 0x4
-#define NDOPT_FLAG_RDHDR 0x8
-#define NDOPT_FLAG_MTU 0x10
+#define NDOPT_FLAG_SRCLINKADDR	(1 << 0)
+#define NDOPT_FLAG_TGTLINKADDR	(1 << 1)
+#define NDOPT_FLAG_PREFIXINFO	(1 << 2)
+#define NDOPT_FLAG_RDHDR	(1 << 3)
+#define NDOPT_FLAG_MTU		(1 << 4)
+#define NDOPT_FLAG_RDNSS	(1 << 5)
+#define NDOPT_FLAG_DNSSL	(1 << 6)
 
-u_int32_t ndopt_flags[] = {
-	0, NDOPT_FLAG_SRCLINKADDR, NDOPT_FLAG_TGTLINKADDR,
-	NDOPT_FLAG_PREFIXINFO, NDOPT_FLAG_RDHDR, NDOPT_FLAG_MTU,
+uint32_t ndopt_flags[] = {
+	[ND_OPT_SOURCE_LINKADDR] =	NDOPT_FLAG_SRCLINKADDR,
+	[ND_OPT_TARGET_LINKADDR] =	NDOPT_FLAG_TGTLINKADDR,
+	[ND_OPT_PREFIX_INFORMATION] =	NDOPT_FLAG_PREFIXINFO,
+	[ND_OPT_REDIRECTED_HEADER] =	NDOPT_FLAG_RDHDR,
+	[ND_OPT_MTU] =			NDOPT_FLAG_MTU,
+	[ND_OPT_RDNSS] =		NDOPT_FLAG_RDNSS,
+	[ND_OPT_DNSSL] =		NDOPT_FLAG_DNSSL,
 };
 
-int main __P((int, char *[]));
-static void set_die __P((int));
-static void die __P((void));
-static void sock_open __P((void));
-static void rtsock_open __P((void));
-static void rtadvd_input __P((void));
-static void rs_input __P((int, struct nd_router_solicit *,
-			  struct in6_pktinfo *, struct sockaddr_in6 *));
-static void ra_input __P((int, struct nd_router_advert *,
-			  struct in6_pktinfo *, struct sockaddr_in6 *));
-static int prefix_check __P((struct nd_opt_prefix_info *, struct rainfo *,
-			     struct sockaddr_in6 *));
-static int nd6_options __P((struct nd_opt_hdr *, int,
-			    union nd_opts *, u_int32_t));
-static void free_ndopts __P((union nd_opts *));
-static void ra_output __P((struct rainfo *));
-static void rtmsg_input __P((void));
-static void rtadvd_set_dump_file __P((int));
-static void set_short_delay __P((struct rainfo *));
+struct sockaddr_in6 sin6_linklocal_allnodes = {
+	.sin6_len =	sizeof(sin6_linklocal_allnodes),
+	.sin6_family =	AF_INET6,
+	.sin6_addr =	IN6ADDR_LINKLOCAL_ALLNODES_INIT,
+};
+struct sockaddr_in6 sin6_linklocal_allrouters = {
+	.sin6_len =	sizeof(sin6_linklocal_allrouters),
+	.sin6_family =	AF_INET6,
+	.sin6_addr =	IN6ADDR_LINKLOCAL_ALLROUTERS_INIT,
+};
+struct sockaddr_in6 sin6_sitelocal_allrouters = {
+	.sin6_len =	sizeof(sin6_sitelocal_allrouters),
+	.sin6_family =	AF_INET6,
+	.sin6_addr =	IN6ADDR_SITELOCAL_ALLROUTERS_INIT,
+};
 
+int main(int, char *[]);
+static void set_die(int);
+static void die(void);
+static void sock_open(void);
+static void rtsock_open(void);
+static void rtadvd_input(void);
+static void rs_input(int, struct nd_router_solicit *,
+    struct in6_pktinfo *, struct sockaddr_in6 *);
+static void ra_input(int, struct nd_router_advert *,
+    struct in6_pktinfo *, struct sockaddr_in6 *);
+static int prefix_check(struct nd_opt_prefix_info *, struct rainfo *,
+    struct sockaddr_in6 *);
+static int nd6_options(struct nd_opt_hdr *, int, union nd_opts *, uint32_t);
+static void free_ndopts(union nd_opts *);
+static void ra_output(struct rainfo *);
+static void rtmsg_input(void);
+static void rtadvd_set_dump_file(int);
+static void set_short_delay(struct rainfo *);
+
 int
-main(argc, argv)
-	int argc;
-	char *argv[];
+main(int argc, char *argv[])
 {
 	struct pollfd set[2];
 	struct timeval *timeout;
@@ -212,11 +231,6 @@
 	while (argc--)
 		getconfig(*argv++);
 
-	if (inet_pton(AF_INET6, ALLNODES, &sin6_allnodes.sin6_addr) != 1) {
-		fprintf(stderr, "fatal: inet_pton failed\n");
-		exit(1);
-	}
-
 	if (!fflag)
 		daemon(1, 0);
 
@@ -286,21 +300,19 @@
 }
 
 static void
-rtadvd_set_dump_file(sig)
-	int sig;
+rtadvd_set_dump_file(int sig)
 {
 	do_dump = 1;
 }
 
 static void
-set_die(sig)
-	int sig;
+set_die(int sig)
 {
 	do_die = 1;
 }
 
 static void
-die()
+die(void)
 {
 	struct rainfo *ra;
 	int i;
@@ -311,12 +323,12 @@
 		    __func__);
 	}
 
-	for (ra = ralist; ra; ra = ra->next) {
+	TAILQ_FOREACH(ra, &ralist, next) {
 		ra->lifetime = 0;
 		make_packet(ra);
 	}
 	for (i = 0; i < retrans; i++) {
-		for (ra = ralist; ra; ra = ra->next)
+		TAILQ_FOREACH(ra, &ralist, next)
 			ra_output(ra);
 		sleep(MIN_DELAY_BETWEEN_RAS);
 	}
@@ -325,7 +337,7 @@
 }
 
 static void
-rtmsg_input()
+rtmsg_input(void)
 {
 	int n, type, ifindex = 0, plen;
 	size_t len;
@@ -545,9 +557,9 @@
 }
 
 void
-rtadvd_input()
+rtadvd_input(void)
 {
-	int i;
+	ssize_t i;
 	int *hlimp = NULL;
 #ifdef OLDRAWSOCKET
 	struct ip6_hdr *ip;
@@ -610,7 +622,7 @@
 	}
 
 #ifdef OLDRAWSOCKET
-	if (i < sizeof(struct ip6_hdr) + sizeof(struct icmp6_hdr)) {
+	if ((size_t)i < sizeof(struct ip6_hdr) + sizeof(struct icmp6_hdr)) {
 		syslog(LOG_ERR,
 		       "<%s> packet size(%d) is too short",
 		       __func__, i);
@@ -620,9 +632,9 @@
 	ip = (struct ip6_hdr *)rcvmhdr.msg_iov[0].iov_base;
 	icp = (struct icmp6_hdr *)(ip + 1); /* XXX: ext. hdr? */
 #else
-	if (i < sizeof(struct icmp6_hdr)) {
+	if ((size_t)i < sizeof(struct icmp6_hdr)) {
 		syslog(LOG_ERR,
-		       "<%s> packet size(%d) is too short",
+		       "<%s> packet size(%zd) is too short",
 		       __func__, i);
 		return;
 	}
@@ -657,10 +669,10 @@
 			    if_indextoname(pi->ipi6_ifindex, ifnamebuf));
 			return;
 		}
-		if (i < sizeof(struct nd_router_solicit)) {
+		if ((size_t)i < sizeof(struct nd_router_solicit)) {
 			syslog(LOG_NOTICE,
 			    "<%s> RS from %s on %s does not have enough "
-			    "length (len = %d)",
+			    "length (len = %zd)",
 			    __func__,
 			    inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf,
 			    INET6_ADDRSTRLEN),
@@ -694,10 +706,10 @@
 			    if_indextoname(pi->ipi6_ifindex, ifnamebuf));
 			return;
 		}
-		if (i < sizeof(struct nd_router_advert)) {
+		if ((size_t)i < sizeof(struct nd_router_advert)) {
 			syslog(LOG_NOTICE,
 			    "<%s> RA from %s on %s does not have enough "
-			    "length (len = %d)",
+			    "length (len = %zd)",
 			    __func__,
 			    inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf,
 			    INET6_ADDRSTRLEN),
@@ -749,6 +761,7 @@
 
 	/* ND option check */
 	memset(&ndopts, 0, sizeof(ndopts));
+	TAILQ_INIT(&ndopts.nd_opts_list);
 	if (nd6_options((struct nd_opt_hdr *)(rs + 1),
 			len - sizeof(struct nd_router_solicit),
 			&ndopts, NDOPT_FLAG_SRCLINKADDR)) {
@@ -776,11 +789,9 @@
 		goto done;
 	}
 
-	ra = ralist;
-	while (ra != NULL) {
+	TAILQ_FOREACH(ra, &ralist, next) {
 		if (pi->ipi6_ifindex == ra->ifindex)
 			break;
-		ra = ra->next;
 	}
 	if (ra == NULL) {
 		syslog(LOG_INFO,
@@ -798,13 +809,12 @@
 	 */
 
 	/* record sockaddr waiting for RA, if possible */
-	sol = (struct soliciter *)malloc(sizeof(*sol));
+	sol = malloc(sizeof(*sol));
 	if (sol) {
 		sol->addr = *from;
 		/* XXX RFC2553 need clarification on flowinfo */
 		sol->addr.sin6_flowinfo = 0;
-		sol->next = ra->soliciter;
-		ra->soliciter = sol;
+		TAILQ_INSERT_HEAD(&ra->soliciter, sol, next);
 	}
 
 	/*
@@ -822,8 +832,7 @@
 }
 
 static void
-set_short_delay(rai)
-	struct rainfo *rai;
+set_short_delay(struct rainfo *rai)
 {
 	long delay;	/* must not be greater than 1000000 */
 	struct timeval interval, now, min_delay, tm_tmp, *rest;
@@ -870,8 +879,9 @@
 	struct rainfo *rai;
 	char ntopbuf[INET6_ADDRSTRLEN], ifnamebuf[IFNAMSIZ];
 	union nd_opts ndopts;
-	char *on_off[] = {"OFF", "ON"};
-	u_int32_t reachabletime, retranstimer, mtu;
+	const char *on_off[] = {"OFF", "ON"};
+	uint32_t reachabletime, retranstimer, mtu;
+	struct nd_optlist *optp;
 	int inconsistent = 0;
 
 	syslog(LOG_DEBUG,
@@ -880,19 +890,22 @@
 	       inet_ntop(AF_INET6, &from->sin6_addr,
 			 ntopbuf, INET6_ADDRSTRLEN),
 	       if_indextoname(pi->ipi6_ifindex, ifnamebuf));
-	
+
 	/* ND option check */
 	memset(&ndopts, 0, sizeof(ndopts));
+	TAILQ_INIT(&ndopts.nd_opts_list);
 	if (nd6_options((struct nd_opt_hdr *)(ra + 1),
-			len - sizeof(struct nd_router_advert),
-			&ndopts, NDOPT_FLAG_SRCLINKADDR |
-			NDOPT_FLAG_PREFIXINFO | NDOPT_FLAG_MTU)) {
+	    len - sizeof(struct nd_router_advert),
+	    &ndopts, NDOPT_FLAG_SRCLINKADDR |
+	    NDOPT_FLAG_PREFIXINFO | NDOPT_FLAG_MTU |
+	    NDOPT_FLAG_RDNSS | NDOPT_FLAG_DNSSL))
+	{
 		syslog(LOG_INFO,
-		       "<%s> ND option check failed for an RA from %s on %s",
-		       __func__,
-		       inet_ntop(AF_INET6, &from->sin6_addr,
-				 ntopbuf, INET6_ADDRSTRLEN),
-		       if_indextoname(pi->ipi6_ifindex, ifnamebuf));
+		    "<%s> ND option check failed for an RA from %s on %s",
+		    __func__,
+		    inet_ntop(AF_INET6, &from->sin6_addr,
+		        ntopbuf, INET6_ADDRSTRLEN),
+		        if_indextoname(pi->ipi6_ifindex, ifnamebuf));
 		return;
 	}
 
@@ -999,21 +1012,14 @@
 		}
 	}
 	/* Preferred and Valid Lifetimes for prefixes */
-	{
-		struct nd_optlist *optp = ndopts.nd_opts_list;
+	if (ndopts.nd_opts_pi)
+		if (prefix_check(ndopts.nd_opts_pi, rai, from))
+			inconsistent++;
+	TAILQ_FOREACH(optp, &ndopts.nd_opts_list, next)
+		if (prefix_check((struct nd_opt_prefix_info *)optp->opt,
+		    rai, from))
+			inconsistent++;
 
-		if (ndopts.nd_opts_pi) {
-			if (prefix_check(ndopts.nd_opts_pi, rai, from))
-				inconsistent++;
-		}
-		while (optp) {
-			if (prefix_check((struct nd_opt_prefix_info *)optp->opt,
-					 rai, from))
-				inconsistent++;
-			optp = optp->next;
-		}
-	}
-
 	if (inconsistent)
 		rai->rainconsistent++;
 	
@@ -1027,7 +1033,7 @@
 prefix_check(struct nd_opt_prefix_info *pinfo,
 	     struct rainfo *rai, struct sockaddr_in6 *from)
 {
-	u_int32_t preferred_time, valid_time;
+	uint32_t preferred_time, valid_time;
 	struct prefix *pp;
 	int inconsistent = 0;
 	char ntopbuf[INET6_ADDRSTRLEN], prefixbuf[INET6_ADDRSTRLEN];
@@ -1156,9 +1162,9 @@
 {
 	struct prefix *pp;
 	int bytelen, bitlen;
-	u_char bitmask;
+	unsigned char bitmask;
 
-	for (pp = rai->prefix.next; pp != &rai->prefix; pp = pp->next) {
+	TAILQ_FOREACH(pp, &rai->prefix, next) {
 		if (plen != pp->prefixlen)
 			continue;
 		bytelen = plen / 8;
@@ -1182,7 +1188,7 @@
 	     struct in6_addr *p1, int plen1)
 {
 	int bytelen, bitlen;
-	u_char bitmask;
+	unsigned char bitmask;
 
 	if (plen0 < plen1)
 		return(0);
@@ -1202,17 +1208,17 @@
 
 static int
 nd6_options(struct nd_opt_hdr *hdr, int limit,
-	    union nd_opts *ndopts, u_int32_t optflags)
+	    union nd_opts *ndopts, uint32_t optflags)
 {
 	int optlen = 0;
 
 	for (; limit > 0; limit -= optlen) {
-		if (limit < sizeof(struct nd_opt_hdr)) {
+		if ((size_t)limit < sizeof(struct nd_opt_hdr)) {
 			syslog(LOG_INFO, "<%s> short option header", __func__);
 			goto bad;
 		}
 
-		hdr = (struct nd_opt_hdr *)((caddr_t)hdr + optlen);
+		hdr = (struct nd_opt_hdr *)((char *)hdr + optlen);
 		if (hdr->nd_opt_len == 0) {
 			syslog(LOG_INFO,
 			    "<%s> bad ND option length(0) (type = %d)",
@@ -1225,7 +1231,9 @@
 			goto bad;
 		}
 
-		if (hdr->nd_opt_type > ND_OPT_MTU)
+		if (hdr->nd_opt_type > ND_OPT_MTU &&
+		    hdr->nd_opt_type != ND_OPT_RDNSS &&
+		    hdr->nd_opt_type != ND_OPT_DNSSL)
 		{
 			syslog(LOG_INFO, "<%s> unknown ND option(type %d)",
 			    __func__, hdr->nd_opt_type);
@@ -1278,9 +1286,8 @@
 				    __func__);
 				goto bad;
 			}
-			pfxlist->next = ndopts->nd_opts_list;
 			pfxlist->opt = hdr;
-			ndopts->nd_opts_list = pfxlist;
+			TAILQ_INSERT_TAIL(&ndopts->nd_opts_list, pfxlist, next);
 
 			break;
 		}
@@ -1300,28 +1307,27 @@
 static void
 free_ndopts(union nd_opts *ndopts)
 {
-	struct nd_optlist *opt = ndopts->nd_opts_list, *next;
+	struct nd_optlist *opt;
 
-	while (opt) {
-		next = opt->next;
+	while ((opt = TAILQ_FIRST(&ndopts->nd_opts_list)) != NULL) {
+		TAILQ_REMOVE(&ndopts->nd_opts_list, opt, next);
 		free(opt);
-		opt = next;
 	}
 }
 
 void
-sock_open()
+sock_open(void)
 {
 	struct icmp6_filter filt;
 	struct ipv6_mreq mreq;
-	struct rainfo *ra = ralist;
+	struct rainfo *ra;
 	int on;
 	/* XXX: should be max MTU attached to the node */
-	static u_char answer[1500];
+	static unsigned char answer[1500];
 
 	rcvcmsgbuflen = CMSG_SPACE(sizeof(struct in6_pktinfo)) +
 				CMSG_SPACE(sizeof(int));
-	rcvcmsgbuf = (u_char *)malloc(rcvcmsgbuflen);
+	rcvcmsgbuf = malloc(rcvcmsgbuflen);
 	if (rcvcmsgbuf == NULL) {
 		syslog(LOG_ERR, "<%s> not enough core", __func__);
 		exit(1);
@@ -1329,7 +1335,7 @@
 
 	sndcmsgbuflen = CMSG_SPACE(sizeof(struct in6_pktinfo)) + 
 				CMSG_SPACE(sizeof(int));
-	sndcmsgbuf = (u_char *)malloc(sndcmsgbuflen);
+	sndcmsgbuf = malloc(sndcmsgbuflen);
 	if (sndcmsgbuf == NULL) {
 		syslog(LOG_ERR, "<%s> not enough core", __func__);
 		exit(1);
@@ -1393,13 +1399,13 @@
 	 * join all routers multicast address on each advertising interface.
 	 */
 	if (inet_pton(AF_INET6, ALLROUTERS_LINK,
-		      &mreq.ipv6mr_multiaddr.s6_addr)
-	    != 1) {
+	    mreq.ipv6mr_multiaddr.s6_addr) != 1)
+	{
 		syslog(LOG_ERR, "<%s> inet_pton failed(library bug?)",
-		       __func__);
+		    __func__);
 		exit(1);
 	}
-	while (ra) {
+	TAILQ_FOREACH(ra, &ralist, next) {
 		mreq.ipv6mr_interface = ra->ifindex;
 		if (setsockopt(sock, IPPROTO_IPV6, IPV6_JOIN_GROUP, &mreq,
 			       sizeof(mreq)) < 0) {
@@ -1407,7 +1413,6 @@
 			       __func__, ra->ifname, strerror(errno));
 			exit(1);
 		}
-		ra = ra->next;
 	}
 
 	/*
@@ -1416,12 +1421,13 @@
 	 */
 	if (accept_rr) {
 		if (inet_pton(AF_INET6, ALLROUTERS_SITE,
-			      &in6a_site_allrouters) != 1) {
+		     mreq.ipv6mr_multiaddr.s6_addr) != 1)
+		{
 			syslog(LOG_ERR, "<%s> inet_pton failed(library bug?)",
-			       __func__);
+			    __func__);
 			exit(1);
 		}
-		mreq.ipv6mr_multiaddr = in6a_site_allrouters;
+		ra = TAILQ_FIRST(&ralist);
 		if (mcastif) {
 			if ((mreq.ipv6mr_interface = if_nametoindex(mcastif))
 			    == 0) {
@@ -1431,33 +1437,33 @@
 				exit(1);
 			}
 		} else
-			mreq.ipv6mr_interface = ralist->ifindex;
+			mreq.ipv6mr_interface = ra->ifindex;
 		if (setsockopt(sock, IPPROTO_IPV6, IPV6_JOIN_GROUP,
 			       &mreq, sizeof(mreq)) < 0) {
 			syslog(LOG_ERR,
 			       "<%s> IPV6_JOIN_GROUP(site) on %s: %s",
 			       __func__,
-			       mcastif ? mcastif : ralist->ifname,
+			       mcastif ? mcastif : ra->ifname,
 			       strerror(errno));
 			exit(1);
 		}
 	}
 	
 	/* initialize msghdr for receiving packets */
-	rcviov[0].iov_base = (caddr_t)answer;
+	rcviov[0].iov_base = answer;
 	rcviov[0].iov_len = sizeof(answer);
-	rcvmhdr.msg_name = (caddr_t)&rcvfrom;
+	rcvmhdr.msg_name = &rcvfrom;
 	rcvmhdr.msg_namelen = sizeof(rcvfrom);
 	rcvmhdr.msg_iov = rcviov;
 	rcvmhdr.msg_iovlen = 1;
-	rcvmhdr.msg_control = (caddr_t) rcvcmsgbuf;
+	rcvmhdr.msg_control = rcvcmsgbuf;
 	rcvmhdr.msg_controllen = rcvcmsgbuflen;
 
 	/* initialize msghdr for sending packets */
 	sndmhdr.msg_namelen = sizeof(struct sockaddr_in6);
 	sndmhdr.msg_iov = sndiov;
 	sndmhdr.msg_iovlen = 1;
-	sndmhdr.msg_control = (caddr_t)sndcmsgbuf;
+	sndmhdr.msg_control = (void *)sndcmsgbuf;
 	sndmhdr.msg_controllen = sndcmsgbuflen;
 	
 	return;
@@ -1465,7 +1471,7 @@
 
 /* open a routing socket to watch the routing table */
 static void
-rtsock_open()
+rtsock_open(void)
 {
 	if ((rtsock = socket(PF_ROUTE, SOCK_RAW, 0)) < 0) {
 		syslog(LOG_ERR,
@@ -1475,11 +1481,11 @@
 }
 
 struct rainfo *
-if_indextorainfo(int idx)
+if_indextorainfo(unsigned int idx)
 {
-	struct rainfo *rai = ralist;
+	struct rainfo *rai;
 
-	for (rai = ralist; rai; rai = rai->next) {
+	TAILQ_FOREACH(rai, &ralist, next) {
 		if (rai->ifindex == idx)
 			return(rai);
 	}
@@ -1488,13 +1494,12 @@
 }
 
 static void
-ra_output(rainfo)
-struct rainfo *rainfo;
+ra_output(struct rainfo *rainfo)
 {
 	int i;
 	struct cmsghdr *cm;
 	struct in6_pktinfo *pi;
-	struct soliciter *sol, *nextsol;
+	struct soliciter *sol;
 
 	if ((iflist[rainfo->ifindex]->ifm_flags & IFF_UP) == 0) {
 		syslog(LOG_DEBUG, "<%s> %s is not up, skip sending RA",
@@ -1504,8 +1509,8 @@
 
 	make_packet(rainfo);	/* XXX: inefficient */
 
-	sndmhdr.msg_name = (caddr_t)&sin6_allnodes;
-	sndmhdr.msg_iov[0].iov_base = (caddr_t)rainfo->ra_data;
+	sndmhdr.msg_name = (void *)&sin6_linklocal_allnodes;
+	sndmhdr.msg_iov[0].iov_base = (void *)rainfo->ra_data;
 	sndmhdr.msg_iov[0].iov_len = rainfo->ra_datalen;
 
 	cm = CMSG_FIRSTHDR(&sndmhdr);
@@ -1534,7 +1539,7 @@
 
 	i = sendmsg(sock, &sndmhdr, 0);
 
-	if (i < 0 || i != rainfo->ra_datalen)  {
+	if (i < 0 || (size_t)i != rainfo->ra_datalen)  {
 		if (i < 0) {
 			syslog(LOG_ERR, "<%s> sendmsg on %s: %s",
 			       __func__, rainfo->ifname,
@@ -1547,11 +1552,9 @@
 	 * XXX commented out.  reason: though spec does not forbit it, unicast
 	 * advert does not really help
 	 */
-	for (sol = rainfo->soliciter; sol; sol = nextsol) {
-		nextsol = sol->next;
-
+	while ((sol = TAILQ_FIRST(&rainfo->soliciter)) != NULL) {
 #if 0
-		sndmhdr.msg_name = (caddr_t)&sol->addr;
+		sndmhdr.msg_name = (void *)&sol->addr;
 		i = sendmsg(sock, &sndmhdr, 0);
 		if (i < 0 || i != rainfo->ra_datalen)  {
 			if (i < 0) {
@@ -1562,11 +1565,9 @@
 			}
 		}
 #endif
-
-		sol->next = NULL;
+		TAILQ_REMOVE(&rainfo->soliciter, sol, next);
 		free(sol);
 	}
-	rainfo->soliciter = NULL;
 
 	/* update counter */
 	if (rainfo->initcounter < MAX_INITIAL_RTR_ADVERTISEMENTS)

cvs diff -r1.14 -r1.15 src/usr.sbin/rtadvd/rtadvd.conf.5 (expand / switch to context diff)
--- src/usr.sbin/rtadvd/rtadvd.conf.5 2009/11/01 15:19:19 1.14
+++ src/usr.sbin/rtadvd/rtadvd.conf.5 2011/12/10 19:14:29 1.15
@@ -1,4 +1,4 @@
-.\"	$NetBSD: rtadvd.conf.5,v 1.14 2009/11/01 15:19:19 jakllsch Exp $
+.\"	$NetBSD: rtadvd.conf.5,v 1.15 2011/12/10 19:14:29 roy Exp $
 .\"	$KAME: rtadvd.conf.5,v 1.50 2005/01/14 05:30:59 jinmei Exp $
 .\"
 .\" Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
@@ -28,7 +28,7 @@
 .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 .\" SUCH DAMAGE.
 .\"
-.Dd November 1, 2009
+.Dd December 7, 2012
 .Dt RTADVD.CONF 5
 .Os
 .Sh NAME
@@ -333,6 +333,66 @@
 .Dq Li rtr
 have basically been obsoleted, and should not be used any more.
 .Pp
+The following items are for ICMPv6 Recursive DNS Server Option and
+DNS Search List Option
+.Pq RFC 6106 ,
+which will be attached to router advertisement header.
+These items are optional.
+.Bl -tag -width indent
+.It Cm \&rdnss
+(str) The IPv6 address of one or more recursive DNS servers.
+The argument must be inside double quotes.
+Multiple DNS servers can be specified in a comma-separated string.
+If different lifetimes are needed for different servers,
+separate entries can be given by using
+.Cm rdnss ,
+.Cm rdnss0 ,
+.Cm rdnss1 ,
+.Cm rdnss2 ...
+options with corresponding
+.Cm rdnssltime ,
+.Cm rdnssltime0 ,
+.Cm rdnssltime1 ,
+.Cm rdnssltime2 ...
+entries.
+Note that the maximum number of servers depends on the receiver side.
+See also
+.Xr resolver 5
+manual page for resolver implementation in
+.Fx .
+.It Cm \&rdnssltime
+The lifetime of the
+.Cm rdnss
+DNS server entries.
+The default value is 3/2 of the interval time.
+.It Cm \&dnssl
+(str) One or more domain names in a comma-separated string.
+These domain names will be used when making DNS queries on a
+non-fully-qualified domain name.
+If different lifetimes are needed for different domains, separate entries
+can be given by using
+.Cm dnssl ,
+.Cm dnssl0 ,
+.Cm dnssl1 ,
+.Cm dnssl2 ...
+options with corresponding
+.Cm dnsslltime ,
+.Cm dnsslltime0 ,
+.Cm dnsslltime1 ,
+.Cm dnsslltime2 ...
+entries.
+Note that the maximum number of names depends on the receiver side.
+See also
+.Xr resolver 5
+manual page for resolver implementation in
+.Fx .
+.It Cm \&dnsslltime
+The lifetime of the
+.Cm dnssl
+DNS search list entries.
+The default value is 3/2 of the interval time.
+.El
+.Pp
 You can also refer one line from another by using
 .Cm tc
 capability.
@@ -369,6 +429,17 @@
 	:addr="2001:db8:ffff:1000::":prefixlen#64:
 .Ed
 .Pp
+The following example configures the
+.Li wlan0
+interface and adds two DNS servers and a DNS domain search options
+using the default option lifetime values.
+.Bd -literal -offset
+wlan0:\\
+	:addr="2001:db8:ffff:1000::":prefixlen#64:\\
+	:rdnss="2001:db8:ffff::10,2001:db8:ffff::2:43":\\
+	:dnssl="example.com":
+.Ed
+.Pp
 The following example presents the default values in an explicit manner.
 The configuration is provided just for reference purposes;
 YOU DO NOT NEED TO HAVE IT AT ALL.
@@ -395,6 +466,12 @@
 Default Router Preferences and More-Specific Routes
 .Dc ,
 RFC 4191
+.Pp
+J. Jeong, S. Park, L. Beloeil, S. Madanapalli
+.Do
+IPv6 Router Advertisement Options for DNS Configuration
+.Dc ,
+RFC 6106
 .Sh HISTORY
 The
 .Xr rtadvd 8

cvs diff -r1.10 -r1.11 src/usr.sbin/rtadvd/rtadvd.h (expand / switch to context diff)
--- src/usr.sbin/rtadvd/rtadvd.h 2006/03/05 23:47:08 1.10
+++ src/usr.sbin/rtadvd/rtadvd.h 2011/12/10 19:14:29 1.11
@@ -1,4 +1,4 @@
-/*	$NetBSD: rtadvd.h,v 1.10 2006/03/05 23:47:08 rpaulo Exp $	*/
+/*	$NetBSD: rtadvd.h,v 1.11 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: rtadvd.h,v 1.30 2005/10/17 14:40:02 suz Exp $	*/
 
 /*
@@ -33,9 +33,15 @@
 #define ALLNODES "ff02::1"
 #define ALLROUTERS_LINK "ff02::2"
 #define ALLROUTERS_SITE "ff05::2"
-#define ANY "::"
-#define RTSOLLEN 8
 
+#define IN6ADDR_SITELOCAL_ALLROUTERS_INIT \
+	{{{ 0xff, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \
+ 	    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02 }}}
+
+//extern struct sockaddr_in6 sin6_linklocal_allnodes;
+//extern struct sockaddr_in6 sin6_linklocal_allrouters;
+extern struct sockaddr_in6 sin6_sitelocal_allrouters;
+
 /* protocol constants and default values */
 #define DEF_MAXRTRADVINTERVAL 600
 #define DEF_ADVLINKMTU 0
@@ -62,8 +68,7 @@
 #define PREFIX_FROM_DYNAMIC 3
 
 struct prefix {
-	struct prefix *next;	/* forward link */
-	struct prefix *prev;	/* previous link */
+	TAILQ_ENTRY(prefix) next;
 
 	struct rainfo *rainfo;	/* back pointer to the interface */
 
@@ -71,37 +76,61 @@
 				     * derived from the kernel is deleted.
 				     */
 
-	u_int32_t validlifetime; /* AdvValidLifetime */
+	uint32_t validlifetime; /* AdvValidLifetime */
 	long	vltimeexpire;	/* expiration of vltime; decrement case only */
-	u_int32_t preflifetime;	/* AdvPreferredLifetime */
+	uint32_t preflifetime;	/* AdvPreferredLifetime */
 	long	pltimeexpire;	/* expiration of pltime; decrement case only */
-	u_int onlinkflg;	/* bool: AdvOnLinkFlag */
-	u_int autoconfflg;	/* bool: AdvAutonomousFlag */
+	uint16_t onlinkflg;	/* bool: AdvOnLinkFlag */
+	uint16_t autoconfflg;	/* bool: AdvAutonomousFlag */
 	int prefixlen;
 	int origin;		/* from kernel or config */
 	struct in6_addr prefix;
 };
 
-#ifdef ROUTEINFO
 struct rtinfo {
-	struct rtinfo *prev;	/* previous link */
-	struct rtinfo *next;	/* forward link */
+	TAILQ_ENTRY(rtinfo) next;
 
-	u_int32_t ltime;	/* route lifetime */
-	u_int rtpref;		/* route preference */
+	uint32_t ltime;	/* route lifetime */
+	uint16_t rtpref;		/* route preference */
 	int prefixlen;
 	struct in6_addr prefix;
 };
-#endif
 
+struct rdnss_addr {
+	TAILQ_ENTRY(rdnss_addr) next;
+
+	struct in6_addr addr;
+};
+
+struct rdnss {
+	TAILQ_ENTRY(rdnss) next;
+
+	TAILQ_HEAD(, rdnss_addr) list;
+	uint32_t lifetime;
+};
+
+struct dnssl_domain {
+	TAILQ_ENTRY(dnssl_domain) next;
+
+	int len;
+	char domain[256];
+};
+
+struct dnssl {
+	TAILQ_ENTRY(dnssl) next;
+
+	TAILQ_HEAD(, dnssl_domain) list;
+	uint32_t lifetime;
+};
+
 struct soliciter {
-	struct soliciter *next;
+	TAILQ_ENTRY(soliciter) next;
+
 	struct sockaddr_in6 addr;
 };
 
 struct	rainfo {
-	/* pointer for list */
-	struct	rainfo *next;
+	TAILQ_ENTRY(rainfo) next;
 
 	/* timer related parameters */
 	struct rtadvd_timer *timer;
@@ -110,52 +139,51 @@
 	int waiting;		/* number of RS waiting for RA */
 
 	/* interface information */
-	int	ifindex;
+	uint16_t	ifindex;
 	int	advlinkopt;	/* bool: whether include link-layer addr opt */
 	struct sockaddr_dl *sdl;
 	char	ifname[16];
-	int	phymtu;		/* mtu of the physical interface */
+	uint32_t	phymtu;		/* mtu of the physical interface */
 
 	/* Router configuration variables */
-	u_short lifetime;	/* AdvDefaultLifetime */
-	u_int	maxinterval;	/* MaxRtrAdvInterval */
-	u_int	mininterval;	/* MinRtrAdvInterval */
+	uint16_t	lifetime;	/* AdvDefaultLifetime */
+	uint16_t	maxinterval;	/* MaxRtrAdvInterval */
+	uint16_t	mininterval;	/* MinRtrAdvInterval */
 	int 	managedflg;	/* AdvManagedFlag */
 	int	otherflg;	/* AdvOtherConfigFlag */
 
 	int	rtpref;		/* router preference */
-	u_int32_t linkmtu;	/* AdvLinkMTU */
-	u_int32_t reachabletime; /* AdvReachableTime */
-	u_int32_t retranstimer;	/* AdvRetransTimer */
-	u_int	hoplimit;	/* AdvCurHopLimit */
-	struct prefix prefix;	/* AdvPrefixList(link head) */
-	int	pfxs;		/* number of prefixes */
-	long	clockskew;	/* used for consisitency check of lifetimes */
+	uint32_t linkmtu;	/* AdvLinkMTU */
+	uint32_t reachabletime; /* AdvReachableTime */
+	uint32_t retranstimer;	/* AdvRetransTimer */
+	uint16_t	hoplimit;	/* AdvCurHopLimit */
+	TAILQ_HEAD(, prefix) prefix;	/* AdvPrefixList(link head) */
+	int	pfxs;
+	uint16_t	clockskew;/* used for consisitency check of lifetimes */
 
-#ifdef ROUTEINFO
-	struct rtinfo route;	/* route information option (link head) */
-	int	routes;		/* number of route information options */
-#endif
+	TAILQ_HEAD(, rtinfo) route;
+	TAILQ_HEAD(, rdnss) rdnss;	/* RDNSS list */
+	TAILQ_HEAD(, dnssl) dnssl;	/* DNS Search List */
 
 	/* actual RA packet data and its length */
 	size_t ra_datalen;
-	u_char *ra_data;
+	char *ra_data;
 
 	/* statistics */
-	u_quad_t raoutput;	/* number of RAs sent */
-	u_quad_t rainput;	/* number of RAs received */
-	u_quad_t rainconsistent; /* number of RAs inconsistent with ours */
-	u_quad_t rsinput;	/* number of RSs received */
+	uint64_t raoutput;	/* number of RAs sent */
+	uint64_t rainput;	/* number of RAs received */
+	uint64_t rainconsistent; /* number of RAs inconsistent with ours */
+	uint64_t rsinput;	/* number of RSs received */
 
 	/* info about soliciter */
-	struct soliciter *soliciter;	/* recent solication source */
+	TAILQ_HEAD(, soliciter) soliciter;	/* recent solication source */
 };
 
-struct rtadvd_timer *ra_timeout __P((void *));
-void ra_timer_update __P((void *, struct timeval *));
+extern TAILQ_HEAD(ralist_head_t, rainfo) ralist;
 
-int prefix_match __P((struct in6_addr *, int, struct in6_addr *, int));
-struct rainfo *if_indextorainfo __P((int));
-struct prefix *find_prefix __P((struct rainfo *, struct in6_addr *, int));
+struct rtadvd_timer *ra_timeout(void *);
+void ra_timer_update(void *, struct timeval *);
 
-extern struct in6_addr in6a_site_allrouters;
+int prefix_match(struct in6_addr *, int, struct in6_addr *, int);
+struct rainfo *if_indextorainfo(unsigned int);
+struct prefix *find_prefix(struct rainfo *, struct in6_addr *, int);

cvs diff -r1.9 -r1.10 src/usr.sbin/rtadvd/timer.c (expand / switch to context diff)
--- src/usr.sbin/rtadvd/timer.c 2006/03/05 23:47:08 1.9
+++ src/usr.sbin/rtadvd/timer.c 2011/12/10 19:14:29 1.10
@@ -1,4 +1,4 @@
-/*	$NetBSD: timer.c,v 1.9 2006/03/05 23:47:08 rpaulo Exp $	*/
+/*	$NetBSD: timer.c,v 1.10 2011/12/10 19:14:29 roy Exp $	*/
 /*	$KAME: timer.c,v 1.11 2005/04/14 06:22:35 suz Exp $	*/
 
 /*
@@ -30,6 +30,7 @@
  * SUCH DAMAGE.
  */
 
+#include <sys/queue.h>
 #include <sys/time.h>
 
 #include <unistd.h>
@@ -39,26 +40,26 @@
 #include <search.h>
 #include "timer.h"
 
-static struct rtadvd_timer timer_head;
+struct rtadvd_timer_head_t ra_timer = TAILQ_HEAD_INITIALIZER(ra_timer);
 
 #define MILLION 1000000
 #define TIMEVAL_EQUAL(t1,t2) ((t1)->tv_sec == (t2)->tv_sec &&\
  (t1)->tv_usec == (t2)->tv_usec)
 
-static struct timeval tm_max = {0x7fffffff, 0x7fffffff};
+static struct timeval tm_limit = {0x7fffffff, 0x7fffffff};
+static struct timeval tm_max;
 
 void
-rtadvd_timer_init()
+rtadvd_timer_init(void)
 {
-	memset(&timer_head, 0, sizeof(timer_head));
 
-	timer_head.next = timer_head.prev = &timer_head;
-	timer_head.tm = tm_max;
+	TAILQ_INIT(&ra_timer);
+	tm_max = tm_limit;
 }
 
 struct rtadvd_timer *
-rtadvd_add_timer(struct rtadvd_timer *(*timeout) __P((void *)),
-    void (*update) __P((void *, struct timeval *)),
+rtadvd_add_timer(struct rtadvd_timer *(*timeout) (void *),
+    void (*update) (void *, struct timeval *),
     void *timeodata, void *updatedata)
 {
 	struct rtadvd_timer *newtimer;
@@ -83,7 +84,7 @@
 	newtimer->tm = tm_max;
 
 	/* link into chain */
-	insque(newtimer, &timer_head);
+	TAILQ_INSERT_TAIL(&ra_timer, newtimer, next);
 
 	return(newtimer);
 }
@@ -91,7 +92,8 @@
 void
 rtadvd_remove_timer(struct rtadvd_timer **timer)
 {
-	remque(*timer);
+
+	TAILQ_REMOVE(&ra_timer, *timer, next);
 	free(*timer);
 	*timer = NULL;
 }
@@ -107,8 +109,8 @@
 	TIMEVAL_ADD(&now, tm, &timer->tm);
 
 	/* update the next expiration time */
-	if (TIMEVAL_LT(timer->tm, timer_head.tm))
-		timer_head.tm = timer->tm;
+	if (TIMEVAL_LT(timer->tm, tm_max))
+		tm_max = timer->tm;
 
 	return;
 }
@@ -119,19 +121,16 @@
  * Return the next interval for select() call.
  */
 struct timeval *
-rtadvd_check_timer()
+rtadvd_check_timer(void)
 {
 	static struct timeval returnval;
 	struct timeval now;
-	struct rtadvd_timer *tm = timer_head.next, *tm_next;
+	struct rtadvd_timer *tm;
 
 	gettimeofday(&now, NULL);
+	tm_max = tm_limit;
 
-	timer_head.tm = tm_max;
-
-	for (tm = timer_head.next; tm != &timer_head; tm = tm_next) {
-		tm_next = tm->next;
-
+	TAILQ_FOREACH(tm, &ra_timer, next) {
 		if (TIMEVAL_LEQ(tm->tm, now)) {
 			if ((*tm->expire)(tm->expire_data) == NULL)
 				continue; /* the timer was removed */
@@ -140,18 +139,18 @@
 			TIMEVAL_ADD(&tm->tm, &now, &tm->tm);
 		}
 
-		if (TIMEVAL_LT(tm->tm, timer_head.tm))
-			timer_head.tm = tm->tm;
+		if (TIMEVAL_LT(tm->tm, tm_max))
+			tm_max = tm->tm;
 	}
 
-	if (TIMEVAL_EQUAL(&tm_max, &timer_head.tm)) {
+	if (TIMEVAL_EQUAL(&tm_max, &tm_limit)) {
 		/* no need to timeout */
 		return(NULL);
-	} else if (TIMEVAL_LT(timer_head.tm, now)) {
+	} else if (TIMEVAL_LT(tm_max, now)) {
 		/* this may occur when the interval is too small */
 		returnval.tv_sec = returnval.tv_usec = 0;
 	} else
-		TIMEVAL_SUB(&timer_head.tm, &now, &returnval);
+		TIMEVAL_SUB(&tm_max, &now, &returnval);
 	return(&returnval);
 }