1 /* $NetBSD: rtadvd.c,v 1.79 2020/08/28 00:19:37 rjs Exp $ */ 2 /* $KAME: rtadvd.c,v 1.92 2005/10/17 14:40:02 suz Exp $ */ 3 4 /* 5 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project. 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 3. Neither the name of the project nor the names of its contributors 17 * may be used to endorse or promote products derived from this software 18 * without specific prior written permission. 19 * 20 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 23 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 30 * SUCH DAMAGE. 31 */ 32 33 #include <sys/param.h> 34 #include <sys/socket.h> 35 #include <sys/uio.h> 36 #include <sys/time.h> 37 #include <sys/queue.h> 38 39 #include <net/if.h> 40 #include <net/route.h> 41 #include <net/if_dl.h> 42 #include <netinet/in.h> 43 #include <netinet/ip6.h> 44 #include <netinet6/ip6_var.h> 45 #include <netinet/icmp6.h> 46 47 #include <arpa/inet.h> 48 49 #include <time.h> 50 #include <unistd.h> 51 #include <stdio.h> 52 #include <err.h> 53 #include <errno.h> 54 #include <string.h> 55 #include <stdlib.h> 56 #include <syslog.h> 57 #include <signal.h> 58 #include <stdarg.h> 59 #ifdef __NetBSD__ 60 #include <util.h> 61 #endif 62 #include <poll.h> 63 #include <pwd.h> 64 65 #include "rtadvd.h" 66 #include "advcap.h" 67 #include "timer.h" 68 #include "if.h" 69 #include "config.h" 70 #include "dump.h" 71 #include "logit.h" 72 #include "prog_ops.h" 73 #include "expandm.h" 74 75 struct msghdr rcvmhdr; 76 static unsigned char *rcvcmsgbuf; 77 static size_t rcvcmsgbuflen; 78 static unsigned char *sndcmsgbuf; 79 static size_t sndcmsgbuflen; 80 volatile sig_atomic_t do_dump; 81 volatile sig_atomic_t do_reconf; 82 volatile sig_atomic_t do_die; 83 struct msghdr sndmhdr; 84 struct iovec rcviov[2]; 85 struct iovec sndiov[2]; 86 struct sockaddr_in6 rcvfrom; 87 static const char *dumpfilename = "/var/run/rtadvd.dump"; /* XXX configurable */ 88 int sock; 89 int rtsock = -1; 90 int Cflag = 0, dflag = 0, sflag = 0, Dflag; 91 static int after_daemon = 0; 92 93 static char **if_argv; 94 static int if_argc; 95 96 char *conffile = NULL; 97 98 struct ralist_head_t ralist = TAILQ_HEAD_INITIALIZER(ralist); 99 100 struct nd_optlist { 101 TAILQ_ENTRY(nd_optlist) next; 102 struct nd_opt_hdr *opt; 103 }; 104 union nd_opts { 105 struct nd_opt_hdr *nd_opt_array[9]; 106 struct { 107 struct nd_opt_hdr *zero; 108 struct nd_opt_hdr *src_lladdr; 109 struct nd_opt_hdr *tgt_lladdr; 110 struct nd_opt_prefix_info *pi; 111 struct nd_opt_rd_hdr *rh; 112 struct nd_opt_mtu *mtu; 113 TAILQ_HEAD(, nd_optlist) list; 114 } nd_opt_each; 115 }; 116 #define nd_opts_src_lladdr nd_opt_each.src_lladdr 117 #define nd_opts_tgt_lladdr nd_opt_each.tgt_lladdr 118 #define nd_opts_pi nd_opt_each.pi 119 #define nd_opts_rh nd_opt_each.rh 120 #define nd_opts_mtu nd_opt_each.mtu 121 #define nd_opts_list nd_opt_each.list 122 123 #define NDOPT_FLAG_SRCLINKADDR (1 << 0) 124 #define NDOPT_FLAG_TGTLINKADDR (1 << 1) 125 #define NDOPT_FLAG_PREFIXINFO (1 << 2) 126 #define NDOPT_FLAG_RDHDR (1 << 3) 127 #define NDOPT_FLAG_MTU (1 << 4) 128 #define NDOPT_FLAG_RDNSS (1 << 5) 129 #define NDOPT_FLAG_DNSSL (1 << 6) 130 131 uint32_t ndopt_flags[] = { 132 [ND_OPT_SOURCE_LINKADDR] = NDOPT_FLAG_SRCLINKADDR, 133 [ND_OPT_TARGET_LINKADDR] = NDOPT_FLAG_TGTLINKADDR, 134 [ND_OPT_PREFIX_INFORMATION] = NDOPT_FLAG_PREFIXINFO, 135 [ND_OPT_REDIRECTED_HEADER] = NDOPT_FLAG_RDHDR, 136 [ND_OPT_MTU] = NDOPT_FLAG_MTU, 137 [ND_OPT_RDNSS] = NDOPT_FLAG_RDNSS, 138 [ND_OPT_DNSSL] = NDOPT_FLAG_DNSSL, 139 }; 140 141 struct sockaddr_in6 sin6_linklocal_allnodes = { 142 .sin6_len = sizeof(sin6_linklocal_allnodes), 143 .sin6_family = AF_INET6, 144 .sin6_addr = IN6ADDR_LINKLOCAL_ALLNODES_INIT, 145 }; 146 #ifdef notdef 147 struct sockaddr_in6 sin6_linklocal_allrouters = { 148 .sin6_len = sizeof(sin6_linklocal_allrouters), 149 .sin6_family = AF_INET6, 150 .sin6_addr = IN6ADDR_LINKLOCAL_ALLROUTERS_INIT, 151 }; 152 #endif 153 struct sockaddr_in6 sin6_sitelocal_allrouters = { 154 .sin6_len = sizeof(sin6_sitelocal_allrouters), 155 .sin6_family = AF_INET6, 156 .sin6_addr = IN6ADDR_SITELOCAL_ALLROUTERS_INIT, 157 }; 158 159 static void set_die(int); 160 static void die(void); 161 static void set_reconf(int); 162 static void sock_open(void); 163 static void rtsock_open(void); 164 static void rtadvd_input(void); 165 static void rs_input(int, struct nd_router_solicit *, 166 struct in6_pktinfo *, struct sockaddr_in6 *); 167 static void ra_input(int, struct nd_router_advert *, 168 struct in6_pktinfo *, struct sockaddr_in6 *); 169 static struct rainfo *ra_output(struct rainfo *, bool); 170 static int prefix_check(struct nd_opt_prefix_info *, struct rainfo *, 171 struct sockaddr_in6 *); 172 static int nd6_options(struct nd_opt_hdr *, int, union nd_opts *, uint32_t); 173 static void free_ndopts(union nd_opts *); 174 static void rtmsg_input(void); 175 static void rtadvd_set_dump_file(int); 176 177 int 178 main(int argc, char *argv[]) 179 { 180 struct pollfd set[2]; 181 struct timespec *timeout; 182 int i, ch; 183 int fflag = 0, logopt; 184 struct passwd *pw; 185 const char *pidfilepath = NULL; 186 pid_t pid; 187 188 /* get command line options and arguments */ 189 #define OPTIONS "Cc:dDfp:s" 190 while ((ch = getopt(argc, argv, OPTIONS)) != -1) { 191 #undef OPTIONS 192 switch (ch) { 193 case 'c': 194 conffile = optarg; 195 break; 196 case 'C': 197 Cflag++; 198 break; 199 case 'd': 200 dflag++; 201 break; 202 case 'D': 203 Dflag++; 204 break; 205 case 'f': 206 fflag = 1; 207 break; 208 case 'p': 209 pidfilepath = optarg; 210 break; 211 case 's': 212 sflag = 1; 213 break; 214 } 215 } 216 argc -= optind; 217 argv += optind; 218 if (argc == 0) { 219 fprintf(stderr, "Usage: %s [-CDdfs] [-c conffile]" 220 " [-p pidfile] interface ...\n", getprogname()); 221 return EXIT_FAILURE; 222 } 223 224 if ((pid = pidfile_lock(pidfilepath)) != 0) { 225 if (pid == -1) { 226 logit(LOG_ERR, "pidfile_lock: %m"); 227 } else { 228 logit(LOG_ERR, "Another instance of `%s' is running " 229 "(pid %d); exiting.", getprogname(), pid); 230 } 231 return EXIT_FAILURE; 232 } 233 234 if (prog_init && prog_init() == -1) 235 err(EXIT_FAILURE, "init failed"); 236 237 logopt = LOG_NDELAY | LOG_PID; 238 if (fflag) 239 logopt |= LOG_PERROR; 240 openlog("rtadvd", logopt, LOG_DAEMON); 241 242 /* set log level */ 243 if (dflag == 0) 244 (void)setlogmask(LOG_UPTO(LOG_ERR)); 245 if (dflag == 1) 246 (void)setlogmask(LOG_UPTO(LOG_INFO)); 247 248 errno = 0; /* Ensure errno is 0 so we know if getpwnam errors or not */ 249 if ((pw = getpwnam(RTADVD_USER)) == NULL) { 250 if (errno == 0) 251 logit(LOG_ERR, 252 "user %s does not exist, aborting", 253 RTADVD_USER); 254 else 255 logit(LOG_ERR, "getpwnam: %s: %m", RTADVD_USER); 256 return EXIT_FAILURE; 257 } 258 259 /* timer initialization */ 260 rtadvd_timer_init(); 261 262 if_argc = argc; 263 if_argv = argv; 264 while (argc--) 265 getconfig(*argv++, 1); 266 267 if (!fflag) { 268 prog_daemon(1, 0); 269 after_daemon = 1; 270 if (pidfile_lock(pidfilepath) != 0) 271 logit(LOG_ERR, " pidfile_lock: %m"); 272 } 273 274 sock_open(); 275 276 set[0].fd = sock; 277 set[0].events = POLLIN; 278 if (sflag == 0) { 279 rtsock_open(); 280 set[1].fd = rtsock; 281 set[1].events = POLLIN; 282 } else 283 set[1].fd = -1; 284 285 logit(LOG_INFO, "dropping privileges to %s", RTADVD_USER); 286 if (prog_chroot(pw->pw_dir) == -1) { 287 logit(LOG_ERR, "chroot: %s: %m", pw->pw_dir); 288 return EXIT_FAILURE; 289 } 290 if (prog_chdir("/") == -1) { 291 logit(LOG_ERR, "chdir: /: %m"); 292 return EXIT_FAILURE; 293 } 294 if (prog_setgroups(1, &pw->pw_gid) == -1 || 295 prog_setgid(pw->pw_gid) == -1 || 296 prog_setuid(pw->pw_uid) == -1) 297 { 298 logit(LOG_ERR, "failed to drop privileges: %m"); 299 return EXIT_FAILURE; 300 } 301 302 signal(SIGINT, set_die); 303 signal(SIGTERM, set_die); 304 signal(SIGHUP, set_reconf); 305 signal(SIGUSR1, rtadvd_set_dump_file); 306 307 for (;;) { 308 if (do_dump) { /* SIGUSR1 */ 309 do_dump = 0; 310 rtadvd_dump_file(dumpfilename); 311 } 312 313 if (do_reconf) { /* SIGHUP */ 314 do_reconf = 0; 315 logit(LOG_INFO, "%s: reloading config on SIGHUP", 316 __func__); 317 argc = if_argc; 318 argv = if_argv; 319 while (argc--) 320 getconfig(*argv++, 0); 321 } 322 323 /* timer expiration check and reset the timer */ 324 timeout = rtadvd_check_timer(); 325 326 if (do_die) { 327 die(); 328 /*NOTREACHED*/ 329 } 330 331 if (timeout != NULL) { 332 logit(LOG_DEBUG, 333 "%s: set timer to %jd:%jd. waiting for " 334 "inputs or timeout", __func__, 335 (intmax_t)timeout->tv_sec, 336 (intmax_t)timeout->tv_nsec); 337 } else { 338 logit(LOG_DEBUG, 339 "%s: there's no timer. waiting for inputs", 340 __func__); 341 } 342 343 if ((i = prog_poll(set, 2, timeout ? (timeout->tv_sec * 1000 + 344 (timeout->tv_nsec + 999999) / 1000000) : INFTIM)) == -1) 345 { 346 /* EINTR would occur upon SIGUSR1 for status dump */ 347 if (errno == EINTR) { 348 if (do_die) 349 die(); 350 continue; 351 } 352 353 logit(LOG_ERR, "%s: poll: %m", __func__); 354 if (Dflag) 355 exit(1); 356 } 357 if (i == 0) /* timeout */ 358 continue; 359 if (rtsock != -1 && set[1].revents & POLLIN) 360 rtmsg_input(); 361 if (set[0].revents & POLLIN) 362 rtadvd_input(); 363 } 364 return EXIT_SUCCESS; /* NOTREACHED */ 365 } 366 367 static void 368 rtadvd_set_dump_file(__unused int sig) 369 { 370 371 do_dump = 1; 372 } 373 374 static void 375 set_reconf(__unused int sig) 376 { 377 378 do_reconf = 1; 379 } 380 381 static void 382 set_die(__unused int sig) 383 { 384 385 do_die = 1; 386 } 387 388 static void 389 die(void) 390 { 391 static int waiting; 392 struct rainfo *rai, *ran; 393 struct rdnss *rdnss; 394 struct dnssl *dnssl; 395 396 if (waiting) { 397 if (TAILQ_FIRST(&ralist)) { 398 logit(LOG_INFO, 399 "%s: waiting for expiration of all RA timers", 400 __func__); 401 return; 402 } 403 logit(LOG_NOTICE, "%s: gracefully terminated", __func__); 404 free(rcvcmsgbuf); 405 free(sndcmsgbuf); 406 exit(EXIT_SUCCESS); 407 /* NOT REACHED */ 408 } 409 410 if (TAILQ_FIRST(&ralist) == NULL) { 411 logit(LOG_NOTICE, "%s: gracefully terminated", __func__); 412 exit(EXIT_SUCCESS); 413 /* NOT REACHED */ 414 } 415 416 waiting = 1; 417 logit(LOG_NOTICE, "%s: final RA transmission started", __func__); 418 419 TAILQ_FOREACH_SAFE(rai, &ralist, next, ran) { 420 if (rai->leaving) { 421 TAILQ_REMOVE(&ralist, rai, next); 422 TAILQ_INSERT_HEAD(&ralist, rai->leaving, next); 423 rai->leaving->leaving = rai->leaving; 424 rai->leaving->leaving_for = rai->leaving; 425 free_rainfo(rai); 426 continue; 427 } 428 rai->lifetime = 0; 429 TAILQ_FOREACH(rdnss, &rai->rdnss, next) 430 rdnss->lifetime = 0; 431 TAILQ_FOREACH(dnssl, &rai->dnssl, next) 432 dnssl->lifetime = 0; 433 make_packet(rai); 434 rai->leaving = rai; 435 rai->leaving_for = rai; 436 rai->initcounter = MAX_INITIAL_RTR_ADVERTISEMENTS; 437 rai->mininterval = MIN_DELAY_BETWEEN_RAS; 438 rai->maxinterval = MIN_DELAY_BETWEEN_RAS; 439 rai->leaving_adv = MAX_FINAL_RTR_ADVERTISEMENTS; 440 ra_output(rai, false); 441 ra_timer_update(rai, &rai->timer->tm); 442 rtadvd_set_timer(&rai->timer->tm, rai->timer); 443 } 444 exit(EXIT_SUCCESS); 445 } 446 447 static void 448 ra_timer_reset(struct rainfo *rai) 449 { 450 451 rtadvd_remove_timer(&rai->timer); 452 rai->timer = rtadvd_add_timer(ra_timeout, ra_timer_update, rai, rai); 453 ra_timer_update(rai, &rai->timer->tm); 454 rtadvd_set_timer(&rai->timer->tm, rai->timer); 455 rtadvd_remove_timer(&rai->timer_sol); 456 rai->timer_sol = rtadvd_add_timer(ra_timeout_sol, NULL, rai, NULL); 457 } 458 459 static void 460 rtmsg_input(void) 461 { 462 int n, type, ifindex = 0, plen; 463 size_t len; 464 union rt_msghdr_buf { 465 struct rt_msghdr rt_msghdr; 466 char data[2048]; 467 } buffer; 468 char *msg, *next, *lim, **argv; 469 char ifname[IF_NAMESIZE]; 470 struct prefix *prefix; 471 struct rainfo *rai; 472 struct in6_addr *addr; 473 char addrbuf[INET6_ADDRSTRLEN]; 474 int prefixchange = 0, argc; 475 476 memset(&buffer, 0, sizeof(buffer)); 477 n = prog_read(rtsock, &buffer, sizeof(buffer)); 478 479 /* We read the buffer first to clear the FD */ 480 if (do_die) 481 return; 482 483 msg = buffer.data; 484 if (dflag > 1) { 485 logit(LOG_DEBUG, "%s: received a routing message " 486 "(type = %d, len = %d)", __func__, rtmsg_type(msg), 487 rtmsg_len(msg)); 488 } 489 if (n > rtmsg_len(msg)) { 490 /* 491 * This usually won't happen for messages received on 492 * a routing socket. 493 */ 494 if (dflag > 1) 495 logit(LOG_DEBUG, 496 "%s: received data length is larger than " 497 "1st routing message len. multiple messages? " 498 "read %d bytes, but 1st msg len = %d", 499 __func__, n, rtmsg_len(msg)); 500 #if 0 501 /* adjust length */ 502 n = rtmsg_len(msg); 503 #endif 504 } 505 506 lim = msg + n; 507 for (next = msg; next < lim; next += len) { 508 int oldifflags; 509 510 next = get_next_msg(next, lim, 0, &len, 511 RTADV_TYPE2BITMASK(RTM_ADD) | 512 RTADV_TYPE2BITMASK(RTM_DELETE) | 513 RTADV_TYPE2BITMASK(RTM_NEWADDR) | 514 RTADV_TYPE2BITMASK(RTM_DELADDR) | 515 #ifdef RTM_IFANNOUNCE 516 RTADV_TYPE2BITMASK(RTM_IFANNOUNCE) | 517 #endif 518 RTADV_TYPE2BITMASK(RTM_IFINFO)); 519 if (len == 0) 520 break; 521 type = rtmsg_type(next); 522 switch (type) { 523 case RTM_ADD: 524 case RTM_DELETE: 525 ifindex = get_rtm_ifindex(next); 526 break; 527 case RTM_NEWADDR: 528 case RTM_DELADDR: 529 ifindex = get_ifam_ifindex(next); 530 break; 531 #ifdef RTM_IFANNOUNCE 532 case RTM_IFANNOUNCE: 533 ifindex = get_ifan_ifindex(next); 534 if (get_ifan_what(next) == IFAN_ARRIVAL) { 535 logit(LOG_DEBUG, 536 "%s: interface %s arrived", 537 __func__, 538 if_indextoname(ifindex, ifname)); 539 if (if_argc == 0) { 540 getconfig(ifname, 0); 541 continue; 542 } 543 argc = if_argc; 544 argv = if_argv; 545 while (argc--) { 546 if (strcmp(ifname, *argv++) == 0) { 547 getconfig(ifname, 0); 548 break; 549 } 550 } 551 continue; 552 } 553 break; 554 #endif 555 case RTM_IFINFO: 556 ifindex = get_ifm_ifindex(next); 557 break; 558 default: 559 /* should not reach here */ 560 if (dflag > 1) { 561 logit(LOG_DEBUG, "%s: unknown rtmsg %d on %s", 562 __func__, type, 563 if_indextoname(ifindex, ifname)); 564 } 565 continue; 566 } 567 568 if ((rai = if_indextorainfo(ifindex)) == NULL) { 569 if (dflag > 1) { 570 logit(LOG_DEBUG, 571 "%s: route changed on " 572 "non advertising interface %s (%d)", 573 __func__, 574 if_indextoname(ifindex, ifname), 575 ifindex); 576 } 577 continue; 578 } 579 oldifflags = rai->ifflags; 580 581 switch (type) { 582 case RTM_ADD: 583 /* init ifflags because it may have changed */ 584 rai->ifflags = if_getflags(ifindex, rai->ifflags); 585 586 if (sflag) 587 break; /* we aren't interested in prefixes */ 588 589 addr = get_addr(msg); 590 plen = get_prefixlen(msg); 591 /* sanity check for plen */ 592 /* as RFC2373, prefixlen is at least 4 */ 593 if (plen < 4 || plen > 127) { 594 logit(LOG_INFO, "%s: new interface route's" 595 "plen %d is invalid for a prefix", 596 __func__, plen); 597 break; 598 } 599 prefix = find_prefix(rai, addr, plen); 600 if (prefix) { 601 if (prefix->timer) { 602 /* 603 * If the prefix has been invalidated, 604 * make it available again. 605 */ 606 update_prefix(prefix); 607 prefixchange = 1; 608 } else if (dflag > 1) { 609 logit(LOG_DEBUG, 610 "%s: new prefix(%s/%d) " 611 "added on %s, " 612 "but it was already in list", 613 __func__, 614 inet_ntop(AF_INET6, addr, 615 (char *)addrbuf, INET6_ADDRSTRLEN), 616 plen, rai->ifname); 617 } 618 break; 619 } 620 add_prefix(rai, ifindex, addr, plen); 621 prefixchange = 1; 622 break; 623 case RTM_DELETE: 624 /* init ifflags because it may have changed */ 625 rai->ifflags = if_getflags(ifindex, rai->ifflags); 626 627 if (sflag) 628 break; 629 630 addr = get_addr(msg); 631 plen = get_prefixlen(msg); 632 /* sanity check for plen */ 633 /* as RFC2373, prefixlen is at least 4 */ 634 if (plen < 4 || plen > 127) { 635 logit(LOG_INFO, 636 "%s: deleted interface route's " 637 "plen %d is invalid for a prefix", 638 __func__, plen); 639 break; 640 } 641 prefix = find_prefix(rai, addr, plen); 642 if (prefix == NULL) { 643 if (dflag > 1) { 644 logit(LOG_DEBUG, 645 "%s: prefix(%s/%d) was " 646 "deleted on %s, " 647 "but it was not in list", 648 __func__, 649 inet_ntop(AF_INET6, addr, 650 (char *)addrbuf, INET6_ADDRSTRLEN), 651 plen, rai->ifname); 652 } 653 break; 654 } 655 invalidate_prefix(prefix); 656 prefixchange = 1; 657 break; 658 case RTM_NEWADDR: 659 case RTM_DELADDR: 660 /* init ifflags because it may have changed */ 661 rai->ifflags = if_getflags(ifindex, rai->ifflags); 662 break; 663 case RTM_IFINFO: 664 rai->ifflags = get_ifm_flags(next); 665 break; 666 #ifdef RTM_IFANNOUNCE 667 case RTM_IFANNOUNCE: 668 if (get_ifan_what(next) == IFAN_DEPARTURE) { 669 logit(LOG_DEBUG, 670 "%s: interface %s departed", 671 __func__, rai->ifname); 672 TAILQ_REMOVE(&ralist, rai, next); 673 if (rai->leaving) 674 free_rainfo(rai->leaving); 675 free_rainfo(rai); 676 continue; 677 } 678 break; 679 #endif 680 default: 681 /* should not reach here */ 682 if (dflag > 1) { 683 logit(LOG_DEBUG, 684 "%s: unknown rtmsg %d on %s", 685 __func__, type, 686 if_indextoname(ifindex, ifname)); 687 } 688 return; 689 } 690 691 /* check if an interface flag is changed */ 692 if ((oldifflags & IFF_UP) != 0 && /* UP to DOWN */ 693 (rai->ifflags & IFF_UP) == 0) { 694 logit(LOG_INFO, 695 "%s: interface %s becomes down. stop timer.", 696 __func__, rai->ifname); 697 rtadvd_remove_timer(&rai->timer); 698 } else if ((oldifflags & IFF_UP) == 0 && /* DOWN to UP */ 699 (rai->ifflags & IFF_UP) != 0) { 700 logit(LOG_INFO, 701 "%s: interface %s becomes up. restart timer.", 702 __func__, rai->ifname); 703 704 rai->initcounter = 0; /* reset the counter */ 705 rai->waiting = 0; /* XXX */ 706 ra_timer_reset(rai); 707 } else if (prefixchange && rai->ifflags & IFF_UP) { 708 /* 709 * An advertised prefix has been added or invalidated. 710 * Will notice the change in a short delay. 711 */ 712 rai->initcounter = 0; 713 ra_timer_set_short_delay(rai, rai->timer); 714 } 715 } 716 717 return; 718 } 719 720 void 721 rtadvd_input(void) 722 { 723 ssize_t i; 724 int *hlimp = NULL; 725 struct icmp6_hdr *icp; 726 int ifindex = 0; 727 struct cmsghdr *cm; 728 struct in6_pktinfo *pi = NULL; 729 char ntopbuf[INET6_ADDRSTRLEN], ifnamebuf[IFNAMSIZ]; 730 struct rainfo *rai; 731 732 /* 733 * Get message. We reset msg_controllen since the field could 734 * be modified if we had received a message before setting 735 * receive options. 736 */ 737 rcvmhdr.msg_controllen = rcvcmsgbuflen; 738 if ((i = prog_recvmsg(sock, &rcvmhdr, 0)) == -1) 739 return; 740 741 /* We read the buffer first to clear the FD */ 742 if (do_die) 743 return; 744 745 /* extract optional information via Advanced API */ 746 for (cm = (struct cmsghdr *)CMSG_FIRSTHDR(&rcvmhdr); 747 cm; 748 cm = (struct cmsghdr *)CMSG_NXTHDR(&rcvmhdr, cm)) { 749 if (cm->cmsg_level == IPPROTO_IPV6 && 750 cm->cmsg_type == IPV6_PKTINFO && 751 cm->cmsg_len == CMSG_LEN(sizeof(struct in6_pktinfo))) { 752 pi = (struct in6_pktinfo *)(CMSG_DATA(cm)); 753 ifindex = pi->ipi6_ifindex; 754 } 755 if (cm->cmsg_level == IPPROTO_IPV6 && 756 cm->cmsg_type == IPV6_HOPLIMIT && 757 cm->cmsg_len == CMSG_LEN(sizeof(int))) 758 hlimp = (int *)CMSG_DATA(cm); 759 } 760 if (ifindex == 0) { 761 logit(LOG_ERR, 762 "%s: failed to get receiving interface", 763 __func__); 764 return; 765 } 766 if (hlimp == NULL) { 767 logit(LOG_ERR, 768 "%s: failed to get receiving hop limit", 769 __func__); 770 return; 771 } 772 773 if ((rai = if_indextorainfo(pi->ipi6_ifindex)) == NULL) { 774 if (dflag > 1) { 775 logit(LOG_DEBUG, 776 "%s: received data for non advertising " 777 "interface (%s)", 778 __func__, 779 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 780 } 781 return; 782 } 783 /* 784 * If we happen to receive data on an interface which is now down, 785 * just discard the data. 786 */ 787 if ((rai->ifflags & IFF_UP) == 0) { 788 logit(LOG_INFO, 789 "%s: received data on a disabled interface (%s)", 790 __func__, 791 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 792 return; 793 } 794 795 if ((size_t)i < sizeof(struct icmp6_hdr)) { 796 logit(LOG_ERR, 797 "%s: packet size(%zd) is too short", 798 __func__, i); 799 return; 800 } 801 802 icp = (struct icmp6_hdr *)rcvmhdr.msg_iov[0].iov_base; 803 804 switch (icp->icmp6_type) { 805 case ND_ROUTER_SOLICIT: 806 /* 807 * Message verification - RFC-2461 6.1.1 808 * XXX: these checks must be done in the kernel as well, 809 * but we can't completely rely on them. 810 */ 811 if (*hlimp != 255) { 812 logit(LOG_NOTICE, 813 "%s: RS with invalid hop limit(%d) " 814 "received from %s on %s", 815 __func__, *hlimp, 816 inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf, 817 INET6_ADDRSTRLEN), 818 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 819 return; 820 } 821 if (icp->icmp6_code) { 822 logit(LOG_NOTICE, 823 "%s: RS with invalid ICMP6 code(%d) " 824 "received from %s on %s", 825 __func__, icp->icmp6_code, 826 inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf, 827 INET6_ADDRSTRLEN), 828 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 829 return; 830 } 831 if ((size_t)i < sizeof(struct nd_router_solicit)) { 832 logit(LOG_NOTICE, 833 "%s: RS from %s on %s does not have enough " 834 "length (len = %zd)", 835 __func__, 836 inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf, 837 INET6_ADDRSTRLEN), 838 if_indextoname(pi->ipi6_ifindex, ifnamebuf), i); 839 return; 840 } 841 rs_input(i, (struct nd_router_solicit *)icp, pi, &rcvfrom); 842 break; 843 case ND_ROUTER_ADVERT: 844 /* 845 * Message verification - RFC-2461 6.1.2 846 * XXX: there's a same dilemma as above... 847 */ 848 if (*hlimp != 255) { 849 logit(LOG_NOTICE, 850 "%s: RA with invalid hop limit(%d) " 851 "received from %s on %s", 852 __func__, *hlimp, 853 inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf, 854 INET6_ADDRSTRLEN), 855 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 856 return; 857 } 858 if (icp->icmp6_code) { 859 logit(LOG_NOTICE, 860 "%s: RA with invalid ICMP6 code(%d) " 861 "received from %s on %s", 862 __func__, icp->icmp6_code, 863 inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf, 864 INET6_ADDRSTRLEN), 865 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 866 return; 867 } 868 if ((size_t)i < sizeof(struct nd_router_advert)) { 869 logit(LOG_NOTICE, 870 "%s: RA from %s on %s does not have enough " 871 "length (len = %zd)", 872 __func__, 873 inet_ntop(AF_INET6, &rcvfrom.sin6_addr, ntopbuf, 874 INET6_ADDRSTRLEN), 875 if_indextoname(pi->ipi6_ifindex, ifnamebuf), i); 876 return; 877 } 878 ra_input(i, (struct nd_router_advert *)icp, pi, &rcvfrom); 879 break; 880 default: 881 /* 882 * Note that this case is POSSIBLE, especially just 883 * after invocation of the daemon. This is because we 884 * could receive message after opening the socket and 885 * before setting ICMP6 type filter(see sock_open()). 886 */ 887 logit(LOG_ERR, "%s: invalid icmp type(%d)", 888 __func__, icp->icmp6_type); 889 return; 890 } 891 } 892 893 static void 894 rs_input(int len, struct nd_router_solicit *rs, 895 struct in6_pktinfo *pi, struct sockaddr_in6 *from) 896 { 897 char ntopbuf[INET6_ADDRSTRLEN], ifnamebuf[IFNAMSIZ]; 898 union nd_opts ndopts; 899 struct rainfo *rai; 900 struct soliciter *sol; 901 902 logit(LOG_DEBUG, 903 "%s: RS received from %s on %s", 904 __func__, 905 inet_ntop(AF_INET6, &from->sin6_addr, 906 ntopbuf, INET6_ADDRSTRLEN), 907 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 908 909 /* ND option check */ 910 memset(&ndopts, 0, sizeof(ndopts)); 911 TAILQ_INIT(&ndopts.nd_opts_list); 912 if (nd6_options((struct nd_opt_hdr *)(rs + 1), 913 len - sizeof(struct nd_router_solicit), 914 &ndopts, NDOPT_FLAG_SRCLINKADDR)) { 915 logit(LOG_INFO, 916 "%s: ND option check failed for an RS from %s on %s", 917 __func__, 918 inet_ntop(AF_INET6, &from->sin6_addr, 919 ntopbuf, INET6_ADDRSTRLEN), 920 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 921 return; 922 } 923 924 /* 925 * If the IP source address is the unspecified address, there 926 * must be no source link-layer address option in the message. 927 * (RFC-2461 6.1.1) 928 */ 929 if (IN6_IS_ADDR_UNSPECIFIED(&from->sin6_addr) && 930 ndopts.nd_opts_src_lladdr) { 931 logit(LOG_INFO, 932 "%s: RS from unspecified src on %s has a link-layer" 933 " address option", 934 __func__, 935 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 936 goto done; 937 } 938 939 if ((rai = if_indextorainfo(pi->ipi6_ifindex)) == NULL) { 940 logit(LOG_INFO, 941 "%s: RS received on non advertising interface(%s)", 942 __func__, 943 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 944 goto done; 945 } 946 947 if (rai->leaving) { 948 logit(LOG_INFO, 949 "%s: RS received on reconfiguring advertising interface(%s)", 950 __func__, rai->ifname); 951 goto done; 952 } 953 954 rai->rsinput++; /* increment statistics */ 955 956 /* 957 * Decide whether to send RA according to the rate-limit 958 * consideration. 959 */ 960 961 /* record sockaddr waiting for RA, if possible */ 962 TAILQ_FOREACH(sol, &rai->soliciter, next) { 963 if (IN6_ARE_ADDR_EQUAL(&sol->addr.sin6_addr, &from->sin6_addr)) 964 break; 965 } 966 if (sol == NULL) { 967 sol = malloc(sizeof(*sol)); 968 if (sol == NULL) { 969 logit(LOG_ERR, "%s: malloc: %m", __func__); 970 } else { 971 sol->addr = *from; 972 /* XXX RFC2553 need clarification on flowinfo */ 973 sol->addr.sin6_flowinfo = 0; 974 TAILQ_INSERT_TAIL(&rai->soliciter, sol, next); 975 } 976 } 977 978 /* 979 * If there is already a waiting RS packet, don't 980 * update the timer. 981 */ 982 if (rai->waiting++) 983 goto done; 984 985 ra_timer_set_short_delay(rai, rai->timer_sol); 986 987 done: 988 free_ndopts(&ndopts); 989 } 990 991 void 992 ra_timer_set_short_delay(struct rainfo *rai, struct rtadvd_timer *timer) 993 { 994 long delay; /* must not be greater than 1000000 */ 995 struct timespec interval, now, min_delay, tm_tmp, *rest; 996 997 /* 998 * Compute a random delay. If the computed value 999 * corresponds to a time later than the time the next 1000 * multicast RA is scheduled to be sent, ignore the random 1001 * delay and send the advertisement at the 1002 * already-scheduled time. RFC2461 6.2.6 1003 */ 1004 delay = arc4random() % MAX_RA_DELAY_TIME; 1005 interval.tv_sec = 0; 1006 interval.tv_nsec = delay; 1007 rest = rtadvd_timer_rest(rai->timer); 1008 if (timespeccmp(rest, &interval, <)) { 1009 logit(LOG_DEBUG, "%s: random delay is larger than " 1010 "the rest of current timer", __func__); 1011 interval = *rest; 1012 } 1013 1014 /* 1015 * If we sent a multicast Router Advertisement within 1016 * the last MIN_DELAY_BETWEEN_RAS seconds, schedule 1017 * the advertisement to be sent at a time corresponding to 1018 * MIN_DELAY_BETWEEN_RAS plus the random value after the 1019 * previous advertisement was sent. 1020 */ 1021 prog_clock_gettime(CLOCK_MONOTONIC, &now); 1022 timespecsub(&now, &rai->lastsent, &tm_tmp); 1023 min_delay.tv_sec = MIN_DELAY_BETWEEN_RAS; 1024 min_delay.tv_nsec = 0; 1025 if (timespeccmp(&tm_tmp, &min_delay, <)) { 1026 timespecsub(&min_delay, &tm_tmp, &min_delay); 1027 timespecadd(&min_delay, &interval, &interval); 1028 } 1029 rtadvd_set_timer(&interval, timer); 1030 } 1031 1032 static void 1033 ra_input(int len, struct nd_router_advert *ra, 1034 struct in6_pktinfo *pi, struct sockaddr_in6 *from) 1035 { 1036 struct rainfo *rai; 1037 char ntopbuf[INET6_ADDRSTRLEN], ifnamebuf[IFNAMSIZ]; 1038 union nd_opts ndopts; 1039 const char *on_off[] = {"OFF", "ON"}; 1040 uint32_t reachabletime, retranstimer, mtu; 1041 struct nd_optlist *optp; 1042 int inconsistent = 0; 1043 1044 logit(LOG_DEBUG, 1045 "%s: RA received from %s on %s", 1046 __func__, 1047 inet_ntop(AF_INET6, &from->sin6_addr, 1048 ntopbuf, INET6_ADDRSTRLEN), 1049 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 1050 1051 /* ND option check */ 1052 memset(&ndopts, 0, sizeof(ndopts)); 1053 TAILQ_INIT(&ndopts.nd_opts_list); 1054 if (nd6_options((struct nd_opt_hdr *)(ra + 1), 1055 len - sizeof(struct nd_router_advert), 1056 &ndopts, NDOPT_FLAG_SRCLINKADDR | 1057 NDOPT_FLAG_PREFIXINFO | NDOPT_FLAG_MTU | 1058 NDOPT_FLAG_RDNSS | NDOPT_FLAG_DNSSL)) 1059 { 1060 logit(LOG_INFO, 1061 "%s: ND option check failed for an RA from %s on %s", 1062 __func__, 1063 inet_ntop(AF_INET6, &from->sin6_addr, 1064 ntopbuf, INET6_ADDRSTRLEN), 1065 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 1066 return; 1067 } 1068 1069 /* 1070 * RA consistency check according to RFC-2461 6.2.7 1071 */ 1072 if ((rai = if_indextorainfo(pi->ipi6_ifindex)) == 0) { 1073 logit(LOG_INFO, 1074 "%s: received RA from %s on non-advertising" 1075 " interface(%s)", 1076 __func__, 1077 inet_ntop(AF_INET6, &from->sin6_addr, 1078 ntopbuf, INET6_ADDRSTRLEN), 1079 if_indextoname(pi->ipi6_ifindex, ifnamebuf)); 1080 goto done; 1081 } 1082 if (rai->leaving) { 1083 logit(LOG_DEBUG, 1084 "%s: received RA on re-configuring interface (%s)", 1085 __func__, rai->ifname); 1086 goto done; 1087 } 1088 rai->rainput++; /* increment statistics */ 1089 1090 /* Cur Hop Limit value */ 1091 if (ra->nd_ra_curhoplimit && rai->hoplimit && 1092 ra->nd_ra_curhoplimit != rai->hoplimit) { 1093 logit(LOG_INFO, 1094 "%s: CurHopLimit inconsistent on %s:" 1095 " %d from %s, %d from us", 1096 __func__, 1097 rai->ifname, 1098 ra->nd_ra_curhoplimit, 1099 inet_ntop(AF_INET6, &from->sin6_addr, 1100 ntopbuf, INET6_ADDRSTRLEN), 1101 rai->hoplimit); 1102 inconsistent++; 1103 } 1104 /* M flag */ 1105 if ((ra->nd_ra_flags_reserved & ND_RA_FLAG_MANAGED) != 1106 rai->managedflg) { 1107 logit(LOG_INFO, 1108 "%s: M flag inconsistent on %s:" 1109 " %s from %s, %s from us", 1110 __func__, 1111 rai->ifname, 1112 on_off[!rai->managedflg], 1113 inet_ntop(AF_INET6, &from->sin6_addr, 1114 ntopbuf, INET6_ADDRSTRLEN), 1115 on_off[rai->managedflg]); 1116 inconsistent++; 1117 } 1118 /* O flag */ 1119 if ((ra->nd_ra_flags_reserved & ND_RA_FLAG_OTHER) != 1120 rai->otherflg) { 1121 logit(LOG_INFO, 1122 "%s: O flag inconsistent on %s:" 1123 " %s from %s, %s from us", 1124 __func__, 1125 rai->ifname, 1126 on_off[!rai->otherflg], 1127 inet_ntop(AF_INET6, &from->sin6_addr, 1128 ntopbuf, INET6_ADDRSTRLEN), 1129 on_off[rai->otherflg]); 1130 inconsistent++; 1131 } 1132 /* Reachable Time */ 1133 reachabletime = ntohl(ra->nd_ra_reachable); 1134 if (reachabletime && rai->reachabletime && 1135 reachabletime != rai->reachabletime) { 1136 logit(LOG_INFO, 1137 "%s: ReachableTime inconsistent on %s:" 1138 " %d from %s, %d from us", 1139 __func__, 1140 rai->ifname, 1141 reachabletime, 1142 inet_ntop(AF_INET6, &from->sin6_addr, 1143 ntopbuf, INET6_ADDRSTRLEN), 1144 rai->reachabletime); 1145 inconsistent++; 1146 } 1147 /* Retrans Timer */ 1148 retranstimer = ntohl(ra->nd_ra_retransmit); 1149 if (retranstimer && rai->retranstimer && 1150 retranstimer != rai->retranstimer) { 1151 logit(LOG_INFO, 1152 "%s: RetranceTimer inconsistent on %s:" 1153 " %d from %s, %d from us", 1154 __func__, 1155 rai->ifname, 1156 retranstimer, 1157 inet_ntop(AF_INET6, &from->sin6_addr, 1158 ntopbuf, INET6_ADDRSTRLEN), 1159 rai->retranstimer); 1160 inconsistent++; 1161 } 1162 /* Values in the MTU options */ 1163 if (ndopts.nd_opts_mtu) { 1164 mtu = ntohl(ndopts.nd_opts_mtu->nd_opt_mtu_mtu); 1165 if (mtu && rai->linkmtu && mtu != rai->linkmtu) { 1166 logit(LOG_INFO, 1167 "%s: MTU option value inconsistent on %s:" 1168 " %d from %s, %d from us", 1169 __func__, 1170 rai->ifname, mtu, 1171 inet_ntop(AF_INET6, &from->sin6_addr, 1172 ntopbuf, INET6_ADDRSTRLEN), 1173 rai->linkmtu); 1174 inconsistent++; 1175 } 1176 } 1177 /* Preferred and Valid Lifetimes for prefixes */ 1178 if (ndopts.nd_opts_pi) 1179 if (prefix_check(ndopts.nd_opts_pi, rai, from)) 1180 inconsistent++; 1181 TAILQ_FOREACH(optp, &ndopts.nd_opts_list, next) 1182 if (prefix_check((struct nd_opt_prefix_info *)optp->opt, 1183 rai, from)) 1184 inconsistent++; 1185 1186 if (inconsistent) 1187 rai->rainconsistent++; 1188 1189 done: 1190 free_ndopts(&ndopts); 1191 } 1192 1193 /* return a non-zero value if the received prefix is inconsitent with ours */ 1194 static int 1195 prefix_check(struct nd_opt_prefix_info *pinfo, 1196 struct rainfo *rai, struct sockaddr_in6 *from) 1197 { 1198 uint32_t preferred_time, valid_time; 1199 struct prefix *pp; 1200 int inconsistent = 0; 1201 char ntopbuf[INET6_ADDRSTRLEN], prefixbuf[INET6_ADDRSTRLEN]; 1202 struct timespec now; 1203 struct in6_addr prefix; 1204 1205 #if 0 /* impossible */ 1206 if (pinfo->nd_opt_pi_type != ND_OPT_PREFIX_INFORMATION) 1207 return 0; 1208 #endif 1209 1210 memcpy(&prefix, &pinfo->nd_opt_pi_prefix, sizeof(prefix)); 1211 1212 /* 1213 * log if the adveritsed prefix has link-local scope(sanity check?) 1214 */ 1215 if (IN6_IS_ADDR_LINKLOCAL(&prefix)) { 1216 logit(LOG_INFO, 1217 "%s: link-local prefix %s/%d is advertised " 1218 "from %s on %s", 1219 __func__, 1220 inet_ntop(AF_INET6, &prefix, 1221 prefixbuf, INET6_ADDRSTRLEN), 1222 pinfo->nd_opt_pi_prefix_len, 1223 inet_ntop(AF_INET6, &from->sin6_addr, 1224 ntopbuf, INET6_ADDRSTRLEN), 1225 rai->ifname); 1226 } 1227 1228 if ((pp = find_prefix(rai, &prefix, 1229 pinfo->nd_opt_pi_prefix_len)) == NULL) { 1230 logit(LOG_INFO, 1231 "%s: prefix %s/%d from %s on %s is not in our list", 1232 __func__, 1233 inet_ntop(AF_INET6, &prefix, 1234 prefixbuf, INET6_ADDRSTRLEN), 1235 pinfo->nd_opt_pi_prefix_len, 1236 inet_ntop(AF_INET6, &from->sin6_addr, 1237 ntopbuf, INET6_ADDRSTRLEN), 1238 rai->ifname); 1239 return 0; 1240 } 1241 1242 preferred_time = ntohl(pinfo->nd_opt_pi_preferred_time); 1243 if (pp->pltimeexpire) { 1244 /* 1245 * The lifetime is decremented in real time, so we should 1246 * compare the expiration time. 1247 * (RFC 2461 Section 6.2.7.) 1248 * XXX: can we really expect that all routers on the link 1249 * have synchronized clocks? 1250 */ 1251 prog_clock_gettime(CLOCK_MONOTONIC, &now); 1252 preferred_time += now.tv_sec; 1253 1254 if (!pp->timer && rai->clockskew && 1255 llabs((long long)preferred_time - pp->pltimeexpire) > rai->clockskew) { 1256 logit(LOG_INFO, 1257 "%s: preferred lifetime for %s/%d" 1258 " (decr. in real time) inconsistent on %s:" 1259 " %d from %s, %ld from us", 1260 __func__, 1261 inet_ntop(AF_INET6, &prefix, 1262 prefixbuf, INET6_ADDRSTRLEN), 1263 pinfo->nd_opt_pi_prefix_len, 1264 rai->ifname, preferred_time, 1265 inet_ntop(AF_INET6, &from->sin6_addr, 1266 ntopbuf, INET6_ADDRSTRLEN), 1267 pp->pltimeexpire); 1268 inconsistent++; 1269 } 1270 } else if (!pp->timer && preferred_time != pp->preflifetime) { 1271 logit(LOG_INFO, 1272 "%s: preferred lifetime for %s/%d" 1273 " inconsistent on %s:" 1274 " %d from %s, %d from us", 1275 __func__, 1276 inet_ntop(AF_INET6, &prefix, 1277 prefixbuf, INET6_ADDRSTRLEN), 1278 pinfo->nd_opt_pi_prefix_len, 1279 rai->ifname, preferred_time, 1280 inet_ntop(AF_INET6, &from->sin6_addr, 1281 ntopbuf, INET6_ADDRSTRLEN), 1282 pp->preflifetime); 1283 } 1284 1285 valid_time = ntohl(pinfo->nd_opt_pi_valid_time); 1286 if (pp->vltimeexpire) { 1287 prog_clock_gettime(CLOCK_MONOTONIC, &now); 1288 valid_time += now.tv_sec; 1289 1290 if (!pp->timer && rai->clockskew && 1291 llabs((long long)valid_time - pp->vltimeexpire) > rai->clockskew) { 1292 logit(LOG_INFO, 1293 "%s: valid lifetime for %s/%d" 1294 " (decr. in real time) inconsistent on %s:" 1295 " %d from %s, %ld from us", 1296 __func__, 1297 inet_ntop(AF_INET6, &prefix, 1298 prefixbuf, INET6_ADDRSTRLEN), 1299 pinfo->nd_opt_pi_prefix_len, 1300 rai->ifname, preferred_time, 1301 inet_ntop(AF_INET6, &from->sin6_addr, 1302 ntopbuf, INET6_ADDRSTRLEN), 1303 pp->vltimeexpire); 1304 inconsistent++; 1305 } 1306 } else if (!pp->timer && valid_time != pp->validlifetime) { 1307 logit(LOG_INFO, 1308 "%s: valid lifetime for %s/%d" 1309 " inconsistent on %s:" 1310 " %d from %s, %d from us", 1311 __func__, 1312 inet_ntop(AF_INET6, &prefix, 1313 prefixbuf, INET6_ADDRSTRLEN), 1314 pinfo->nd_opt_pi_prefix_len, 1315 rai->ifname, valid_time, 1316 inet_ntop(AF_INET6, &from->sin6_addr, 1317 ntopbuf, INET6_ADDRSTRLEN), 1318 pp->validlifetime); 1319 inconsistent++; 1320 } 1321 1322 return inconsistent; 1323 } 1324 1325 struct prefix * 1326 find_prefix(struct rainfo *rai, struct in6_addr *prefix, int plen) 1327 { 1328 struct prefix *pp; 1329 int bytelen, bitlen; 1330 unsigned char bitmask; 1331 1332 TAILQ_FOREACH(pp, &rai->prefix, next) { 1333 if (plen != pp->prefixlen) 1334 continue; 1335 bytelen = plen / 8; 1336 bitlen = plen % 8; 1337 bitmask = 0xff << (8 - bitlen); 1338 if (memcmp(prefix, &pp->prefix, bytelen)) 1339 continue; 1340 if (bitlen == 0 || 1341 ((prefix->s6_addr[bytelen] & bitmask) == 1342 (pp->prefix.s6_addr[bytelen] & bitmask))) { 1343 return pp; 1344 } 1345 } 1346 1347 return NULL; 1348 } 1349 1350 /* check if p0/plen0 matches p1/plen1; return 1 if matches, otherwise 0. */ 1351 int 1352 prefix_match(struct in6_addr *p0, int plen0, 1353 struct in6_addr *p1, int plen1) 1354 { 1355 int bytelen, bitlen; 1356 unsigned char bitmask; 1357 1358 if (plen0 < plen1) 1359 return 0; 1360 bytelen = plen1 / 8; 1361 bitlen = plen1 % 8; 1362 bitmask = 0xff << (8 - bitlen); 1363 if (memcmp(p0, p1, bytelen)) 1364 return 0; 1365 if (bitlen == 0 || 1366 ((p0->s6_addr[bytelen] & bitmask) == 1367 (p1->s6_addr[bytelen] & bitmask))) { 1368 return 1; 1369 } 1370 1371 return 0; 1372 } 1373 1374 static int 1375 nd6_options(struct nd_opt_hdr *hdr, int limit, 1376 union nd_opts *ndopts, uint32_t optflags) 1377 { 1378 int optlen = 0; 1379 1380 for (; limit > 0; limit -= optlen) { 1381 if ((size_t)limit < sizeof(struct nd_opt_hdr)) { 1382 logit(LOG_INFO, "%s: short option header", __func__); 1383 goto bad; 1384 } 1385 1386 hdr = (struct nd_opt_hdr *)((char *)hdr + optlen); 1387 if (hdr->nd_opt_len == 0) { 1388 logit(LOG_INFO, 1389 "%s: bad ND option length(0) (type = %d)", 1390 __func__, hdr->nd_opt_type); 1391 goto bad; 1392 } 1393 optlen = hdr->nd_opt_len << 3; 1394 if (optlen > limit) { 1395 logit(LOG_INFO, "%s: short option", __func__); 1396 goto bad; 1397 } 1398 1399 if (hdr->nd_opt_type > ND_OPT_MTU && 1400 hdr->nd_opt_type != ND_OPT_RDNSS && 1401 hdr->nd_opt_type != ND_OPT_DNSSL) 1402 { 1403 logit(LOG_INFO, "%s: unknown ND option(type %d)", 1404 __func__, hdr->nd_opt_type); 1405 continue; 1406 } 1407 1408 if ((ndopt_flags[hdr->nd_opt_type] & optflags) == 0) { 1409 logit(LOG_INFO, "%s: unexpected ND option(type %d)", 1410 __func__, hdr->nd_opt_type); 1411 continue; 1412 } 1413 1414 /* 1415 * Option length check. Do it here for all fixed-length 1416 * options. 1417 */ 1418 if ((hdr->nd_opt_type == ND_OPT_MTU && 1419 (optlen != sizeof(struct nd_opt_mtu))) || 1420 ((hdr->nd_opt_type == ND_OPT_PREFIX_INFORMATION && 1421 optlen != sizeof(struct nd_opt_prefix_info))) || 1422 (hdr->nd_opt_type == ND_OPT_RDNSS && 1423 ((optlen < (int)sizeof(struct nd_opt_rdnss) || 1424 (optlen - sizeof(struct nd_opt_rdnss)) % 16 != 0))) || 1425 (hdr->nd_opt_type == ND_OPT_DNSSL && 1426 optlen < (int)sizeof(struct nd_opt_dnssl))) 1427 { 1428 logit(LOG_INFO, "%s: invalid option length", 1429 __func__); 1430 continue; 1431 } 1432 1433 switch (hdr->nd_opt_type) { 1434 case ND_OPT_TARGET_LINKADDR: 1435 case ND_OPT_REDIRECTED_HEADER: 1436 case ND_OPT_RDNSS: 1437 case ND_OPT_DNSSL: 1438 break; /* we don't care about these options */ 1439 case ND_OPT_SOURCE_LINKADDR: 1440 case ND_OPT_MTU: 1441 if (ndopts->nd_opt_array[hdr->nd_opt_type]) { 1442 logit(LOG_INFO, 1443 "%s: duplicated ND option (type = %d)", 1444 __func__, hdr->nd_opt_type); 1445 } 1446 ndopts->nd_opt_array[hdr->nd_opt_type] = hdr; 1447 break; 1448 case ND_OPT_PREFIX_INFORMATION: 1449 { 1450 struct nd_optlist *pfxlist; 1451 1452 if (ndopts->nd_opts_pi == 0) { 1453 ndopts->nd_opts_pi = 1454 (struct nd_opt_prefix_info *)hdr; 1455 continue; 1456 } 1457 if ((pfxlist = malloc(sizeof(*pfxlist))) == NULL) { 1458 logit(LOG_ERR, "%s: can't allocate memory", 1459 __func__); 1460 goto bad; 1461 } 1462 pfxlist->opt = hdr; 1463 TAILQ_INSERT_TAIL(&ndopts->nd_opts_list, pfxlist, next); 1464 1465 break; 1466 } 1467 default: /* impossible */ 1468 break; 1469 } 1470 } 1471 1472 return 0; 1473 1474 bad: 1475 free_ndopts(ndopts); 1476 return -1; 1477 } 1478 1479 static void 1480 free_ndopts(union nd_opts *ndopts) 1481 { 1482 struct nd_optlist *opt; 1483 1484 while ((opt = TAILQ_FIRST(&ndopts->nd_opts_list)) != NULL) { 1485 TAILQ_REMOVE(&ndopts->nd_opts_list, opt, next); 1486 free(opt); 1487 } 1488 } 1489 1490 void 1491 sock_open(void) 1492 { 1493 struct icmp6_filter filt; 1494 struct ipv6_mreq mreq; 1495 struct rainfo *ra; 1496 int on; 1497 /* XXX: should be max MTU attached to the node */ 1498 static unsigned char answer[1500]; 1499 1500 rcvcmsgbuflen = CMSG_SPACE(sizeof(struct in6_pktinfo)) + 1501 CMSG_SPACE(sizeof(int)); 1502 rcvcmsgbuf = malloc(rcvcmsgbuflen); 1503 if (rcvcmsgbuf == NULL) { 1504 logit(LOG_ERR, "%s: malloc: %m", __func__); 1505 exit(EXIT_FAILURE); 1506 } 1507 1508 sndcmsgbuflen = CMSG_SPACE(sizeof(struct in6_pktinfo)); 1509 sndcmsgbuf = malloc(sndcmsgbuflen); 1510 if (sndcmsgbuf == NULL) { 1511 logit(LOG_ERR, "%s: malloc: %m", __func__); 1512 exit(EXIT_FAILURE); 1513 } 1514 1515 if ((sock = prog_socket(AF_INET6, SOCK_RAW, IPPROTO_ICMPV6)) == -1) { 1516 logit(LOG_ERR, "%s: socket: %m", __func__); 1517 exit(EXIT_FAILURE); 1518 } 1519 1520 /* RFC 4861 Section 4.2 */ 1521 on = 255; 1522 if (prog_setsockopt(sock, IPPROTO_IPV6, IPV6_MULTICAST_HOPS, &on, 1523 sizeof(on)) == -1) { 1524 logit(LOG_ERR, "%s: IPV6_MULTICAST_HOPS: %m", __func__); 1525 exit(EXIT_FAILURE); 1526 } 1527 on = 255; 1528 if (prog_setsockopt(sock, IPPROTO_IPV6, IPV6_UNICAST_HOPS, &on, 1529 sizeof(on)) == -1) { 1530 logit(LOG_ERR, "%s: IPV6_UNICAST_HOPS: %m", __func__); 1531 exit(EXIT_FAILURE); 1532 } 1533 1534 /* specify to tell receiving interface */ 1535 on = 1; 1536 if (prog_setsockopt(sock, IPPROTO_IPV6, IPV6_RECVPKTINFO, &on, 1537 sizeof(on)) == -1) { 1538 logit(LOG_ERR, "%s: IPV6_RECVPKTINFO: %m", __func__); 1539 exit(EXIT_FAILURE); 1540 } 1541 1542 on = 1; 1543 /* specify to tell value of hoplimit field of received IP6 hdr */ 1544 if (prog_setsockopt(sock, IPPROTO_IPV6, IPV6_RECVHOPLIMIT, &on, 1545 sizeof(on)) == -1) { 1546 logit(LOG_ERR, "%s: IPV6_RECVHOPLIMIT: %m", __func__); 1547 exit(EXIT_FAILURE); 1548 } 1549 1550 ICMP6_FILTER_SETBLOCKALL(&filt); 1551 ICMP6_FILTER_SETPASS(ND_ROUTER_SOLICIT, &filt); 1552 ICMP6_FILTER_SETPASS(ND_ROUTER_ADVERT, &filt); 1553 if (prog_setsockopt(sock, IPPROTO_ICMPV6, ICMP6_FILTER, &filt, 1554 sizeof(filt)) == -1) { 1555 logit(LOG_ERR, "%s: IICMP6_FILTER: %m", __func__); 1556 exit(EXIT_FAILURE); 1557 } 1558 1559 /* 1560 * join all routers multicast address on each advertising interface. 1561 */ 1562 if (inet_pton(AF_INET6, ALLROUTERS_LINK, 1563 mreq.ipv6mr_multiaddr.s6_addr) != 1) 1564 { 1565 logit(LOG_ERR, "%s: inet_pton failed(library bug?)", 1566 __func__); 1567 exit(EXIT_FAILURE); 1568 } 1569 TAILQ_FOREACH(ra, &ralist, next) { 1570 mreq.ipv6mr_interface = ra->ifindex; 1571 if (prog_setsockopt(sock, IPPROTO_IPV6, IPV6_JOIN_GROUP, &mreq, 1572 sizeof(mreq)) == -1) { 1573 logit(LOG_ERR, "%s: IPV6_JOIN_GROUP(link) on %s: %m", 1574 __func__, ra->ifname); 1575 continue; 1576 } 1577 } 1578 1579 /* initialize msghdr for receiving packets */ 1580 rcviov[0].iov_base = answer; 1581 rcviov[0].iov_len = sizeof(answer); 1582 rcvmhdr.msg_name = &rcvfrom; 1583 rcvmhdr.msg_namelen = sizeof(rcvfrom); 1584 rcvmhdr.msg_iov = rcviov; 1585 rcvmhdr.msg_iovlen = 1; 1586 rcvmhdr.msg_control = rcvcmsgbuf; 1587 rcvmhdr.msg_controllen = rcvcmsgbuflen; 1588 1589 /* initialize msghdr for sending packets */ 1590 sndmhdr.msg_namelen = sizeof(struct sockaddr_in6); 1591 sndmhdr.msg_iov = sndiov; 1592 sndmhdr.msg_iovlen = 1; 1593 sndmhdr.msg_control = sndcmsgbuf; 1594 sndmhdr.msg_controllen = sndcmsgbuflen; 1595 } 1596 1597 /* open a routing socket to watch the routing table */ 1598 static void 1599 rtsock_open(void) 1600 { 1601 #ifdef RO_MSGFILTER 1602 unsigned char msgfilter[] = { 1603 RTM_ADD, RTM_DELETE, 1604 RTM_NEWADDR, RTM_DELADDR, 1605 #ifdef RTM_IFANNOUNCE 1606 RTM_IFANNOUNCE, 1607 #endif 1608 RTM_IFINFO, 1609 }; 1610 #endif 1611 1612 if ((rtsock = prog_socket(PF_ROUTE, SOCK_RAW, 0)) == -1) { 1613 logit(LOG_ERR, "%s: socket: %m", __func__); 1614 exit(EXIT_FAILURE); 1615 } 1616 #ifdef RO_MSGFILTER 1617 if (prog_setsockopt(rtsock, PF_ROUTE, RO_MSGFILTER, 1618 &msgfilter, sizeof(msgfilter) == -1)) 1619 logit(LOG_ERR, "%s: RO_MSGFILTER: %m", __func__); 1620 #endif 1621 } 1622 1623 struct rainfo * 1624 if_indextorainfo(unsigned int idx) 1625 { 1626 struct rainfo *rai; 1627 1628 TAILQ_FOREACH(rai, &ralist, next) { 1629 if (rai->ifindex == idx) 1630 return rai; 1631 } 1632 1633 return NULL; /* search failed */ 1634 } 1635 1636 struct rainfo * 1637 ra_output(struct rainfo *rai, bool solicited) 1638 { 1639 int i; 1640 struct cmsghdr *cm; 1641 struct in6_pktinfo *pi; 1642 struct soliciter *sol; 1643 1644 if ((rai->ifflags & IFF_UP) == 0) { 1645 logit(LOG_DEBUG, "%s: %s is not up, skip sending RA", 1646 __func__, rai->ifname); 1647 return NULL; 1648 } 1649 1650 make_packet(rai); /* XXX: inefficient */ 1651 1652 sndmhdr.msg_name = (void *)&sin6_linklocal_allnodes; 1653 sndmhdr.msg_iov[0].iov_base = (void *)rai->ra_data; 1654 sndmhdr.msg_iov[0].iov_len = rai->ra_datalen; 1655 1656 /* specify the outgoing interface */ 1657 cm = CMSG_FIRSTHDR(&sndmhdr); 1658 cm->cmsg_level = IPPROTO_IPV6; 1659 cm->cmsg_type = IPV6_PKTINFO; 1660 cm->cmsg_len = CMSG_LEN(sizeof(struct in6_pktinfo)); 1661 pi = (struct in6_pktinfo *)CMSG_DATA(cm); 1662 memset(&pi->ipi6_addr, 0, sizeof(pi->ipi6_addr)); /*XXX*/ 1663 pi->ipi6_ifindex = rai->ifindex; 1664 1665 logit(LOG_DEBUG, 1666 "%s: send RA on %s, # of waitings = %d", 1667 __func__, rai->ifname, rai->waiting); 1668 1669 if (solicited) { 1670 /* unicast solicited RA's as per RFC 7772 */ 1671 while ((sol = TAILQ_FIRST(&rai->soliciter)) != NULL) { 1672 sndmhdr.msg_name = (void *)&sol->addr; 1673 i = prog_sendmsg(sock, &sndmhdr, 0); 1674 if (i < 0 || (size_t)i != rai->ra_datalen) { 1675 if (i < 0) { 1676 logit(LOG_ERR, 1677 "%s: unicast sendmsg on %s: %m", 1678 __func__, rai->ifname); 1679 } 1680 } 1681 TAILQ_REMOVE(&rai->soliciter, sol, next); 1682 free(sol); 1683 } 1684 1685 /* reset waiting conter */ 1686 rai->waiting = 0; 1687 1688 /* disable timer */ 1689 rai->timer_sol->enabled = false; 1690 1691 return rai; 1692 } 1693 1694 i = prog_sendmsg(sock, &sndmhdr, 0); 1695 if (i < 0 || (size_t)i != rai->ra_datalen) { 1696 if (i < 0) { 1697 logit(LOG_ERR, "%s: sendmsg on %s: %m", 1698 __func__, rai->ifname); 1699 } 1700 } 1701 1702 if (rai->leaving_adv > 0) { 1703 if (--(rai->leaving_adv) == 0) { 1704 /* leaving for ourself means we're shutting down */ 1705 if (rai->leaving_for == rai) { 1706 TAILQ_REMOVE(&ralist, rai, next); 1707 free_rainfo(rai); 1708 return NULL; 1709 } 1710 logit(LOG_DEBUG, 1711 "%s: expired RA," 1712 " new config active for interface (%s)", 1713 __func__, rai->ifname); 1714 ra_timer_reset(rai->leaving_for); 1715 rai->leaving_for->leaving = NULL; 1716 free_rainfo(rai); 1717 return NULL; 1718 } 1719 } 1720 1721 /* update counter */ 1722 if (rai->initcounter < MAX_INITIAL_RTR_ADVERTISEMENTS) 1723 rai->initcounter++; 1724 rai->raoutput++; 1725 1726 /* update timestamp */ 1727 prog_clock_gettime(CLOCK_MONOTONIC, &rai->lastsent); 1728 return rai; 1729 } 1730 1731 /* process unsolicited RA timer */ 1732 struct rtadvd_timer * 1733 ra_timeout(void *data) 1734 { 1735 struct rainfo *rai = (struct rainfo *)data; 1736 1737 logit(LOG_DEBUG, 1738 "%s: unsolicited RA timer on %s is expired", 1739 __func__, rai->ifname); 1740 1741 if (ra_output(rai, false)) 1742 return rai->timer; 1743 return NULL; 1744 } 1745 1746 /* process solicited RA timer */ 1747 struct rtadvd_timer * 1748 ra_timeout_sol(void *data) 1749 { 1750 struct rainfo *rai = (struct rainfo *)data; 1751 1752 logit(LOG_DEBUG, 1753 "%s: solicited RA timer on %s is expired", 1754 __func__, rai->ifname); 1755 1756 if (ra_output(rai, true)) 1757 return rai->timer_sol; 1758 return NULL; 1759 } 1760 1761 /* update RA timer */ 1762 void 1763 ra_timer_update(void *data, struct timespec *tm) 1764 { 1765 struct rainfo *rai = (struct rainfo *)data; 1766 long interval; 1767 1768 /* 1769 * Whenever a multicast advertisement is sent from an interface, 1770 * the timer is reset to a uniformly-distributed random value 1771 * between the interface's configured MinRtrAdvInterval and 1772 * MaxRtrAdvInterval (RFC2461 6.2.4). 1773 */ 1774 interval = rai->mininterval; 1775 if (rai->mininterval != rai->maxinterval) 1776 interval += arc4random() % (rai->maxinterval-rai->mininterval); 1777 1778 /* 1779 * For the first few advertisements (up to 1780 * MAX_INITIAL_RTR_ADVERTISEMENTS), if the randomly chosen interval 1781 * is greater than MAX_INITIAL_RTR_ADVERT_INTERVAL, the timer 1782 * SHOULD be set to MAX_INITIAL_RTR_ADVERT_INTERVAL instead. 1783 * (RFC-2461 6.2.4) 1784 */ 1785 if (rai->initcounter < MAX_INITIAL_RTR_ADVERTISEMENTS && 1786 interval > MAX_INITIAL_RTR_ADVERT_INTERVAL) 1787 interval = MAX_INITIAL_RTR_ADVERT_INTERVAL; 1788 1789 tm->tv_sec = interval; 1790 tm->tv_nsec = 0; 1791 1792 logit(LOG_DEBUG, 1793 "%s: RA timer on %s is set to %jd:%jd", 1794 __func__, rai->ifname, 1795 (intmax_t)tm->tv_sec, (intmax_t)tm->tv_nsec); 1796 } 1797 1798 void 1799 logit(int level, const char *fmt, ...) 1800 { 1801 va_list ap; 1802 char *buf; 1803 1804 va_start(ap, fmt); 1805 if (!Dflag && after_daemon) { 1806 vsyslog(level, fmt, ap); 1807 va_end(ap); 1808 return; 1809 } 1810 if (level >= LOG_INFO && !dflag) 1811 return; 1812 1813 vwarnx(expandm(fmt, "\n", &buf), ap); 1814 free(buf); 1815 va_end(ap); 1816 } 1817