xref: /titanic_44/usr/src/cmd/cmd-inet/usr.lib/in.ndpd/main.c (revision 3289e1bdec732dbdf04517907516fd0d00f6a6f8)
1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 /*
22  * Copyright 2007 Sun Microsystems, Inc.  All rights reserved.
23  * Use is subject to license terms.
24  */
25 
26 #pragma ident	"%Z%%M%	%I%	%E% SMI"
27 
28 #include "defs.h"
29 #include "tables.h"
30 #include <fcntl.h>
31 #include <sys/un.h>
32 
33 static void	initlog(void);
34 static void	run_timeouts(void);
35 
36 static void	advertise(struct sockaddr_in6 *sin6, struct phyint *pi,
37 		    boolean_t no_prefixes);
38 static void	solicit(struct sockaddr_in6 *sin6, struct phyint *pi);
39 static void	initifs(boolean_t first);
40 static void	check_if_removed(struct phyint *pi);
41 static void	loopback_ra_enqueue(struct phyint *pi,
42 		    struct nd_router_advert *ra, int len);
43 static void	loopback_ra_dequeue(void);
44 static void	check_daemonize(void);
45 
46 struct in6_addr all_nodes_mcast = { { 0xff, 0x2, 0x0, 0x0,
47 				    0x0, 0x0, 0x0, 0x0,
48 				    0x0, 0x0, 0x0, 0x0,
49 				    0x0, 0x0, 0x0, 0x1 } };
50 
51 struct in6_addr all_routers_mcast = { { 0xff, 0x2, 0x0, 0x0,
52 				    0x0, 0x0, 0x0, 0x0,
53 				    0x0, 0x0, 0x0, 0x0,
54 				    0x0, 0x0, 0x0, 0x2 } };
55 
56 static struct sockaddr_in6 v6allnodes = { AF_INET6, 0, 0,
57 				    { 0xff, 0x2, 0x0, 0x0,
58 				    0x0, 0x0, 0x0, 0x0,
59 				    0x0, 0x0, 0x0, 0x0,
60 				    0x0, 0x0, 0x0, 0x1 } };
61 
62 static struct sockaddr_in6 v6allrouters = { AF_INET6, 0, 0,
63 				    { 0xff, 0x2, 0x0, 0x0,
64 				    0x0, 0x0, 0x0, 0x0,
65 				    0x0, 0x0, 0x0, 0x0,
66 				    0x0, 0x0, 0x0, 0x2 } };
67 
68 static char **argv0;		/* Saved for re-exec on SIGHUP */
69 
70 static uint64_t packet[(IP_MAXPACKET + 1)/8];
71 
72 static int	show_ifs = 0;
73 static boolean_t	already_daemonized = _B_FALSE;
74 int		debug = 0;
75 int		no_loopback = 0; /* Do not send RA packets to ourselves */
76 
77 /*
78  * Size of routing socket message used by in.ndpd which includes the header,
79  * space for the RTA_DST, RTA_GATEWAY and RTA_NETMASK (each a sockaddr_in6)
80  * plus space for the RTA_IFP (a sockaddr_dl).
81  */
82 #define	NDP_RTM_MSGLEN	sizeof (struct rt_msghdr) +	\
83 			sizeof (struct sockaddr_in6) +	\
84 			sizeof (struct sockaddr_in6) +	\
85 			sizeof (struct sockaddr_in6) +	\
86 			sizeof (struct sockaddr_dl)
87 
88 /*
89  * These are referenced externally in tables.c in order to fill in the
90  * dynamic portions of the routing socket message and then to send the message
91  * itself.
92  */
93 int	rtsock = -1;			/* Routing socket */
94 struct	rt_msghdr	*rt_msg;	/* Routing socket message */
95 struct	sockaddr_in6	*rta_gateway;	/* RTA_GATEWAY sockaddr */
96 struct	sockaddr_dl	*rta_ifp;	/* RTA_IFP sockaddr */
97 int	mibsock = -1;			/* mib request socket */
98 
99 /*
100  * Return the current time in milliseconds truncated to
101  * fit in an integer.
102  */
103 uint_t
104 getcurrenttime(void)
105 {
106 	struct timeval tp;
107 
108 	if (gettimeofday(&tp, NULL) < 0) {
109 		logperror("getcurrenttime: gettimeofday failed");
110 		exit(1);
111 	}
112 	return (tp.tv_sec * 1000 + tp.tv_usec / 1000);
113 }
114 
115 /*
116  * Output a preformated packet from the packet[] buffer.
117  */
118 static void
119 sendpacket(struct sockaddr_in6 *sin6, int sock, int size, int flags)
120 {
121 	int cc;
122 	char abuf[INET6_ADDRSTRLEN];
123 
124 	cc = sendto(sock, (char *)packet, size, flags,
125 		(struct sockaddr *)sin6, sizeof (*sin6));
126 	if (cc < 0 || cc != size) {
127 		if (cc < 0) {
128 			logperror("sendpacket: sendto");
129 		}
130 		logmsg(LOG_ERR, "sendpacket: wrote %s %d chars, ret=%d\n",
131 		    inet_ntop(sin6->sin6_family,
132 		    (void *)&sin6->sin6_addr,
133 		    abuf, sizeof (abuf)),
134 		    size, cc);
135 	}
136 }
137 
138 /* Send a Router Solicitation */
139 static void
140 solicit(struct sockaddr_in6 *sin6, struct phyint *pi)
141 {
142 	int packetlen = 0;
143 	struct	nd_router_solicit *rs = (struct nd_router_solicit *)packet;
144 	char *pptr = (char *)packet;
145 
146 	rs->nd_rs_type = ND_ROUTER_SOLICIT;
147 	rs->nd_rs_code = 0;
148 	rs->nd_rs_cksum = htons(0);
149 	rs->nd_rs_reserved = htonl(0);
150 
151 	packetlen += sizeof (*rs);
152 	pptr += sizeof (*rs);
153 
154 	/* Attach any options */
155 	if (pi->pi_hdw_addr_len != 0) {
156 		struct nd_opt_lla *lo = (struct nd_opt_lla *)pptr;
157 		int optlen;
158 
159 		/* roundup to multiple of 8 and make padding zero */
160 		optlen = ((sizeof (struct nd_opt_hdr) +
161 		    pi->pi_hdw_addr_len + 7) / 8) * 8;
162 		bzero(pptr, optlen);
163 
164 		lo->nd_opt_lla_type = ND_OPT_SOURCE_LINKADDR;
165 		lo->nd_opt_lla_len = optlen / 8;
166 		bcopy((char *)pi->pi_hdw_addr,
167 		    (char *)lo->nd_opt_lla_hdw_addr,
168 		    pi->pi_hdw_addr_len);
169 		packetlen += optlen;
170 		pptr += optlen;
171 	}
172 
173 	if (debug & D_PKTOUT) {
174 		print_route_sol("Sending solicitation to ", pi, rs, packetlen,
175 		    sin6);
176 	}
177 	sendpacket(sin6, pi->pi_sock, packetlen, 0);
178 }
179 
180 /*
181  * Send a (set of) Router Advertisements and feed them back to ourselves
182  * for processing. Unless no_prefixes is set all prefixes are included.
183  * If there are too many prefix options to fit in one packet multiple
184  * packets will be sent - each containing a subset of the prefix options.
185  */
186 static void
187 advertise(struct sockaddr_in6 *sin6, struct phyint *pi, boolean_t no_prefixes)
188 {
189 	struct	nd_opt_prefix_info *po;
190 	char *pptr = (char *)packet;
191 	struct nd_router_advert *ra;
192 	struct adv_prefix *adv_pr;
193 	int packetlen = 0;
194 
195 	ra = (struct nd_router_advert *)pptr;
196 	ra->nd_ra_type = ND_ROUTER_ADVERT;
197 	ra->nd_ra_code = 0;
198 	ra->nd_ra_cksum = htons(0);
199 	ra->nd_ra_curhoplimit = pi->pi_AdvCurHopLimit;
200 	ra->nd_ra_flags_reserved = 0;
201 	if (pi->pi_AdvManagedFlag)
202 		ra->nd_ra_flags_reserved |= ND_RA_FLAG_MANAGED;
203 	if (pi->pi_AdvOtherConfigFlag)
204 		ra->nd_ra_flags_reserved |= ND_RA_FLAG_OTHER;
205 
206 	if (pi->pi_adv_state == FINAL_ADV)
207 		ra->nd_ra_router_lifetime = htons(0);
208 	else
209 		ra->nd_ra_router_lifetime = htons(pi->pi_AdvDefaultLifetime);
210 	ra->nd_ra_reachable = htonl(pi->pi_AdvReachableTime);
211 	ra->nd_ra_retransmit = htonl(pi->pi_AdvRetransTimer);
212 
213 	packetlen = sizeof (*ra);
214 	pptr += sizeof (*ra);
215 
216 	if (pi->pi_adv_state == FINAL_ADV) {
217 		if (debug & D_PKTOUT) {
218 			print_route_adv("Sending advert (FINAL) to ", pi,
219 			    ra, packetlen, sin6);
220 		}
221 		sendpacket(sin6, pi->pi_sock, packetlen, 0);
222 		/* Feed packet back in for router operation */
223 		loopback_ra_enqueue(pi, ra, packetlen);
224 		return;
225 	}
226 
227 	/* Attach any options */
228 	if (pi->pi_hdw_addr_len != 0) {
229 		struct nd_opt_lla *lo = (struct nd_opt_lla *)pptr;
230 		int optlen;
231 
232 		/* roundup to multiple of 8 and make padding zero */
233 		optlen = ((sizeof (struct nd_opt_hdr) +
234 		    pi->pi_hdw_addr_len + 7) / 8) * 8;
235 		bzero(pptr, optlen);
236 
237 		lo->nd_opt_lla_type = ND_OPT_SOURCE_LINKADDR;
238 		lo->nd_opt_lla_len = optlen / 8;
239 		bcopy((char *)pi->pi_hdw_addr,
240 		    (char *)lo->nd_opt_lla_hdw_addr,
241 		    pi->pi_hdw_addr_len);
242 		packetlen += optlen;
243 		pptr += optlen;
244 	}
245 
246 	if (pi->pi_AdvLinkMTU != 0) {
247 		struct nd_opt_mtu *mo = (struct nd_opt_mtu *)pptr;
248 
249 		mo->nd_opt_mtu_type = ND_OPT_MTU;
250 		mo->nd_opt_mtu_len = sizeof (struct nd_opt_mtu) / 8;
251 		mo->nd_opt_mtu_reserved = 0;
252 		mo->nd_opt_mtu_mtu = htonl(pi->pi_AdvLinkMTU);
253 
254 		packetlen += sizeof (struct nd_opt_mtu);
255 		pptr += sizeof (struct nd_opt_mtu);
256 	}
257 
258 	if (no_prefixes) {
259 		if (debug & D_PKTOUT) {
260 			print_route_adv("Sending advert to ", pi,
261 			    ra, packetlen, sin6);
262 		}
263 		sendpacket(sin6, pi->pi_sock, packetlen, 0);
264 		/* Feed packet back in for router operation */
265 		loopback_ra_enqueue(pi, ra, packetlen);
266 		return;
267 	}
268 
269 	po = (struct nd_opt_prefix_info *)pptr;
270 	for (adv_pr = pi->pi_adv_prefix_list; adv_pr != NULL;
271 	    adv_pr = adv_pr->adv_pr_next) {
272 		if (!adv_pr->adv_pr_AdvOnLinkFlag &&
273 		    !adv_pr->adv_pr_AdvAutonomousFlag) {
274 			continue;
275 		}
276 
277 		/*
278 		 * If the prefix doesn't fit in packet send
279 		 * what we have so far and start with new packet.
280 		 */
281 		if (packetlen + sizeof (*po) >
282 		    pi->pi_LinkMTU - sizeof (struct ip6_hdr)) {
283 			if (debug & D_PKTOUT) {
284 				print_route_adv("Sending advert "
285 				    "(FRAG) to ",
286 				    pi, ra, packetlen, sin6);
287 			}
288 			sendpacket(sin6, pi->pi_sock, packetlen, 0);
289 			/* Feed packet back in for router operation */
290 			loopback_ra_enqueue(pi, ra, packetlen);
291 			packetlen = sizeof (*ra);
292 			pptr = (char *)packet + sizeof (*ra);
293 			po = (struct nd_opt_prefix_info *)pptr;
294 		}
295 		po->nd_opt_pi_type = ND_OPT_PREFIX_INFORMATION;
296 		po->nd_opt_pi_len = sizeof (*po)/8;
297 		po->nd_opt_pi_flags_reserved = 0;
298 		if (adv_pr->adv_pr_AdvOnLinkFlag) {
299 			po->nd_opt_pi_flags_reserved |=
300 			    ND_OPT_PI_FLAG_ONLINK;
301 		}
302 		if (adv_pr->adv_pr_AdvAutonomousFlag) {
303 			po->nd_opt_pi_flags_reserved |=
304 			    ND_OPT_PI_FLAG_AUTO;
305 		}
306 		po->nd_opt_pi_prefix_len = adv_pr->adv_pr_prefix_len;
307 		/*
308 		 * If both Adv*Expiration and Adv*Lifetime are
309 		 * set we prefer the former and make the lifetime
310 		 * decrement in real time.
311 		 */
312 		if (adv_pr->adv_pr_AdvValidRealTime) {
313 			po->nd_opt_pi_valid_time =
314 			    htonl(adv_pr->adv_pr_AdvValidExpiration);
315 		} else {
316 			po->nd_opt_pi_valid_time =
317 			    htonl(adv_pr->adv_pr_AdvValidLifetime);
318 		}
319 		if (adv_pr->adv_pr_AdvPreferredRealTime) {
320 			po->nd_opt_pi_preferred_time =
321 			    htonl(adv_pr->adv_pr_AdvPreferredExpiration);
322 		} else {
323 			po->nd_opt_pi_preferred_time =
324 			    htonl(adv_pr->adv_pr_AdvPreferredLifetime);
325 		}
326 		po->nd_opt_pi_reserved2 = htonl(0);
327 		po->nd_opt_pi_prefix = adv_pr->adv_pr_prefix;
328 
329 		po++;
330 		packetlen += sizeof (*po);
331 	}
332 	if (debug & D_PKTOUT) {
333 		print_route_adv("Sending advert to ", pi,
334 		    ra, packetlen, sin6);
335 	}
336 	sendpacket(sin6, pi->pi_sock, packetlen, 0);
337 	/* Feed packet back in for router operation */
338 	loopback_ra_enqueue(pi, ra, packetlen);
339 }
340 
341 /* Poll support */
342 static int		pollfd_num = 0;	/* Allocated and initialized */
343 static struct pollfd	*pollfds = NULL;
344 
345 /*
346  * Add fd to the set being polled. Returns 0 if ok; -1 if failed.
347  */
348 int
349 poll_add(int fd)
350 {
351 	int i;
352 	int new_num;
353 	struct pollfd *newfds;
354 
355 	/* Check if already present */
356 	for (i = 0; i < pollfd_num; i++) {
357 		if (pollfds[i].fd == fd)
358 			return (0);
359 	}
360 	/* Check for empty spot already present */
361 	for (i = 0; i < pollfd_num; i++) {
362 		if (pollfds[i].fd == -1) {
363 			pollfds[i].fd = fd;
364 			return (0);
365 		}
366 	}
367 
368 	/* Allocate space for 32 more fds and initialize to -1 */
369 	new_num = pollfd_num + 32;
370 	newfds = realloc(pollfds, new_num * sizeof (struct pollfd));
371 	if (newfds == NULL) {
372 		logperror("poll_add: realloc");
373 		return (-1);
374 	}
375 
376 	newfds[pollfd_num].fd = fd;
377 	newfds[pollfd_num++].events = POLLIN;
378 
379 	for (i = pollfd_num; i < new_num; i++) {
380 		newfds[i].fd = -1;
381 		newfds[i].events = POLLIN;
382 	}
383 	pollfd_num = new_num;
384 	pollfds = newfds;
385 	return (0);
386 }
387 
388 /*
389  * Remove fd from the set being polled. Returns 0 if ok; -1 if failed.
390  */
391 int
392 poll_remove(int fd)
393 {
394 	int i;
395 
396 	/* Check if already present */
397 	for (i = 0; i < pollfd_num; i++) {
398 		if (pollfds[i].fd == fd) {
399 			pollfds[i].fd = -1;
400 			return (0);
401 		}
402 	}
403 	return (-1);
404 }
405 
406 /*
407  * Extract information about the ifname (either a physical interface and
408  * the ":0" logical interface or just a logical interface).
409  * If the interface (still) exists in kernel set pr_in_use
410  * for caller to be able to detect interfaces that are removed.
411  * Starts sending advertisements/solicitations when new physical interfaces
412  * are detected.
413  */
414 static void
415 if_process(int s, char *ifname, boolean_t first)
416 {
417 	struct lifreq lifr;
418 	struct phyint *pi;
419 	struct prefix *pr;
420 	char *cp;
421 	char phyintname[LIFNAMSIZ + 1];
422 
423 	if (debug & D_IFSCAN)
424 		logmsg(LOG_DEBUG, "if_process(%s)\n", ifname);
425 
426 	(void) strncpy(lifr.lifr_name, ifname, sizeof (lifr.lifr_name));
427 	lifr.lifr_name[sizeof (lifr.lifr_name) - 1] = '\0';
428 	if (ioctl(s, SIOCGLIFFLAGS, (char *)&lifr) < 0) {
429 		if (errno == ENXIO) {
430 			/*
431 			 * Interface has disappeared
432 			 */
433 			return;
434 		}
435 		logperror("if_process: ioctl (get interface flags)");
436 		return;
437 	}
438 
439 	/*
440 	 * Ignore loopback and point-to-multipoint interfaces.
441 	 * Point-to-point interfaces always have IFF_MULTICAST set.
442 	 */
443 	if (!(lifr.lifr_flags & IFF_MULTICAST) ||
444 	    (lifr.lifr_flags & IFF_LOOPBACK)) {
445 		return;
446 	}
447 
448 	if (!(lifr.lifr_flags & IFF_IPV6))
449 		return;
450 
451 	(void) strncpy(phyintname, ifname, sizeof (phyintname));
452 	phyintname[sizeof (phyintname) - 1] = '\0';
453 	if ((cp = strchr(phyintname, IF_SEPARATOR)) != NULL) {
454 		*cp = '\0';
455 	}
456 
457 	pi = phyint_lookup(phyintname);
458 	if (pi == NULL) {
459 		/*
460 		 * Do not add anything for new interfaces until they are UP.
461 		 * For existing interfaces we track the up flag.
462 		 */
463 		if (!(lifr.lifr_flags & IFF_UP))
464 			return;
465 
466 		pi = phyint_create(phyintname);
467 		if (pi == NULL) {
468 			logmsg(LOG_ERR, "if_process: out of memory\n");
469 			return;
470 		}
471 	}
472 	(void) phyint_init_from_k(pi);
473 	if (pi->pi_sock == -1 && !(pi->pi_kernel_state & PI_PRESENT)) {
474 		/* Interface is not yet present */
475 		if (debug & D_PHYINT) {
476 			logmsg(LOG_DEBUG, "if_process: interface not yet "
477 			    "present %s\n", pi->pi_name);
478 		}
479 		return;
480 	}
481 
482 	if (pi->pi_sock != -1) {
483 		if (poll_add(pi->pi_sock) == -1) {
484 			/*
485 			 * reset state.
486 			 */
487 			phyint_cleanup(pi);
488 		}
489 	}
490 
491 	/*
492 	 * Check if IFF_ROUTER has been turned off in kernel in which
493 	 * case we have to turn off AdvSendAdvertisements.
494 	 * The kernel will automatically turn off IFF_ROUTER if
495 	 * ip6_forwarding is turned off.
496 	 * Note that we do not switch back should IFF_ROUTER be turned on.
497 	 */
498 	if (!first &&
499 	    pi->pi_AdvSendAdvertisements && !(pi->pi_flags & IFF_ROUTER)) {
500 		logmsg(LOG_INFO, "No longer a router on %s\n", pi->pi_name);
501 		check_to_advertise(pi, START_FINAL_ADV);
502 
503 		pi->pi_AdvSendAdvertisements = 0;
504 		pi->pi_sol_state = NO_SOLICIT;
505 	}
506 
507 	/*
508 	 * Send advertisments and solicitation only if the interface is
509 	 * present in the kernel.
510 	 */
511 	if (pi->pi_kernel_state & PI_PRESENT) {
512 
513 		if (pi->pi_AdvSendAdvertisements) {
514 			if (pi->pi_adv_state == NO_ADV)
515 				check_to_advertise(pi, START_INIT_ADV);
516 		} else {
517 			if (pi->pi_sol_state == NO_SOLICIT)
518 				check_to_solicit(pi, START_INIT_SOLICIT);
519 		}
520 	}
521 
522 	/*
523 	 * Track static kernel prefixes to prevent in.ndpd from clobbering
524 	 * them by creating a struct prefix for each prefix detected in the
525 	 * kernel.
526 	 */
527 	pr = prefix_lookup_name(pi, ifname);
528 	if (pr == NULL) {
529 		pr = prefix_create_name(pi, ifname);
530 		if (pr == NULL) {
531 			logmsg(LOG_ERR, "if_process: out of memory\n");
532 			return;
533 		}
534 		if (prefix_init_from_k(pr) == -1) {
535 			prefix_delete(pr);
536 			return;
537 		}
538 	}
539 	/* Detect prefixes which are removed */
540 	if (pr->pr_kernel_state != 0)
541 		pr->pr_in_use = _B_TRUE;
542 
543 	if ((lifr.lifr_flags & IFF_DUPLICATE) &&
544 	    !(lifr.lifr_flags & IFF_DHCPRUNNING) &&
545 	    (pr->pr_flags & IFF_TEMPORARY)) {
546 		in6_addr_t *token;
547 		int i;
548 		char abuf[INET6_ADDRSTRLEN];
549 
550 		if (++pr->pr_attempts >= MAX_DAD_FAILURES) {
551 			logmsg(LOG_ERR, "%s: token %s is duplicate after %d "
552 			    "attempts; disabling temporary addresses on %s",
553 			    pr->pr_name, inet_ntop(AF_INET6,
554 			    (void *)&pi->pi_tmp_token, abuf, sizeof (abuf)),
555 			    pr->pr_attempts, pi->pi_name);
556 			pi->pi_TmpAddrsEnabled = 0;
557 			tmptoken_delete(pi);
558 			prefix_delete(pr);
559 			return;
560 		}
561 		logmsg(LOG_WARNING, "%s: token %s is duplicate; trying again",
562 		    pr->pr_name, inet_ntop(AF_INET6, (void *)&pi->pi_tmp_token,
563 		    abuf, sizeof (abuf)));
564 		if (!tmptoken_create(pi)) {
565 			prefix_delete(pr);
566 			return;
567 		}
568 		token = &pi->pi_tmp_token;
569 		for (i = 0; i < 16; i++) {
570 			/*
571 			 * prefix_create ensures that pr_prefix has all-zero
572 			 * bits after prefixlen.
573 			 */
574 			pr->pr_address.s6_addr[i] = pr->pr_prefix.s6_addr[i] |
575 			    token->s6_addr[i];
576 		}
577 		if (prefix_lookup_addr_match(pr) != NULL) {
578 			prefix_delete(pr);
579 			return;
580 		}
581 		pr->pr_CreateTime = getcurrenttime() / MILLISEC;
582 		/*
583 		 * We've got a new token.  Clearing PR_AUTO causes
584 		 * prefix_update_k to bring the interface up and set the
585 		 * address.
586 		 */
587 		pr->pr_kernel_state &= ~PR_AUTO;
588 		prefix_update_k(pr);
589 	}
590 }
591 
592 static int ifsock = -1;
593 
594 /*
595  * Scan all interfaces to detect changes as well as new and deleted intefaces
596  * 'first' is set for the initial call only. Do not effect anything.
597  */
598 static void
599 initifs(boolean_t first)
600 {
601 	char *buf;
602 	int bufsize;
603 	int numifs;
604 	int n;
605 	struct lifnum lifn;
606 	struct lifconf lifc;
607 	struct lifreq *lifr;
608 	struct phyint *pi;
609 	struct phyint *next_pi;
610 	struct prefix *pr;
611 
612 	if (debug & D_IFSCAN)
613 		logmsg(LOG_DEBUG, "Reading interface configuration\n");
614 	if (ifsock < 0) {
615 		ifsock = socket(AF_INET6, SOCK_DGRAM, 0);
616 		if (ifsock < 0) {
617 			logperror("initifs: socket");
618 			return;
619 		}
620 	}
621 	lifn.lifn_family = AF_INET6;
622 	lifn.lifn_flags = LIFC_NOXMIT | LIFC_TEMPORARY;
623 	if (ioctl(ifsock, SIOCGLIFNUM, (char *)&lifn) < 0) {
624 		logperror("initifs: ioctl (get interface numbers)");
625 		return;
626 	}
627 	numifs = lifn.lifn_count;
628 	bufsize = numifs * sizeof (struct lifreq);
629 
630 	buf = (char *)malloc(bufsize);
631 	if (buf == NULL) {
632 		logmsg(LOG_ERR, "initifs: out of memory\n");
633 		return;
634 	}
635 
636 	/*
637 	 * Mark the interfaces so that we can find phyints and prefixes
638 	 * which have disappeared from the kernel.
639 	 * if_process will set pr_in_use when it finds the interface
640 	 * in the kernel.
641 	 */
642 	for (pi = phyints; pi != NULL; pi = pi->pi_next) {
643 		/*
644 		 * Before re-examining the state of the interfaces,
645 		 * PI_PRESENT should be cleared from pi_kernel_state.
646 		 */
647 		pi->pi_kernel_state &= ~PI_PRESENT;
648 		for (pr = pi->pi_prefix_list; pr != NULL; pr = pr->pr_next) {
649 			pr->pr_in_use = _B_FALSE;
650 		}
651 	}
652 
653 	lifc.lifc_family = AF_INET6;
654 	lifc.lifc_flags = LIFC_NOXMIT | LIFC_TEMPORARY;
655 	lifc.lifc_len = bufsize;
656 	lifc.lifc_buf = buf;
657 
658 	if (ioctl(ifsock, SIOCGLIFCONF, (char *)&lifc) < 0) {
659 		logperror("initifs: ioctl (get interface configuration)");
660 		free(buf);
661 		return;
662 	}
663 
664 	lifr = (struct lifreq *)lifc.lifc_req;
665 	for (n = lifc.lifc_len / sizeof (struct lifreq); n > 0; n--, lifr++)
666 		if_process(ifsock, lifr->lifr_name, first);
667 	free(buf);
668 
669 	/*
670 	 * Detect phyints that have been removed from the kernel.
671 	 * Since we can't recreate it here (would require ifconfig plumb
672 	 * logic) we just terminate use of that phyint.
673 	 */
674 	for (pi = phyints; pi != NULL; pi = next_pi) {
675 		next_pi = pi->pi_next;
676 		/*
677 		 * If interface (still) exists in kernel, set
678 		 * pi_state to indicate that.
679 		 */
680 		if (pi->pi_kernel_state & PI_PRESENT) {
681 			pi->pi_state |= PI_PRESENT;
682 		}
683 
684 		check_if_removed(pi);
685 	}
686 	if (show_ifs)
687 		phyint_print_all();
688 }
689 
690 
691 /*
692  * Router advertisement state machine. Used for everything but timer
693  * events which use advertise_event directly.
694  */
695 void
696 check_to_advertise(struct phyint *pi, enum adv_events event)
697 {
698 	uint_t delay;
699 	enum adv_states old_state = pi->pi_adv_state;
700 
701 	if (debug & D_STATE) {
702 		logmsg(LOG_DEBUG, "check_to_advertise(%s, %d) state %d\n",
703 		    pi->pi_name, (int)event, (int)old_state);
704 	}
705 	delay = advertise_event(pi, event, 0);
706 	if (delay != TIMER_INFINITY) {
707 		/* Make sure the global next event is updated */
708 		timer_schedule(delay);
709 	}
710 
711 	if (debug & D_STATE) {
712 		logmsg(LOG_DEBUG, "check_to_advertise(%s, %d) state %d -> %d\n",
713 		    pi->pi_name, (int)event, (int)old_state,
714 		    (int)pi->pi_adv_state);
715 	}
716 }
717 
718 /*
719  * Router advertisement state machine.
720  * Return the number of milliseconds until next timeout (TIMER_INFINITY
721  * if never).
722  * For the ADV_TIMER event the caller passes in the number of milliseconds
723  * since the last timer event in the 'elapsed' parameter.
724  */
725 uint_t
726 advertise_event(struct phyint *pi, enum adv_events event, uint_t elapsed)
727 {
728 	uint_t delay;
729 
730 	if (debug & D_STATE) {
731 		logmsg(LOG_DEBUG, "advertise_event(%s, %d, %d) state %d\n",
732 		    pi->pi_name, (int)event, elapsed, (int)pi->pi_adv_state);
733 	}
734 	check_daemonize();
735 	if (!pi->pi_AdvSendAdvertisements)
736 		return (TIMER_INFINITY);
737 	if (pi->pi_flags & IFF_NORTEXCH) {
738 		if (debug & D_PKTOUT) {
739 			logmsg(LOG_DEBUG, "Suppress sending RA packet on %s "
740 			    "(no route exchange on interface)\n",
741 			    pi->pi_name);
742 		}
743 		return (TIMER_INFINITY);
744 	}
745 
746 	switch (event) {
747 	case ADV_OFF:
748 		pi->pi_adv_state = NO_ADV;
749 		return (TIMER_INFINITY);
750 
751 	case START_INIT_ADV:
752 		if (pi->pi_adv_state == INIT_ADV)
753 			return (pi->pi_adv_time_left);
754 		pi->pi_adv_count = ND_MAX_INITIAL_RTR_ADVERTISEMENTS;
755 		pi->pi_adv_time_left = 0;
756 		pi->pi_adv_state = INIT_ADV;
757 		break;	/* send advertisement */
758 
759 	case START_FINAL_ADV:
760 		if (pi->pi_adv_state == NO_ADV)
761 			return (TIMER_INFINITY);
762 		if (pi->pi_adv_state == FINAL_ADV)
763 			return (pi->pi_adv_time_left);
764 		pi->pi_adv_count = ND_MAX_FINAL_RTR_ADVERTISEMENTS;
765 		pi->pi_adv_time_left = 0;
766 		pi->pi_adv_state = FINAL_ADV;
767 		break;	/* send advertisement */
768 
769 	case RECEIVED_SOLICIT:
770 		if (pi->pi_adv_state == NO_ADV)
771 			return (TIMER_INFINITY);
772 		if (pi->pi_adv_state == SOLICIT_ADV) {
773 			if (pi->pi_adv_time_left != 0)
774 				return (pi->pi_adv_time_left);
775 			break;
776 		}
777 		delay = GET_RANDOM(0, ND_MAX_RA_DELAY_TIME);
778 		if (delay < pi->pi_adv_time_left)
779 			pi->pi_adv_time_left = delay;
780 		if (pi->pi_adv_time_since_sent < ND_MIN_DELAY_BETWEEN_RAS) {
781 			/*
782 			 * Send an advertisement (ND_MIN_DELAY_BETWEEN_RAS
783 			 * plus random delay) after the previous
784 			 * advertisement was sent.
785 			 */
786 			pi->pi_adv_time_left = delay +
787 			    ND_MIN_DELAY_BETWEEN_RAS -
788 			    pi->pi_adv_time_since_sent;
789 		}
790 		pi->pi_adv_state = SOLICIT_ADV;
791 		break;
792 
793 	case ADV_TIMER:
794 		if (pi->pi_adv_state == NO_ADV)
795 			return (TIMER_INFINITY);
796 		/* Decrease time left */
797 		if (pi->pi_adv_time_left >= elapsed)
798 			pi->pi_adv_time_left -= elapsed;
799 		else
800 			pi->pi_adv_time_left = 0;
801 
802 		/* Increase time since last advertisement was sent */
803 		pi->pi_adv_time_since_sent += elapsed;
804 		break;
805 	default:
806 		logmsg(LOG_ERR, "advertise_event: Unknown event %d\n",
807 		    (int)event);
808 		return (TIMER_INFINITY);
809 	}
810 
811 	if (pi->pi_adv_time_left != 0)
812 		return (pi->pi_adv_time_left);
813 
814 	/* Send advertisement and calculate next time to send */
815 	if (pi->pi_adv_state == FINAL_ADV) {
816 		/* Omit the prefixes */
817 		advertise(&v6allnodes, pi, _B_TRUE);
818 	} else {
819 		advertise(&v6allnodes, pi, _B_FALSE);
820 	}
821 	pi->pi_adv_time_since_sent = 0;
822 
823 	switch (pi->pi_adv_state) {
824 	case SOLICIT_ADV:
825 		/*
826 		 * The solicited advertisement has been sent.
827 		 * Revert to periodic advertisements.
828 		 */
829 		pi->pi_adv_state = REG_ADV;
830 		/* FALLTHRU */
831 	case REG_ADV:
832 		pi->pi_adv_time_left =
833 		    GET_RANDOM(1000 * pi->pi_MinRtrAdvInterval,
834 		    1000 * pi->pi_MaxRtrAdvInterval);
835 		break;
836 
837 	case INIT_ADV:
838 		if (--pi->pi_adv_count > 0) {
839 			delay = GET_RANDOM(1000 * pi->pi_MinRtrAdvInterval,
840 			    1000 * pi->pi_MaxRtrAdvInterval);
841 			if (delay > ND_MAX_INITIAL_RTR_ADVERT_INTERVAL)
842 				delay = ND_MAX_INITIAL_RTR_ADVERT_INTERVAL;
843 			pi->pi_adv_time_left = delay;
844 		} else {
845 			pi->pi_adv_time_left =
846 			    GET_RANDOM(1000 * pi->pi_MinRtrAdvInterval,
847 			    1000 * pi->pi_MaxRtrAdvInterval);
848 			pi->pi_adv_state = REG_ADV;
849 		}
850 		break;
851 
852 	case FINAL_ADV:
853 		if (--pi->pi_adv_count > 0) {
854 			pi->pi_adv_time_left =
855 			    ND_MAX_INITIAL_RTR_ADVERT_INTERVAL;
856 		} else {
857 			pi->pi_adv_state = NO_ADV;
858 		}
859 		break;
860 	}
861 	if (pi->pi_adv_state != NO_ADV)
862 		return (pi->pi_adv_time_left);
863 	else
864 		return (TIMER_INFINITY);
865 }
866 
867 /*
868  * Router solicitation state machine. Used for everything but timer
869  * events which use solicit_event directly.
870  */
871 void
872 check_to_solicit(struct phyint *pi, enum solicit_events event)
873 {
874 	uint_t delay;
875 	enum solicit_states old_state = pi->pi_sol_state;
876 
877 	if (debug & D_STATE) {
878 		logmsg(LOG_DEBUG, "check_to_solicit(%s, %d) state %d\n",
879 		    pi->pi_name, (int)event, (int)old_state);
880 	}
881 	delay = solicit_event(pi, event, 0);
882 	if (delay != TIMER_INFINITY) {
883 		/* Make sure the global next event is updated */
884 		timer_schedule(delay);
885 	}
886 
887 	if (debug & D_STATE) {
888 		logmsg(LOG_DEBUG, "check_to_solicit(%s, %d) state %d -> %d\n",
889 		    pi->pi_name, (int)event, (int)old_state,
890 		    (int)pi->pi_sol_state);
891 	}
892 }
893 
894 static void
895 daemonize_ndpd(void)
896 {
897 	FILE *pidfp;
898 	mode_t pidmode = (S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH); /* 0644 */
899 	struct itimerval it;
900 	boolean_t timerval = _B_TRUE;
901 
902 	/*
903 	 * Need to get current timer settings so they can be restored
904 	 * after the fork(), as the it_value and it_interval values for
905 	 * the ITIMER_REAL timer are reset to 0 in the child process.
906 	 */
907 	if (getitimer(ITIMER_REAL, &it) < 0) {
908 		if (debug & D_TIMER)
909 			logmsg(LOG_DEBUG,
910 			    "daemonize_ndpd: failed to get itimerval\n");
911 		timerval = _B_FALSE;
912 	}
913 
914 	/* Daemonize. */
915 	switch (fork()) {
916 	case 0:
917 		/* Child */
918 		break;
919 	case -1:
920 		logperror("fork");
921 		exit(1);
922 	default:
923 		/* Parent */
924 		_exit(0);
925 	}
926 
927 	/* Store our process id, blow away any existing file if it exists. */
928 	if ((pidfp = fopen(PATH_PID, "w")) == NULL) {
929 		(void) fprintf(stderr, "%s: unable to open " PATH_PID ": %s\n",
930 		    argv0[0], strerror(errno));
931 	} else {
932 		(void) fprintf(pidfp, "%ld\n", getpid());
933 		(void) fclose(pidfp);
934 		(void) chmod(PATH_PID, pidmode);
935 	}
936 
937 	(void) close(0);
938 	(void) close(1);
939 	(void) close(2);
940 
941 	(void) chdir("/");
942 	(void) open("/dev/null", O_RDWR);
943 	(void) dup2(0, 1);
944 	(void) dup2(0, 2);
945 	(void) setsid();
946 
947 	already_daemonized = _B_TRUE;
948 
949 	/*
950 	 * Restore timer values, if we were able to save them; if not,
951 	 * check and set the right value by calling run_timeouts().
952 	 */
953 	if (timerval) {
954 		if (setitimer(ITIMER_REAL, &it, NULL) < 0) {
955 			logperror("daemonize_ndpd: setitimer");
956 			exit(2);
957 		}
958 	} else {
959 		run_timeouts();
960 	}
961 }
962 
963 /*
964  * Check to see if the time is right to daemonize.  The right time is when:
965  *
966  * 1.  We haven't already daemonized.
967  * 2.  We are not in debug mode.
968  * 3.  All interfaces are marked IFF_NOXMIT.
969  * 4.  All non-router interfaces have their prefixes set up and we're
970  *     done sending router solicitations on those interfaces without
971  *     prefixes.
972  */
973 static void
974 check_daemonize(void)
975 {
976 	struct phyint		*pi;
977 
978 	if (already_daemonized || debug != 0)
979 		return;
980 
981 	for (pi = phyints; pi != NULL; pi = pi->pi_next) {
982 		if (!(pi->pi_flags & IFF_NOXMIT))
983 			break;
984 	}
985 
986 	/*
987 	 * If we can't transmit on any of the interfaces there is no reason
988 	 * to hold up progress.
989 	 */
990 	if (pi == NULL) {
991 		daemonize_ndpd();
992 		return;
993 	}
994 
995 	/* Check all interfaces.  If any are still soliciting, just return. */
996 	for (pi = phyints; pi != NULL; pi = pi->pi_next) {
997 		if (pi->pi_AdvSendAdvertisements ||
998 		    !(pi->pi_kernel_state & PI_PRESENT))
999 			continue;
1000 
1001 		if (pi->pi_sol_state == INIT_SOLICIT)
1002 			return;
1003 	}
1004 
1005 	daemonize_ndpd();
1006 }
1007 
1008 /*
1009  * Router solicitation state machine.
1010  * Return the number of milliseconds until next timeout (TIMER_INFINITY
1011  * if never).
1012  * For the SOL_TIMER event the caller passes in the number of milliseconds
1013  * since the last timer event in the 'elapsed' parameter.
1014  */
1015 uint_t
1016 solicit_event(struct phyint *pi, enum solicit_events event, uint_t elapsed)
1017 {
1018 	if (debug & D_STATE) {
1019 		logmsg(LOG_DEBUG, "solicit_event(%s, %d, %d) state %d\n",
1020 		    pi->pi_name, (int)event, elapsed, (int)pi->pi_sol_state);
1021 	}
1022 
1023 	if (pi->pi_AdvSendAdvertisements)
1024 		return (TIMER_INFINITY);
1025 	if (pi->pi_flags & IFF_NORTEXCH) {
1026 		if (debug & D_PKTOUT) {
1027 			logmsg(LOG_DEBUG, "Suppress sending RS packet on %s "
1028 			    "(no route exchange on interface)\n",
1029 			    pi->pi_name);
1030 		}
1031 		return (TIMER_INFINITY);
1032 	}
1033 
1034 	switch (event) {
1035 	case SOLICIT_OFF:
1036 		pi->pi_sol_state = NO_SOLICIT;
1037 		check_daemonize();
1038 		return (TIMER_INFINITY);
1039 
1040 	case SOLICIT_DONE:
1041 		pi->pi_sol_state = DONE_SOLICIT;
1042 		check_daemonize();
1043 		return (TIMER_INFINITY);
1044 
1045 	case RESTART_INIT_SOLICIT:
1046 		/*
1047 		 * This event allows us to start solicitation over again
1048 		 * without losing the RA flags.  We start solicitation over
1049 		 * when we are missing an interface prefix for a newly-
1050 		 * encountered DHCP interface.
1051 		 */
1052 		if (pi->pi_sol_state == INIT_SOLICIT)
1053 			return (pi->pi_sol_time_left);
1054 		pi->pi_sol_count = ND_MAX_RTR_SOLICITATIONS;
1055 		pi->pi_sol_time_left =
1056 		    GET_RANDOM(0, ND_MAX_RTR_SOLICITATION_DELAY);
1057 		pi->pi_sol_state = INIT_SOLICIT;
1058 		break;
1059 
1060 	case START_INIT_SOLICIT:
1061 		if (pi->pi_sol_state == INIT_SOLICIT)
1062 			return (pi->pi_sol_time_left);
1063 		pi->pi_ra_flags = 0;
1064 		pi->pi_sol_count = ND_MAX_RTR_SOLICITATIONS;
1065 		pi->pi_sol_time_left =
1066 		    GET_RANDOM(0, ND_MAX_RTR_SOLICITATION_DELAY);
1067 		pi->pi_sol_state = INIT_SOLICIT;
1068 		break;
1069 
1070 	case SOL_TIMER:
1071 		if (pi->pi_sol_state == NO_SOLICIT)
1072 			return (TIMER_INFINITY);
1073 		/* Decrease time left */
1074 		if (pi->pi_sol_time_left >= elapsed)
1075 			pi->pi_sol_time_left -= elapsed;
1076 		else
1077 			pi->pi_sol_time_left = 0;
1078 		break;
1079 	default:
1080 		logmsg(LOG_ERR, "solicit_event: Unknown event %d\n",
1081 		    (int)event);
1082 		return (TIMER_INFINITY);
1083 	}
1084 
1085 	if (pi->pi_sol_time_left != 0)
1086 		return (pi->pi_sol_time_left);
1087 
1088 	/* Send solicitation and calculate next time */
1089 	switch (pi->pi_sol_state) {
1090 	case INIT_SOLICIT:
1091 		solicit(&v6allrouters, pi);
1092 		if (--pi->pi_sol_count == 0) {
1093 			if (debug & D_STATE) {
1094 				logmsg(LOG_DEBUG, "solicit_event: no routers "
1095 				    "found on %s; assuming default flags\n",
1096 				    pi->pi_name);
1097 			}
1098 			if (pi->pi_StatefulAddrConf) {
1099 				pi->pi_ra_flags |= ND_RA_FLAG_MANAGED |
1100 				    ND_RA_FLAG_OTHER;
1101 				start_dhcp(pi);
1102 			}
1103 			pi->pi_sol_state = DONE_SOLICIT;
1104 			check_daemonize();
1105 			return (TIMER_INFINITY);
1106 		}
1107 		pi->pi_sol_time_left = ND_RTR_SOLICITATION_INTERVAL;
1108 		return (pi->pi_sol_time_left);
1109 	case NO_SOLICIT:
1110 	case DONE_SOLICIT:
1111 		return (TIMER_INFINITY);
1112 	default:
1113 		return (pi->pi_sol_time_left);
1114 	}
1115 }
1116 
1117 /*
1118  * Timer mechanism using relative time (in milliseconds) from the
1119  * previous timer event. Timers exceeding TIMER_INFINITY milliseconds
1120  * will fire after TIMER_INFINITY milliseconds.
1121  */
1122 static uint_t timer_previous;	/* When last SIGALRM occurred */
1123 static uint_t timer_next;	/* Currently scheduled timeout */
1124 
1125 static void
1126 timer_init(void)
1127 {
1128 	timer_previous = getcurrenttime();
1129 	timer_next = TIMER_INFINITY;
1130 	run_timeouts();
1131 }
1132 
1133 /*
1134  * Make sure the next SIGALRM occurs delay milliseconds from the current
1135  * time if not earlier.
1136  * Handles getcurrenttime (32 bit integer holding milliseconds) wraparound
1137  * by treating differences greater than 0x80000000 as negative.
1138  */
1139 void
1140 timer_schedule(uint_t delay)
1141 {
1142 	uint_t now;
1143 	struct itimerval itimerval;
1144 
1145 	now = getcurrenttime();
1146 	if (debug & D_TIMER) {
1147 		logmsg(LOG_DEBUG, "timer_schedule(%u): now %u next %u\n",
1148 		    delay, now, timer_next);
1149 	}
1150 	/* Will this timer occur before the currently scheduled SIGALRM? */
1151 	if (delay >= timer_next - now) {
1152 		if (debug & D_TIMER) {
1153 			logmsg(LOG_DEBUG, "timer_schedule(%u): no action - "
1154 			    "next in %u ms\n",
1155 			    delay, timer_next - now);
1156 		}
1157 		return;
1158 	}
1159 	if (delay == 0) {
1160 		/* Minimum allowed delay */
1161 		delay = 1;
1162 	}
1163 	timer_next = now + delay;
1164 
1165 	itimerval.it_value.tv_sec = delay / 1000;
1166 	itimerval.it_value.tv_usec = (delay % 1000) * 1000;
1167 	itimerval.it_interval.tv_sec = 0;
1168 	itimerval.it_interval.tv_usec = 0;
1169 	if (debug & D_TIMER) {
1170 		logmsg(LOG_DEBUG, "timer_schedule(%u): sec %lu usec %lu\n",
1171 		    delay,
1172 		    itimerval.it_value.tv_sec, itimerval.it_value.tv_usec);
1173 	}
1174 	if (setitimer(ITIMER_REAL, &itimerval, NULL) < 0) {
1175 		logperror("timer_schedule: setitimer");
1176 		exit(2);
1177 	}
1178 }
1179 
1180 /*
1181  * Conditional running of timer. If more than 'minimal_time' millseconds
1182  * since the timer routines were last run we run them.
1183  * Used when packets arrive.
1184  */
1185 static void
1186 conditional_run_timeouts(uint_t minimal_time)
1187 {
1188 	uint_t now;
1189 	uint_t elapsed;
1190 
1191 	now = getcurrenttime();
1192 	elapsed = now - timer_previous;
1193 	if (elapsed > minimal_time) {
1194 		if (debug & D_TIMER) {
1195 			logmsg(LOG_DEBUG, "conditional_run_timeouts: "
1196 			    "elapsed %d\n", elapsed);
1197 		}
1198 		run_timeouts();
1199 	}
1200 }
1201 
1202 /*
1203  * Timer has fired.
1204  * Determine when the next timer event will occur by asking all
1205  * the timer routines.
1206  * Should not be called from a timer routine but in some cases this is
1207  * done because the code doesn't know that e.g. it was called from
1208  * ifconfig_timer(). In this case the nested run_timeouts will just return but
1209  * the running run_timeouts will ensure to call all the timer functions by
1210  * looping once more.
1211  */
1212 static void
1213 run_timeouts(void)
1214 {
1215 	uint_t now;
1216 	uint_t elapsed;
1217 	uint_t next;
1218 	uint_t nexti;
1219 	struct phyint *pi;
1220 	struct phyint *next_pi;
1221 	struct prefix *pr;
1222 	struct prefix *next_pr;
1223 	struct adv_prefix *adv_pr;
1224 	struct adv_prefix *next_adv_pr;
1225 	struct router *dr;
1226 	struct router *next_dr;
1227 	static boolean_t timeout_running;
1228 	static boolean_t do_retry;
1229 
1230 	if (timeout_running) {
1231 		if (debug & D_TIMER)
1232 			logmsg(LOG_DEBUG, "run_timeouts: nested call\n");
1233 		do_retry = _B_TRUE;
1234 		return;
1235 	}
1236 	timeout_running = _B_TRUE;
1237 retry:
1238 	/* How much time since the last time we were called? */
1239 	now = getcurrenttime();
1240 	elapsed = now - timer_previous;
1241 	timer_previous = now;
1242 
1243 	if (debug & D_TIMER)
1244 		logmsg(LOG_DEBUG, "run_timeouts: elapsed %d\n", elapsed);
1245 
1246 	next = TIMER_INFINITY;
1247 	for (pi = phyints; pi != NULL; pi = next_pi) {
1248 		next_pi = pi->pi_next;
1249 		nexti = phyint_timer(pi, elapsed);
1250 		if (nexti != TIMER_INFINITY && nexti < next)
1251 			next = nexti;
1252 		if (debug & D_TIMER) {
1253 			logmsg(LOG_DEBUG, "run_timeouts (pi %s): %d -> %u ms\n",
1254 			    pi->pi_name, nexti, next);
1255 		}
1256 		for (pr = pi->pi_prefix_list; pr != NULL; pr = next_pr) {
1257 			next_pr = pr->pr_next;
1258 			nexti = prefix_timer(pr, elapsed);
1259 			if (nexti != TIMER_INFINITY && nexti < next)
1260 				next = nexti;
1261 			if (debug & D_TIMER) {
1262 				logmsg(LOG_DEBUG, "run_timeouts (pr %s): "
1263 				    "%d -> %u ms\n", pr->pr_name, nexti, next);
1264 			}
1265 		}
1266 		for (adv_pr = pi->pi_adv_prefix_list; adv_pr != NULL;
1267 		    adv_pr = next_adv_pr) {
1268 			next_adv_pr = adv_pr->adv_pr_next;
1269 			nexti = adv_prefix_timer(adv_pr, elapsed);
1270 			if (nexti != TIMER_INFINITY && nexti < next)
1271 				next = nexti;
1272 			if (debug & D_TIMER) {
1273 				logmsg(LOG_DEBUG, "run_timeouts "
1274 				    "(adv pr on %s): %d -> %u ms\n",
1275 				    adv_pr->adv_pr_physical->pi_name,
1276 				    nexti, next);
1277 			}
1278 		}
1279 		for (dr = pi->pi_router_list; dr != NULL; dr = next_dr) {
1280 			next_dr = dr->dr_next;
1281 			nexti = router_timer(dr, elapsed);
1282 			if (nexti != TIMER_INFINITY && nexti < next)
1283 				next = nexti;
1284 			if (debug & D_TIMER) {
1285 				logmsg(LOG_DEBUG, "run_timeouts (dr): "
1286 				    "%d -> %u ms\n", nexti, next);
1287 			}
1288 		}
1289 		if (pi->pi_TmpAddrsEnabled) {
1290 			nexti = tmptoken_timer(pi, elapsed);
1291 			if (nexti != TIMER_INFINITY && nexti < next)
1292 				next = nexti;
1293 			if (debug & D_TIMER) {
1294 				logmsg(LOG_DEBUG, "run_timeouts (tmp on %s): "
1295 				    "%d -> %u ms\n", pi->pi_name, nexti, next);
1296 			}
1297 		}
1298 	}
1299 	/*
1300 	 * Make sure the timer functions are run at least once
1301 	 * an hour.
1302 	 */
1303 	if (next == TIMER_INFINITY)
1304 		next = 3600 * 1000;	/* 1 hour */
1305 
1306 	if (debug & D_TIMER)
1307 		logmsg(LOG_DEBUG, "run_timeouts: %u ms\n", next);
1308 	timer_schedule(next);
1309 	if (do_retry) {
1310 		if (debug & D_TIMER)
1311 			logmsg(LOG_DEBUG, "run_timeouts: retry\n");
1312 		do_retry = _B_FALSE;
1313 		goto retry;
1314 	}
1315 	timeout_running = _B_FALSE;
1316 }
1317 
1318 static int eventpipe_read = -1;	/* Used for synchronous signal delivery */
1319 static int eventpipe_write = -1;
1320 
1321 /*
1322  * Ensure that signals are processed synchronously with the rest of
1323  * the code by just writing a one character signal number on the pipe.
1324  * The poll loop will pick this up and process the signal event.
1325  */
1326 static void
1327 sig_handler(int signo)
1328 {
1329 	uchar_t buf = (uchar_t)signo;
1330 
1331 	if (eventpipe_write == -1) {
1332 		logmsg(LOG_ERR, "sig_handler: no pipe\n");
1333 		return;
1334 	}
1335 	if (write(eventpipe_write, &buf, sizeof (buf)) < 0)
1336 		logperror("sig_handler: write");
1337 }
1338 
1339 /*
1340  * Pick up a signal "byte" from the pipe and process it.
1341  */
1342 static void
1343 in_signal(int fd)
1344 {
1345 	uchar_t buf;
1346 	struct phyint *pi;
1347 	struct phyint *next_pi;
1348 
1349 	switch (read(fd, &buf, sizeof (buf))) {
1350 	case -1:
1351 		logperror("in_signal: read");
1352 		exit(1);
1353 		/* NOTREACHED */
1354 	case 1:
1355 		break;
1356 	case 0:
1357 		logmsg(LOG_ERR, "in_signal: read eof\n");
1358 		exit(1);
1359 		/* NOTREACHED */
1360 	default:
1361 		logmsg(LOG_ERR, "in_signal: read > 1\n");
1362 		exit(1);
1363 	}
1364 
1365 	if (debug & D_TIMER)
1366 		logmsg(LOG_DEBUG, "in_signal() got %d\n", buf);
1367 
1368 	switch (buf) {
1369 	case SIGALRM:
1370 		if (debug & D_TIMER) {
1371 			uint_t now = getcurrenttime();
1372 
1373 			logmsg(LOG_DEBUG, "in_signal(SIGALRM) delta %u\n",
1374 			    now - timer_next);
1375 		}
1376 		timer_next = TIMER_INFINITY;
1377 		run_timeouts();
1378 		break;
1379 	case SIGHUP:
1380 		/* Re-read config file by exec'ing ourselves */
1381 		for (pi = phyints; pi != NULL; pi = next_pi) {
1382 			next_pi = pi->pi_next;
1383 			if (pi->pi_AdvSendAdvertisements)
1384 				check_to_advertise(pi, START_FINAL_ADV);
1385 
1386 			phyint_delete(pi);
1387 		}
1388 
1389 		/*
1390 		 * Prevent fd leaks.  Everything gets re-opened at start-up
1391 		 * time.  0, 1, and 2 are closed and re-opened as
1392 		 * /dev/null, so we'll leave those open.
1393 		 */
1394 		closefrom(3);
1395 
1396 		logmsg(LOG_ERR, "SIGHUP: restart and reread config file\n");
1397 		(void) execv(argv0[0], argv0);
1398 		(void) unlink(PATH_PID);
1399 		_exit(0177);
1400 		/* NOTREACHED */
1401 	case SIGUSR1:
1402 		logmsg(LOG_DEBUG, "Printing configuration:\n");
1403 		phyint_print_all();
1404 		break;
1405 	case SIGINT:
1406 	case SIGTERM:
1407 	case SIGQUIT:
1408 		for (pi = phyints; pi != NULL; pi = next_pi) {
1409 			next_pi = pi->pi_next;
1410 			if (pi->pi_AdvSendAdvertisements)
1411 				check_to_advertise(pi, START_FINAL_ADV);
1412 
1413 			phyint_delete(pi);
1414 		}
1415 		(void) unlink(NDPD_SNMP_SOCKET);
1416 		(void) unlink(PATH_PID);
1417 		exit(0);
1418 		/* NOTREACHED */
1419 	case 255:
1420 		/*
1421 		 * Special "signal" from looback_ra_enqueue.
1422 		 * Handle any queued loopback router advertisements.
1423 		 */
1424 		loopback_ra_dequeue();
1425 		break;
1426 	default:
1427 		logmsg(LOG_ERR, "in_signal: unknown signal: %d\n", buf);
1428 	}
1429 }
1430 
1431 /*
1432  * Create pipe for signal delivery and set up signal handlers.
1433  */
1434 static void
1435 setup_eventpipe(void)
1436 {
1437 	int fds[2];
1438 	struct sigaction act;
1439 
1440 	if ((pipe(fds)) < 0) {
1441 		logperror("setup_eventpipe: pipe");
1442 		exit(1);
1443 	}
1444 	eventpipe_read = fds[0];
1445 	eventpipe_write = fds[1];
1446 	if (poll_add(eventpipe_read) == -1) {
1447 		exit(1);
1448 	}
1449 	act.sa_handler = sig_handler;
1450 	act.sa_flags = SA_RESTART;
1451 	(void) sigaction(SIGALRM, &act, NULL);
1452 
1453 	(void) sigset(SIGHUP, sig_handler);
1454 	(void) sigset(SIGUSR1, sig_handler);
1455 	(void) sigset(SIGTERM, sig_handler);
1456 	(void) sigset(SIGINT, sig_handler);
1457 	(void) sigset(SIGQUIT, sig_handler);
1458 }
1459 
1460 /*
1461  * Create a routing socket for receiving RTM_IFINFO messages and initialize
1462  * the routing socket message header and as much of the sockaddrs as possible.
1463  */
1464 static int
1465 setup_rtsock(void)
1466 {
1467 	int s;
1468 	int ret;
1469 	char *cp;
1470 	struct sockaddr_in6 *sin6;
1471 
1472 	s = socket(PF_ROUTE, SOCK_RAW, AF_INET6);
1473 	if (s == -1) {
1474 		logperror("socket(PF_ROUTE)");
1475 		exit(1);
1476 	}
1477 	ret = fcntl(s, F_SETFL, O_NDELAY|O_NONBLOCK);
1478 	if (ret < 0) {
1479 		logperror("fcntl(O_NDELAY)");
1480 		exit(1);
1481 	}
1482 	if (poll_add(s) == -1) {
1483 		exit(1);
1484 	}
1485 
1486 	/*
1487 	 * Allocate storage for the routing socket message.
1488 	 */
1489 	rt_msg = (struct rt_msghdr *)malloc(NDP_RTM_MSGLEN);
1490 	if (rt_msg == NULL) {
1491 		logperror("malloc");
1492 		exit(1);
1493 	}
1494 
1495 	/*
1496 	 * Initialize the routing socket message by zero-filling it and then
1497 	 * setting the fields where are constant through the lifetime of the
1498 	 * process.
1499 	 */
1500 	bzero(rt_msg, NDP_RTM_MSGLEN);
1501 	rt_msg->rtm_msglen = NDP_RTM_MSGLEN;
1502 	rt_msg->rtm_version = RTM_VERSION;
1503 	rt_msg->rtm_addrs = RTA_DST | RTA_GATEWAY | RTA_NETMASK | RTA_IFP;
1504 	rt_msg->rtm_pid = getpid();
1505 	if (rt_msg->rtm_pid < 0) {
1506 		logperror("getpid");
1507 		exit(1);
1508 	}
1509 
1510 	/*
1511 	 * The RTA_DST sockaddr does not change during the lifetime of the
1512 	 * process so it can be completely initialized at this time.
1513 	 */
1514 	cp = (char *)rt_msg + sizeof (struct rt_msghdr);
1515 	sin6 = (struct sockaddr_in6 *)cp;
1516 	sin6->sin6_family = AF_INET6;
1517 	sin6->sin6_addr = in6addr_any;
1518 
1519 	/*
1520 	 * Initialize the constant portion of the RTA_GATEWAY sockaddr.
1521 	 */
1522 	cp += sizeof (struct sockaddr_in6);
1523 	rta_gateway = (struct sockaddr_in6 *)cp;
1524 	rta_gateway->sin6_family = AF_INET6;
1525 
1526 	/*
1527 	 * The RTA_NETMASK sockaddr does not change during the lifetime of the
1528 	 * process so it can be completely initialized at this time.
1529 	 */
1530 	cp += sizeof (struct sockaddr_in6);
1531 	sin6 = (struct sockaddr_in6 *)cp;
1532 	sin6->sin6_family = AF_INET6;
1533 	sin6->sin6_addr = in6addr_any;
1534 
1535 	/*
1536 	 * Initialize the constant portion of the RTA_IFP sockaddr.
1537 	 */
1538 	cp += sizeof (struct sockaddr_in6);
1539 	rta_ifp = (struct sockaddr_dl *)cp;
1540 	rta_ifp->sdl_family = AF_LINK;
1541 
1542 	return (s);
1543 }
1544 
1545 static int
1546 setup_mibsock(void)
1547 {
1548 	int sock;
1549 	int ret;
1550 	int len;
1551 	struct sockaddr_un laddr;
1552 
1553 	sock = socket(AF_UNIX, SOCK_DGRAM, 0);
1554 	if (sock == -1) {
1555 		logperror("setup_mibsock: socket(AF_UNIX)");
1556 		exit(1);
1557 	}
1558 
1559 	bzero(&laddr, sizeof (laddr));
1560 	laddr.sun_family = AF_UNIX;
1561 
1562 	(void) strncpy(laddr.sun_path, NDPD_SNMP_SOCKET,
1563 	    sizeof (laddr.sun_path));
1564 	len = sizeof (struct sockaddr_un);
1565 
1566 	(void) unlink(NDPD_SNMP_SOCKET);
1567 	ret = bind(sock, (struct sockaddr *)&laddr, len);
1568 	if (ret < 0) {
1569 		logperror("setup_mibsock: bind\n");
1570 		exit(1);
1571 	}
1572 
1573 	ret = fcntl(sock, F_SETFL, O_NONBLOCK);
1574 	if (ret < 0) {
1575 		logperror("fcntl(O_NONBLOCK)");
1576 		exit(1);
1577 	}
1578 	if (poll_add(sock) == -1) {
1579 		exit(1);
1580 	}
1581 	return (sock);
1582 }
1583 
1584 /*
1585  * Retrieve one routing socket message. If RTM_IFINFO indicates
1586  * new phyint do a full scan of the interfaces. If RTM_IFINFO
1587  * indicates an existing phyint, only scan that phyint and associated
1588  * prefixes.
1589  */
1590 static void
1591 process_rtsock(int rtsock)
1592 {
1593 	int n;
1594 #define	MSG_SIZE	2048/8
1595 	int64_t msg[MSG_SIZE];
1596 	struct rt_msghdr *rtm;
1597 	struct if_msghdr *ifm;
1598 	struct phyint *pi;
1599 	struct prefix *pr;
1600 	boolean_t need_initifs = _B_FALSE;
1601 	boolean_t need_ifscan = _B_FALSE;
1602 	int64_t	ifscan_msg[10][MSG_SIZE];
1603 	int ifscan_index = 0;
1604 	int i;
1605 
1606 	/* Empty the rtsock and coealesce all the work that we have */
1607 	while (ifscan_index < 10) {
1608 		n = read(rtsock, msg, sizeof (msg));
1609 		if (n <= 0) {
1610 			/* No more messages */
1611 			break;
1612 		}
1613 		rtm = (struct rt_msghdr *)msg;
1614 		if (rtm->rtm_version != RTM_VERSION) {
1615 			logmsg(LOG_ERR,
1616 			    "process_rtsock: version %d not understood\n",
1617 			    rtm->rtm_version);
1618 			return;
1619 		}
1620 		switch (rtm->rtm_type) {
1621 		case RTM_NEWADDR:
1622 		case RTM_DELADDR:
1623 			/*
1624 			 * Some logical interface has changed - have to scan
1625 			 * everything to determine what actually changed.
1626 			 */
1627 			if (debug & D_IFSCAN) {
1628 				logmsg(LOG_DEBUG, "process_rtsock: "
1629 				    "message %d\n", rtm->rtm_type);
1630 			}
1631 			need_initifs = _B_TRUE;
1632 			break;
1633 		case RTM_IFINFO:
1634 			need_ifscan = _B_TRUE;
1635 			(void) memcpy(ifscan_msg[ifscan_index], rtm,
1636 			    sizeof (msg));
1637 			ifscan_index++;
1638 			/* Handled below */
1639 			break;
1640 		default:
1641 			/* Not interesting */
1642 			break;
1643 		}
1644 	}
1645 	/*
1646 	 * If we do full scan i.e initifs, we don't need to
1647 	 * scan a particular interface as we should have
1648 	 * done that as part of initifs.
1649 	 */
1650 	if (need_initifs) {
1651 		initifs(_B_FALSE);
1652 		return;
1653 	}
1654 
1655 	if (!need_ifscan)
1656 		return;
1657 
1658 	for (i = 0; i < ifscan_index; i++) {
1659 		ifm = (struct if_msghdr *)ifscan_msg[i];
1660 		if (debug & D_IFSCAN)
1661 			logmsg(LOG_DEBUG, "process_rtsock: index %d\n",
1662 			    ifm->ifm_index);
1663 
1664 		pi = phyint_lookup_on_index(ifm->ifm_index);
1665 		if (pi == NULL) {
1666 			/*
1667 			 * A new physical interface. Do a full scan of the
1668 			 * to catch any new logical interfaces.
1669 			 */
1670 			initifs(_B_FALSE);
1671 			return;
1672 		}
1673 
1674 		if (ifm->ifm_flags != pi->pi_flags) {
1675 			if (debug & D_IFSCAN) {
1676 				logmsg(LOG_DEBUG, "process_rtsock: clr for "
1677 				    "%s old flags 0x%x new flags 0x%x\n",
1678 				    pi->pi_name, pi->pi_flags, ifm->ifm_flags);
1679 			}
1680 		}
1681 
1682 
1683 		/*
1684 		 * Mark the interfaces so that we can find phyints and prefixes
1685 		 * which have disappeared from the kernel.
1686 		 * if_process will set pr_in_use when it finds the
1687 		 * interface in the kernel.
1688 		 * Before re-examining the state of the interfaces,
1689 		 * PI_PRESENT should be cleared from pi_kernel_state.
1690 		 */
1691 		pi->pi_kernel_state &= ~PI_PRESENT;
1692 		for (pr = pi->pi_prefix_list; pr != NULL; pr = pr->pr_next) {
1693 			pr->pr_in_use = _B_FALSE;
1694 		}
1695 
1696 		if (ifsock < 0) {
1697 			ifsock = socket(AF_INET6, SOCK_DGRAM, 0);
1698 			if (ifsock < 0) {
1699 				logperror("process_rtsock: socket");
1700 				return;
1701 			}
1702 		}
1703 		if_process(ifsock, pi->pi_name, _B_FALSE);
1704 		for (pr = pi->pi_prefix_list; pr != NULL; pr = pr->pr_next) {
1705 			if_process(ifsock, pr->pr_name, _B_FALSE);
1706 		}
1707 		/*
1708 		 * If interface (still) exists in kernel, set
1709 		 * pi_state to indicate that.
1710 		 */
1711 		if (pi->pi_kernel_state & PI_PRESENT) {
1712 			pi->pi_state |= PI_PRESENT;
1713 		}
1714 		check_if_removed(pi);
1715 		if (show_ifs)
1716 			phyint_print_all();
1717 	}
1718 }
1719 
1720 static void
1721 process_mibsock(int mibsock)
1722 {
1723 	struct phyint *pi;
1724 	socklen_t fromlen;
1725 	struct sockaddr_un from;
1726 	ndpd_info_t ndpd_info;
1727 	ssize_t len;
1728 	int command;
1729 
1730 	fromlen = (socklen_t)sizeof (from);
1731 	len = recvfrom(mibsock, &command, sizeof (int), 0,
1732 	    (struct sockaddr *)&from, &fromlen);
1733 
1734 	if (len < sizeof (int) || command != NDPD_SNMP_INFO_REQ) {
1735 		logperror("process_mibsock: bad command \n");
1736 		return;
1737 	}
1738 
1739 	ndpd_info.info_type = NDPD_SNMP_INFO_RESPONSE;
1740 	ndpd_info.info_version = NDPD_SNMP_INFO_VER;
1741 	ndpd_info.info_num_of_phyints = num_of_phyints;
1742 
1743 	(void) sendto(mibsock, &ndpd_info, sizeof (ndpd_info_t), 0,
1744 	    (struct sockaddr *)&from, fromlen);
1745 
1746 	for (pi = phyints; pi != NULL; pi = pi->pi_next) {
1747 		int prefixes;
1748 		int routers;
1749 		struct prefix   *prefix_list;
1750 		struct router   *router_list;
1751 		ndpd_phyint_info_t phyint;
1752 		ndpd_prefix_info_t prefix;
1753 		ndpd_router_info_t router;
1754 		/*
1755 		 * get number of prefixes
1756 		 */
1757 		routers = 0;
1758 		prefixes = 0;
1759 		prefix_list = pi->pi_prefix_list;
1760 		while (prefix_list != NULL) {
1761 			prefixes++;
1762 			prefix_list = prefix_list->pr_next;
1763 		}
1764 
1765 		/*
1766 		 * get number of routers
1767 		 */
1768 		router_list = pi->pi_router_list;
1769 		while (router_list != NULL) {
1770 			routers++;
1771 			router_list = router_list->dr_next;
1772 		}
1773 
1774 		phyint.phyint_info_type = NDPD_PHYINT_INFO;
1775 		phyint.phyint_info_version = NDPD_PHYINT_INFO_VER;
1776 		phyint.phyint_index = pi->pi_index;
1777 		bcopy(pi->pi_config,
1778 		    phyint.phyint_config, I_IFSIZE);
1779 		phyint.phyint_num_of_prefixes = prefixes;
1780 		phyint.phyint_num_of_routers = routers;
1781 		(void) sendto(mibsock, &phyint, sizeof (phyint), 0,
1782 		    (struct sockaddr *)&from, fromlen);
1783 
1784 		/*
1785 		 * Copy prefix information
1786 		 */
1787 
1788 		prefix_list = pi->pi_prefix_list;
1789 		while (prefix_list != NULL) {
1790 			prefix.prefix_info_type = NDPD_PREFIX_INFO;
1791 			prefix.prefix_info_version = NDPD_PREFIX_INFO_VER;
1792 			prefix.prefix_prefix = prefix_list->pr_prefix;
1793 			prefix.prefix_len = prefix_list->pr_prefix_len;
1794 			prefix.prefix_flags = prefix_list->pr_flags;
1795 			prefix.prefix_phyint_index = pi->pi_index;
1796 			prefix.prefix_ValidLifetime =
1797 			    prefix_list->pr_ValidLifetime;
1798 			prefix.prefix_PreferredLifetime =
1799 			    prefix_list->pr_PreferredLifetime;
1800 			prefix.prefix_OnLinkLifetime =
1801 			    prefix_list->pr_OnLinkLifetime;
1802 			prefix.prefix_OnLinkFlag =
1803 			    prefix_list->pr_OnLinkFlag;
1804 			prefix.prefix_AutonomousFlag =
1805 			    prefix_list->pr_AutonomousFlag;
1806 			(void) sendto(mibsock, &prefix, sizeof (prefix), 0,
1807 			    (struct sockaddr *)&from, fromlen);
1808 			prefix_list = prefix_list->pr_next;
1809 		}
1810 		/*
1811 		 * Copy router information
1812 		 */
1813 		router_list = pi->pi_router_list;
1814 		while (router_list != NULL) {
1815 			router.router_info_type = NDPD_ROUTER_INFO;
1816 			router.router_info_version = NDPD_ROUTER_INFO_VER;
1817 			router.router_address = router_list->dr_address;
1818 			router.router_lifetime = router_list->dr_lifetime;
1819 			router.router_phyint_index = pi->pi_index;
1820 			(void) sendto(mibsock, &router, sizeof (router), 0,
1821 			    (struct sockaddr *)&from, fromlen);
1822 			router_list = router_list->dr_next;
1823 		}
1824 	}
1825 }
1826 
1827 /*
1828  * Check whether the address formed by pr->pr_prefix and pi_token
1829  * exists in the kernel. Cannot call SIOCTMYADDR/ONLINK as it
1830  * does not check for down addresses. This function should not
1831  * be called for onlink prefixes.
1832  */
1833 static boolean_t
1834 is_address_present(struct phyint *pi, struct prefix *pr, uint64_t flags)
1835 {
1836 	int s;
1837 	in6_addr_t addr, *token;
1838 	int i;
1839 	int ret;
1840 	struct sockaddr_in6 sin6;
1841 
1842 	s = socket(AF_INET6, SOCK_DGRAM, 0);
1843 	if (s < 0) {
1844 		logperror("is_address_present: socket");
1845 		/*
1846 		 * By returning B_TRUE, we make the caller delete
1847 		 * the prefix from the internal table. In the worst
1848 		 * case the next RA will create the prefix.
1849 		 */
1850 		return (_B_TRUE);
1851 	}
1852 	if (flags & IFF_TEMPORARY)
1853 		token = &pi->pi_tmp_token;
1854 	else
1855 		token = &pi->pi_token;
1856 	for (i = 0; i < 16; i++) {
1857 		/*
1858 		 * prefix_create ensures that pr_prefix has all-zero
1859 		 * bits after prefixlen.
1860 		 */
1861 		addr.s6_addr[i] = pr->pr_prefix.s6_addr[i] | token->s6_addr[i];
1862 	}
1863 	(void) memset(&sin6, 0, sizeof (struct sockaddr_in6));
1864 	sin6.sin6_family = AF_INET6;
1865 	sin6.sin6_addr = addr;
1866 	ret = bind(s, (struct sockaddr *)&sin6, sizeof (struct sockaddr_in6));
1867 	(void) close(s);
1868 	if (ret < 0 && errno == EADDRNOTAVAIL)
1869 		return (_B_FALSE);
1870 	else
1871 		return (_B_TRUE);
1872 }
1873 
1874 /*
1875  * Look if the phyint or one of its prefixes have been removed from
1876  * the kernel and take appropriate action.
1877  * Uses {pi,pr}_in_use.
1878  */
1879 static void
1880 check_if_removed(struct phyint *pi)
1881 {
1882 	struct prefix *pr;
1883 	struct prefix *next_pr;
1884 
1885 	/*
1886 	 * Detect phyints that have been removed from the kernel.
1887 	 * Since we can't recreate it here (would require ifconfig plumb
1888 	 * logic) we just terminate use of that phyint.
1889 	 */
1890 	if (!(pi->pi_kernel_state & PI_PRESENT) &&
1891 	    (pi->pi_state & PI_PRESENT)) {
1892 		logmsg(LOG_ERR, "Interface %s has been removed from kernel. "
1893 		    "in.ndpd will no longer use it\n", pi->pi_name);
1894 		/*
1895 		 * Clear state so that should the phyint reappear
1896 		 * we will start with initial advertisements or
1897 		 * solicitations.
1898 		 */
1899 		phyint_cleanup(pi);
1900 	}
1901 	/*
1902 	 * Detect prefixes which are removed.
1903 	 *
1904 	 * We remove the prefix in all of the following cases :
1905 	 *
1906 	 * 1) Static prefixes are not the ones we create. So,
1907 	 *    just remove it from our tables.
1908 	 *
1909 	 * 2) On-link prefixes potentially move to a different
1910 	 *    phyint during failover. As it does not have
1911 	 *    an address, we can't use the logic in is_address_present
1912 	 *    to detect whether it is present in the kernel or not.
1913 	 *    Thus when it is manually removed we don't recreate it.
1914 	 *
1915 	 * 3) If there is a token mis-match and this prefix is not
1916 	 *    in the kernel, it means we don't need this prefix on
1917 	 *    this interface anymore. It must have been moved to a
1918 	 *    different interface by in.mpathd. This normally
1919 	 *    happens after a failover followed by a failback (or
1920 	 *    another failover) and we re-read the network
1921 	 *    configuration. For the failover from A to B, we would
1922 	 *    have created state on B about A's address, which will
1923 	 *    not be in use after the subsequent failback. So, we
1924 	 *    remove that prefix here.
1925 	 *
1926 	 * 4) If the physical interface is not present, then remove
1927 	 *    the prefix. In the cases where we are advertising
1928 	 *    prefixes, the state is kept in advertisement prefix and
1929 	 *    hence we can delete the prefix.
1930 	 *
1931 	 * 5) Similar to case (3), when we failover from A to B, the
1932 	 *    prefix in A will not be in use as it has been moved to B.
1933 	 *    We will delete it from our tables and recreate it when
1934 	 *    it fails back. is_address_present makes sure that the
1935 	 *    address is still valid in kernel.
1936 	 *
1937 	 * If none of the above is true, we recreate the prefix as it
1938 	 * has been manually removed. We do it only when the interface
1939 	 * is not FAILED or INACTIVE or OFFLINE.
1940 	 */
1941 	for (pr = pi->pi_prefix_list; pr != NULL; pr = next_pr) {
1942 		next_pr = pr->pr_next;
1943 		if (!pr->pr_in_use) {
1944 			/* Clear PR_AUTO and PR_ONLINK */
1945 			pr->pr_kernel_state &= PR_STATIC;
1946 			if ((pr->pr_state & PR_STATIC) ||
1947 			    !(pr->pr_state & PR_AUTO) ||
1948 			    !(prefix_token_match(pi, pr, pr->pr_flags)) ||
1949 			    (!(pi->pi_kernel_state & PI_PRESENT)) ||
1950 			    (is_address_present(pi, pr, pr->pr_flags))) {
1951 				prefix_delete(pr);
1952 			} else if (!(pi->pi_flags &
1953 			    (IFF_FAILED|IFF_INACTIVE|IFF_OFFLINE)) &&
1954 			    pr->pr_state != pr->pr_kernel_state) {
1955 				pr->pr_name[0] = '\0';
1956 				logmsg(LOG_INFO, "Prefix manually removed "
1957 				    "on %s - recreating it!\n",
1958 				    pi->pi_name);
1959 				prefix_update_k(pr);
1960 			}
1961 		}
1962 	}
1963 }
1964 
1965 
1966 /*
1967  * Queuing mechanism for router advertisements that are sent by in.ndpd
1968  * and that also need to be processed by in.ndpd.
1969  * Uses "signal number" 255 to indicate to the main poll loop
1970  * that there is something to dequeue and send to incomining_ra().
1971  */
1972 struct raq {
1973 	struct raq	*raq_next;
1974 	struct phyint	*raq_pi;
1975 	int		raq_packetlen;
1976 	uchar_t		*raq_packet;
1977 };
1978 static struct raq *raq_head = NULL;
1979 
1980 /*
1981  * Allocate a struct raq and memory for the packet.
1982  * Send signal 255 to have poll dequeue.
1983  */
1984 static void
1985 loopback_ra_enqueue(struct phyint *pi, struct nd_router_advert *ra, int len)
1986 {
1987 	struct raq *raq;
1988 	struct raq **raqp;
1989 
1990 	if (no_loopback)
1991 		return;
1992 
1993 	if (debug & D_PKTOUT)
1994 		logmsg(LOG_DEBUG, "loopback_ra_enqueue for %s\n", pi->pi_name);
1995 
1996 	raq = calloc(sizeof (struct raq), 1);
1997 	if (raq == NULL) {
1998 		logmsg(LOG_ERR, "loopback_ra_enqueue: out of memory\n");
1999 		return;
2000 	}
2001 	raq->raq_packet = malloc(len);
2002 	if (raq->raq_packet == NULL) {
2003 		free(raq);
2004 		logmsg(LOG_ERR, "loopback_ra_enqueue: out of memory\n");
2005 		return;
2006 	}
2007 	bcopy(ra, raq->raq_packet, len);
2008 	raq->raq_packetlen = len;
2009 	raq->raq_pi = pi;
2010 
2011 	/* Tail insert */
2012 	raqp = &raq_head;
2013 	while (*raqp != NULL)
2014 		raqp = &((*raqp)->raq_next);
2015 	*raqp = raq;
2016 
2017 	/* Signal for poll loop */
2018 	sig_handler(255);
2019 }
2020 
2021 /*
2022  * Dequeue and process all queued advertisements.
2023  */
2024 static void
2025 loopback_ra_dequeue(void)
2026 {
2027 	struct sockaddr_in6 from = IN6ADDR_LOOPBACK_INIT;
2028 	struct raq *raq;
2029 
2030 	if (debug & D_PKTIN)
2031 		logmsg(LOG_DEBUG, "loopback_ra_dequeue()\n");
2032 
2033 	while ((raq = raq_head) != NULL) {
2034 		raq_head = raq->raq_next;
2035 		raq->raq_next = NULL;
2036 
2037 		if (debug & D_PKTIN) {
2038 			logmsg(LOG_DEBUG, "loopback_ra_dequeue for %s\n",
2039 			    raq->raq_pi->pi_name);
2040 		}
2041 
2042 		incoming_ra(raq->raq_pi,
2043 		    (struct nd_router_advert *)raq->raq_packet,
2044 		    raq->raq_packetlen, &from, _B_TRUE);
2045 		free(raq->raq_packet);
2046 		free(raq);
2047 	}
2048 }
2049 
2050 
2051 static void
2052 usage(char *cmd)
2053 {
2054 	(void) fprintf(stderr,
2055 	    "usage: %s [ -adt ] [-f <config file>]\n", cmd);
2056 }
2057 
2058 int
2059 main(int argc, char *argv[])
2060 {
2061 	int i;
2062 	struct phyint *pi;
2063 	int c;
2064 	char *config_file = PATH_NDPD_CONF;
2065 	boolean_t file_required = _B_FALSE;
2066 
2067 	argv0 = argv;
2068 	srandom(gethostid());
2069 	(void) umask(0022);
2070 
2071 	while ((c = getopt(argc, argv, "adD:ntIf:")) != EOF) {
2072 		switch (c) {
2073 		case 'a':
2074 			/*
2075 			 * The StatelessAddrConf variable in ndpd.conf, if
2076 			 * present, will override this setting.
2077 			 */
2078 			ifdefaults[I_StatelessAddrConf].cf_value = 0;
2079 			break;
2080 		case 'd':
2081 			debug = D_ALL;
2082 			break;
2083 		case 'D':
2084 			i = strtol((char *)optarg, NULL, 0);
2085 			if (i == 0) {
2086 				(void) fprintf(stderr, "Bad debug flags: %s\n",
2087 				    (char *)optarg);
2088 				exit(1);
2089 			}
2090 			debug |= i;
2091 			break;
2092 		case 'n':
2093 			no_loopback = 1;
2094 			break;
2095 		case 'I':
2096 			show_ifs = 1;
2097 			break;
2098 		case 't':
2099 			debug |= D_PKTIN | D_PKTOUT | D_PKTBAD;
2100 			break;
2101 		case 'f':
2102 			config_file = (char *)optarg;
2103 			file_required = _B_TRUE;
2104 			break;
2105 		case '?':
2106 			usage(argv[0]);
2107 			exit(1);
2108 		}
2109 	}
2110 
2111 	if (parse_config(config_file, file_required) == -1)
2112 		exit(2);
2113 
2114 	if (show_ifs)
2115 		phyint_print_all();
2116 
2117 	if (debug == 0) {
2118 		initlog();
2119 	}
2120 
2121 	setup_eventpipe();
2122 	rtsock = setup_rtsock();
2123 	mibsock = setup_mibsock();
2124 	timer_init();
2125 	initifs(_B_TRUE);
2126 
2127 	check_daemonize();
2128 
2129 	for (;;) {
2130 		if (poll(pollfds, pollfd_num, -1) < 0) {
2131 			if (errno == EINTR)
2132 				continue;
2133 			logperror("main: poll");
2134 			exit(1);
2135 		}
2136 		for (i = 0; i < pollfd_num; i++) {
2137 			if (!(pollfds[i].revents & POLLIN))
2138 				continue;
2139 			if (pollfds[i].fd == eventpipe_read) {
2140 				in_signal(eventpipe_read);
2141 				break;
2142 			}
2143 			if (pollfds[i].fd == rtsock) {
2144 				process_rtsock(rtsock);
2145 				break;
2146 			}
2147 			if (pollfds[i].fd == mibsock) {
2148 				process_mibsock(mibsock);
2149 				break;
2150 			}
2151 			/*
2152 			 * Run timer routine to advance clock if more than
2153 			 * half a second since the clock was advanced.
2154 			 * This limits CPU usage under severe packet
2155 			 * arrival rates but it creates a slight inaccuracy
2156 			 * in the timer mechanism.
2157 			 */
2158 			conditional_run_timeouts(500U);
2159 			for (pi = phyints; pi != NULL; pi = pi->pi_next) {
2160 				if (pollfds[i].fd == pi->pi_sock) {
2161 					in_data(pi);
2162 					break;
2163 				}
2164 			}
2165 		}
2166 	}
2167 	/* NOTREACHED */
2168 	return (0);
2169 }
2170 
2171 /*
2172  * LOGGER
2173  */
2174 
2175 static boolean_t logging = _B_FALSE;
2176 
2177 static void
2178 initlog(void)
2179 {
2180 	logging = _B_TRUE;
2181 	openlog("in.ndpd", LOG_PID | LOG_CONS, LOG_DAEMON);
2182 }
2183 
2184 /* Print the date/time without a trailing carridge return */
2185 static void
2186 fprintdate(FILE *file)
2187 {
2188 	char buf[BUFSIZ];
2189 	struct tm tms;
2190 	time_t now;
2191 
2192 	now = time(NULL);
2193 	(void) localtime_r(&now, &tms);
2194 	(void) strftime(buf, sizeof (buf), "%h %d %X", &tms);
2195 	(void) fprintf(file, "%s ", buf);
2196 }
2197 
2198 /* PRINTFLIKE2 */
2199 void
2200 logmsg(int level, const char *fmt, ...)
2201 {
2202 	va_list ap;
2203 	va_start(ap, fmt);
2204 
2205 	if (logging) {
2206 		vsyslog(level, fmt, ap);
2207 	} else {
2208 		fprintdate(stderr);
2209 		(void) vfprintf(stderr, fmt, ap);
2210 	}
2211 	va_end(ap);
2212 }
2213 
2214 void
2215 logperror(const char *str)
2216 {
2217 	if (logging) {
2218 		syslog(LOG_ERR, "%s: %m\n", str);
2219 	} else {
2220 		fprintdate(stderr);
2221 		(void) fprintf(stderr, "%s: %s\n", str, strerror(errno));
2222 	}
2223 }
2224 
2225 void
2226 logperror_pi(const struct phyint *pi, const char *str)
2227 {
2228 	if (logging) {
2229 		syslog(LOG_ERR, "%s (interface %s): %m\n",
2230 		    str, pi->pi_name);
2231 	} else {
2232 		fprintdate(stderr);
2233 		(void) fprintf(stderr, "%s (interface %s): %s\n",
2234 		    str, pi->pi_name, strerror(errno));
2235 	}
2236 }
2237 
2238 void
2239 logperror_pr(const struct prefix *pr, const char *str)
2240 {
2241 	if (logging) {
2242 		syslog(LOG_ERR, "%s (prefix %s if %s): %m\n",
2243 		    str, pr->pr_name, pr->pr_physical->pi_name);
2244 	} else {
2245 		fprintdate(stderr);
2246 		(void) fprintf(stderr, "%s (prefix %s if %s): %s\n",
2247 		    str, pr->pr_name, pr->pr_physical->pi_name,
2248 		    strerror(errno));
2249 	}
2250 }
2251