1 /* $FreeBSD$ */ 2 /* $KAME: in6_ifattach.c,v 1.118 2001/05/24 07:44:00 itojun 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/systm.h> 35 #include <sys/malloc.h> 36 #include <sys/socket.h> 37 #include <sys/sockio.h> 38 #include <sys/kernel.h> 39 #include <sys/syslog.h> 40 #include <sys/md5.h> 41 42 #include <net/if.h> 43 #include <net/if_dl.h> 44 #include <net/if_types.h> 45 #include <net/route.h> 46 47 #include <netinet/in.h> 48 #include <netinet/in_var.h> 49 #include <netinet/if_ether.h> 50 #include <netinet/in_pcb.h> 51 52 #include <netinet/ip6.h> 53 #include <netinet6/ip6_var.h> 54 #include <netinet6/in6_var.h> 55 #include <netinet6/in6_pcb.h> 56 #include <netinet6/in6_ifattach.h> 57 #include <netinet6/ip6_var.h> 58 #include <netinet6/nd6.h> 59 #include <netinet6/scope6_var.h> 60 61 #include <net/net_osdep.h> 62 63 struct in6_ifstat **in6_ifstat = NULL; 64 struct icmp6_ifstat **icmp6_ifstat = NULL; 65 size_t in6_ifstatmax = 0; 66 size_t icmp6_ifstatmax = 0; 67 unsigned long in6_maxmtu = 0; 68 69 #ifdef IP6_AUTO_LINKLOCAL 70 int ip6_auto_linklocal = IP6_AUTO_LINKLOCAL; 71 #else 72 int ip6_auto_linklocal = 1; /* enable by default */ 73 #endif 74 75 struct callout in6_tmpaddrtimer_ch; 76 77 extern struct inpcbinfo udbinfo; 78 extern struct inpcbinfo ripcbinfo; 79 80 static int get_rand_ifid __P((struct ifnet *, struct in6_addr *)); 81 static int generate_tmp_ifid __P((u_int8_t *, const u_int8_t *, u_int8_t *)); 82 static int get_hw_ifid __P((struct ifnet *, struct in6_addr *)); 83 static int get_ifid __P((struct ifnet *, struct ifnet *, struct in6_addr *)); 84 static int in6_ifattach_linklocal __P((struct ifnet *, struct ifnet *)); 85 static int in6_ifattach_loopback __P((struct ifnet *)); 86 87 #define EUI64_GBIT 0x01 88 #define EUI64_UBIT 0x02 89 #define EUI64_TO_IFID(in6) do {(in6)->s6_addr[8] ^= EUI64_UBIT; } while (0) 90 #define EUI64_GROUP(in6) ((in6)->s6_addr[8] & EUI64_GBIT) 91 #define EUI64_INDIVIDUAL(in6) (!EUI64_GROUP(in6)) 92 #define EUI64_LOCAL(in6) ((in6)->s6_addr[8] & EUI64_UBIT) 93 #define EUI64_UNIVERSAL(in6) (!EUI64_LOCAL(in6)) 94 95 #define IFID_LOCAL(in6) (!EUI64_LOCAL(in6)) 96 #define IFID_UNIVERSAL(in6) (!EUI64_UNIVERSAL(in6)) 97 98 /* 99 * Generate a last-resort interface identifier, when the machine has no 100 * IEEE802/EUI64 address sources. 101 * The goal here is to get an interface identifier that is 102 * (1) random enough and (2) does not change across reboot. 103 * We currently use MD5(hostname) for it. 104 */ 105 static int 106 get_rand_ifid(ifp, in6) 107 struct ifnet *ifp; 108 struct in6_addr *in6; /* upper 64bits are preserved */ 109 { 110 MD5_CTX ctxt; 111 u_int8_t digest[16]; 112 int hostnamelen = strlen(hostname); 113 114 #if 0 115 /* we need at least several letters as seed for ifid */ 116 if (hostnamelen < 3) 117 return -1; 118 #endif 119 120 /* generate 8 bytes of pseudo-random value. */ 121 bzero(&ctxt, sizeof(ctxt)); 122 MD5Init(&ctxt); 123 MD5Update(&ctxt, hostname, hostnamelen); 124 MD5Final(digest, &ctxt); 125 126 /* assumes sizeof(digest) > sizeof(ifid) */ 127 bcopy(digest, &in6->s6_addr[8], 8); 128 129 /* make sure to set "u" bit to local, and "g" bit to individual. */ 130 in6->s6_addr[8] &= ~EUI64_GBIT; /* g bit to "individual" */ 131 in6->s6_addr[8] |= EUI64_UBIT; /* u bit to "local" */ 132 133 /* convert EUI64 into IPv6 interface identifier */ 134 EUI64_TO_IFID(in6); 135 136 return 0; 137 } 138 139 static int 140 generate_tmp_ifid(seed0, seed1, ret) 141 u_int8_t *seed0, *ret; 142 const u_int8_t *seed1; 143 { 144 MD5_CTX ctxt; 145 u_int8_t seed[16], digest[16], nullbuf[8]; 146 u_int32_t val32; 147 struct timeval tv; 148 149 /* If there's no hisotry, start with a random seed. */ 150 bzero(nullbuf, sizeof(nullbuf)); 151 if (bcmp(nullbuf, seed0, sizeof(nullbuf)) == 0) { 152 int i; 153 154 for (i = 0; i < 2; i++) { 155 microtime(&tv); 156 val32 = random() ^ tv.tv_usec; 157 bcopy(&val32, seed + sizeof(val32) * i, sizeof(val32)); 158 } 159 } else { 160 bcopy(seed0, seed, 8); 161 } 162 163 /* copy the right-most 64-bits of the given address */ 164 /* XXX assumption on the size of IFID */ 165 bcopy(seed1, &seed[8], 8); 166 167 if (0) { /* for debugging purposes only */ 168 int i; 169 170 printf("generate_tmp_ifid: new randomized ID from: "); 171 for (i = 0; i < 16; i++) 172 printf("%02x", seed[i]); 173 printf(" "); 174 } 175 176 /* generate 16 bytes of pseudo-random value. */ 177 bzero(&ctxt, sizeof(ctxt)); 178 MD5Init(&ctxt); 179 MD5Update(&ctxt, seed, sizeof(seed)); 180 MD5Final(digest, &ctxt); 181 182 /* 183 * RFC 3041 3.2.1. (3) 184 * Take the left-most 64-bits of the MD5 digest and set bit 6 (the 185 * left-most bit is numbered 0) to zero. 186 */ 187 bcopy(digest, ret, 8); 188 ret[0] &= ~EUI64_UBIT; 189 190 /* 191 * XXX: we'd like to ensure that the generated value is not zero 192 * for simplicity. If the caclculated digest happens to be zero, 193 * use a random non-zero value as the last resort. 194 */ 195 if (bcmp(nullbuf, ret, sizeof(nullbuf)) == 0) { 196 log(LOG_INFO, 197 "generate_tmp_ifid: computed MD5 value is zero.\n"); 198 199 microtime(&tv); 200 val32 = random() ^ tv.tv_usec; 201 val32 = 1 + (val32 % (0xffffffff - 1)); 202 } 203 204 /* 205 * RFC 3041 3.2.1. (4) 206 * Take the rightmost 64-bits of the MD5 digest and save them in 207 * stable storage as the history value to be used in the next 208 * iteration of the algorithm. 209 */ 210 bcopy(&digest[8], seed0, 8); 211 212 if (0) { /* for debugging purposes only */ 213 int i; 214 215 printf("to: "); 216 for (i = 0; i < 16; i++) 217 printf("%02x", digest[i]); 218 printf("\n"); 219 } 220 221 return 0; 222 } 223 224 /* 225 * Get interface identifier for the specified interface. 226 * XXX assumes single sockaddr_dl (AF_LINK address) per an interface 227 */ 228 static int 229 get_hw_ifid(ifp, in6) 230 struct ifnet *ifp; 231 struct in6_addr *in6; /* upper 64bits are preserved */ 232 { 233 struct ifaddr *ifa; 234 struct sockaddr_dl *sdl; 235 u_int8_t *addr; 236 size_t addrlen; 237 static u_int8_t allzero[8] = { 0, 0, 0, 0, 0, 0, 0, 0 }; 238 static u_int8_t allone[8] = 239 { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 240 241 for (ifa = ifp->if_addrlist.tqh_first; 242 ifa; 243 ifa = ifa->ifa_list.tqe_next) 244 { 245 if (ifa->ifa_addr->sa_family != AF_LINK) 246 continue; 247 sdl = (struct sockaddr_dl *)ifa->ifa_addr; 248 if (sdl == NULL) 249 continue; 250 if (sdl->sdl_alen == 0) 251 continue; 252 253 goto found; 254 } 255 256 return -1; 257 258 found: 259 addr = LLADDR(sdl); 260 addrlen = sdl->sdl_alen; 261 262 /* get EUI64 */ 263 switch (ifp->if_type) { 264 case IFT_ETHER: 265 case IFT_FDDI: 266 case IFT_ISO88025: 267 case IFT_ATM: 268 case IFT_IEEE1394: 269 #ifdef IFT_IEEE80211 270 case IFT_IEEE80211: 271 #endif 272 /* IEEE802/EUI64 cases - what others? */ 273 /* IEEE1394 uses 16byte length address starting with EUI64 */ 274 if (addrlen > 8) 275 addrlen = 8; 276 277 /* look at IEEE802/EUI64 only */ 278 if (addrlen != 8 && addrlen != 6) 279 return -1; 280 281 /* 282 * check for invalid MAC address - on bsdi, we see it a lot 283 * since wildboar configures all-zero MAC on pccard before 284 * card insertion. 285 */ 286 if (bcmp(addr, allzero, addrlen) == 0) 287 return -1; 288 if (bcmp(addr, allone, addrlen) == 0) 289 return -1; 290 291 /* make EUI64 address */ 292 if (addrlen == 8) 293 bcopy(addr, &in6->s6_addr[8], 8); 294 else if (addrlen == 6) { 295 in6->s6_addr[8] = addr[0]; 296 in6->s6_addr[9] = addr[1]; 297 in6->s6_addr[10] = addr[2]; 298 in6->s6_addr[11] = 0xff; 299 in6->s6_addr[12] = 0xfe; 300 in6->s6_addr[13] = addr[3]; 301 in6->s6_addr[14] = addr[4]; 302 in6->s6_addr[15] = addr[5]; 303 } 304 break; 305 306 case IFT_ARCNET: 307 if (addrlen != 1) 308 return -1; 309 if (!addr[0]) 310 return -1; 311 312 bzero(&in6->s6_addr[8], 8); 313 in6->s6_addr[15] = addr[0]; 314 315 /* 316 * due to insufficient bitwidth, we mark it local. 317 */ 318 in6->s6_addr[8] &= ~EUI64_GBIT; /* g bit to "individual" */ 319 in6->s6_addr[8] |= EUI64_UBIT; /* u bit to "local" */ 320 break; 321 322 case IFT_GIF: 323 #ifdef IFT_STF 324 case IFT_STF: 325 #endif 326 /* 327 * RFC2893 says: "SHOULD use IPv4 address as ifid source". 328 * however, IPv4 address is not very suitable as unique 329 * identifier source (can be renumbered). 330 * we don't do this. 331 */ 332 return -1; 333 334 default: 335 return -1; 336 } 337 338 /* sanity check: g bit must not indicate "group" */ 339 if (EUI64_GROUP(in6)) 340 return -1; 341 342 /* convert EUI64 into IPv6 interface identifier */ 343 EUI64_TO_IFID(in6); 344 345 /* 346 * sanity check: ifid must not be all zero, avoid conflict with 347 * subnet router anycast 348 */ 349 if ((in6->s6_addr[8] & ~(EUI64_GBIT | EUI64_UBIT)) == 0x00 && 350 bcmp(&in6->s6_addr[9], allzero, 7) == 0) { 351 return -1; 352 } 353 354 return 0; 355 } 356 357 /* 358 * Get interface identifier for the specified interface. If it is not 359 * available on ifp0, borrow interface identifier from other information 360 * sources. 361 */ 362 static int 363 get_ifid(ifp0, altifp, in6) 364 struct ifnet *ifp0; 365 struct ifnet *altifp; /* secondary EUI64 source */ 366 struct in6_addr *in6; 367 { 368 struct ifnet *ifp; 369 370 /* first, try to get it from the interface itself */ 371 if (get_hw_ifid(ifp0, in6) == 0) { 372 nd6log((LOG_DEBUG, "%s: got interface identifier from itself\n", 373 if_name(ifp0))); 374 goto success; 375 } 376 377 /* try secondary EUI64 source. this basically is for ATM PVC */ 378 if (altifp && get_hw_ifid(altifp, in6) == 0) { 379 nd6log((LOG_DEBUG, "%s: got interface identifier from %s\n", 380 if_name(ifp0), if_name(altifp))); 381 goto success; 382 } 383 384 /* next, try to get it from some other hardware interface */ 385 IFNET_RLOCK(); 386 for (ifp = ifnet.tqh_first; ifp; ifp = ifp->if_list.tqe_next) 387 { 388 if (ifp == ifp0) 389 continue; 390 if (get_hw_ifid(ifp, in6) != 0) 391 continue; 392 393 /* 394 * to borrow ifid from other interface, ifid needs to be 395 * globally unique 396 */ 397 if (IFID_UNIVERSAL(in6)) { 398 nd6log((LOG_DEBUG, 399 "%s: borrow interface identifier from %s\n", 400 if_name(ifp0), if_name(ifp))); 401 IFNET_RUNLOCK(); 402 goto success; 403 } 404 } 405 IFNET_RUNLOCK(); 406 407 /* last resort: get from random number source */ 408 if (get_rand_ifid(ifp, in6) == 0) { 409 nd6log((LOG_DEBUG, 410 "%s: interface identifier generated by random number\n", 411 if_name(ifp0))); 412 goto success; 413 } 414 415 printf("%s: failed to get interface identifier\n", if_name(ifp0)); 416 return -1; 417 418 success: 419 nd6log((LOG_INFO, "%s: ifid: " 420 "%02x:%02x:%02x:%02x:%02x:%02x:%02x:%02x\n", 421 if_name(ifp0), 422 in6->s6_addr[8], in6->s6_addr[9], 423 in6->s6_addr[10], in6->s6_addr[11], 424 in6->s6_addr[12], in6->s6_addr[13], 425 in6->s6_addr[14], in6->s6_addr[15])); 426 return 0; 427 } 428 429 static int 430 in6_ifattach_linklocal(ifp, altifp) 431 struct ifnet *ifp; 432 struct ifnet *altifp; /* secondary EUI64 source */ 433 { 434 struct in6_ifaddr *ia; 435 struct in6_aliasreq ifra; 436 struct nd_prefix pr0; 437 int i, error; 438 439 /* 440 * configure link-local address. 441 */ 442 bzero(&ifra, sizeof(ifra)); 443 444 /* 445 * in6_update_ifa() does not use ifra_name, but we accurately set it 446 * for safety. 447 */ 448 strncpy(ifra.ifra_name, if_name(ifp), sizeof(ifra.ifra_name)); 449 450 ifra.ifra_addr.sin6_family = AF_INET6; 451 ifra.ifra_addr.sin6_len = sizeof(struct sockaddr_in6); 452 ifra.ifra_addr.sin6_addr.s6_addr16[0] = htons(0xfe80); 453 #ifdef SCOPEDROUTING 454 ifra.ifra_addr.sin6_addr.s6_addr16[1] = 0 455 #else 456 ifra.ifra_addr.sin6_addr.s6_addr16[1] = htons(ifp->if_index); /* XXX */ 457 #endif 458 ifra.ifra_addr.sin6_addr.s6_addr32[1] = 0; 459 if ((ifp->if_flags & IFF_LOOPBACK) != 0) { 460 ifra.ifra_addr.sin6_addr.s6_addr32[2] = 0; 461 ifra.ifra_addr.sin6_addr.s6_addr32[3] = htonl(1); 462 } else { 463 if (get_ifid(ifp, altifp, &ifra.ifra_addr.sin6_addr) != 0) { 464 nd6log((LOG_ERR, 465 "%s: no ifid available\n", if_name(ifp))); 466 return -1; 467 } 468 } 469 #ifdef SCOPEDROUTING 470 ifra.ifra_addr.sin6_scope_id = 471 in6_addr2scopeid(ifp, &ifra.ifra_addr.sin6_addr); 472 #endif 473 474 ifra.ifra_prefixmask.sin6_len = sizeof(struct sockaddr_in6); 475 ifra.ifra_prefixmask.sin6_family = AF_INET6; 476 ifra.ifra_prefixmask.sin6_addr = in6mask64; 477 #ifdef SCOPEDROUTING 478 /* take into accound the sin6_scope_id field for routing */ 479 ifra.ifra_prefixmask.sin6_scope_id = 0xffffffff; 480 #endif 481 /* link-local addresses should NEVER expire. */ 482 ifra.ifra_lifetime.ia6t_vltime = ND6_INFINITE_LIFETIME; 483 ifra.ifra_lifetime.ia6t_pltime = ND6_INFINITE_LIFETIME; 484 485 /* 486 * Do not let in6_update_ifa() do DAD, since we need a random delay 487 * before sending an NS at the first time the interface becomes up. 488 * Instead, in6_if_up() will start DAD with a proper random delay. 489 */ 490 ifra.ifra_flags |= IN6_IFF_NODAD; 491 492 /* 493 * Now call in6_update_ifa() to do a bunch of procedures to configure 494 * a link-local address. We can set NULL to the 3rd argument, because 495 * we know there's no other link-local address on the interface 496 * and therefore we are adding one (instead of updating one). 497 */ 498 if ((error = in6_update_ifa(ifp, &ifra, NULL)) != 0) { 499 /* 500 * XXX: When the interface does not support IPv6, this call 501 * would fail in the SIOCSIFADDR ioctl. I believe the 502 * notification is rather confusing in this case, so just 503 * supress it. (jinmei@kame.net 20010130) 504 */ 505 if (error != EAFNOSUPPORT) 506 log(LOG_NOTICE, "in6_ifattach_linklocal: failed to " 507 "configure a link-local address on %s " 508 "(errno=%d)\n", 509 if_name(ifp), error); 510 return(-1); 511 } 512 513 /* 514 * Adjust ia6_flags so that in6_if_up will perform DAD. 515 * XXX: Some P2P interfaces seem not to send packets just after 516 * becoming up, so we skip p2p interfaces for safety. 517 */ 518 ia = in6ifa_ifpforlinklocal(ifp, 0); /* ia must not be NULL */ 519 #ifdef DIAGNOSTIC 520 if (!ia) { 521 panic("ia == NULL in in6_ifattach_linklocal"); 522 /* NOTREACHED */ 523 } 524 #endif 525 if (in6if_do_dad(ifp) && (ifp->if_flags & IFF_POINTOPOINT) == 0) { 526 ia->ia6_flags &= ~IN6_IFF_NODAD; 527 ia->ia6_flags |= IN6_IFF_TENTATIVE; 528 } 529 530 /* 531 * Make the link-local prefix (fe80::/64%link) as on-link. 532 * Since we'd like to manage prefixes separately from addresses, 533 * we make an ND6 prefix structure for the link-local prefix, 534 * and add it to the prefix list as a never-expire prefix. 535 * XXX: this change might affect some existing code base... 536 */ 537 bzero(&pr0, sizeof(pr0)); 538 pr0.ndpr_ifp = ifp; 539 /* this should be 64 at this moment. */ 540 pr0.ndpr_plen = in6_mask2len(&ifra.ifra_prefixmask.sin6_addr, NULL); 541 pr0.ndpr_mask = ifra.ifra_prefixmask.sin6_addr; 542 pr0.ndpr_prefix = ifra.ifra_addr; 543 /* apply the mask for safety. (nd6_prelist_add will apply it again) */ 544 for (i = 0; i < 4; i++) { 545 pr0.ndpr_prefix.sin6_addr.s6_addr32[i] &= 546 in6mask64.s6_addr32[i]; 547 } 548 /* 549 * Initialize parameters. The link-local prefix must always be 550 * on-link, and its lifetimes never expire. 551 */ 552 pr0.ndpr_raf_onlink = 1; 553 pr0.ndpr_raf_auto = 1; /* probably meaningless */ 554 pr0.ndpr_vltime = ND6_INFINITE_LIFETIME; 555 pr0.ndpr_pltime = ND6_INFINITE_LIFETIME; 556 /* 557 * Since there is no other link-local addresses, nd6_prefix_lookup() 558 * probably returns NULL. However, we cannot always expect the result. 559 * For example, if we first remove the (only) existing link-local 560 * address, and then reconfigure another one, the prefix is still 561 * valid with referring to the old link-local address. 562 */ 563 if (nd6_prefix_lookup(&pr0) == NULL) { 564 if ((error = nd6_prelist_add(&pr0, NULL, NULL)) != 0) 565 return(error); 566 } 567 568 return 0; 569 } 570 571 static int 572 in6_ifattach_loopback(ifp) 573 struct ifnet *ifp; /* must be IFT_LOOP */ 574 { 575 struct in6_aliasreq ifra; 576 int error; 577 578 bzero(&ifra, sizeof(ifra)); 579 580 /* 581 * in6_update_ifa() does not use ifra_name, but we accurately set it 582 * for safety. 583 */ 584 strncpy(ifra.ifra_name, if_name(ifp), sizeof(ifra.ifra_name)); 585 586 ifra.ifra_prefixmask.sin6_len = sizeof(struct sockaddr_in6); 587 ifra.ifra_prefixmask.sin6_family = AF_INET6; 588 ifra.ifra_prefixmask.sin6_addr = in6mask128; 589 590 /* 591 * Always initialize ia_dstaddr (= broadcast address) to loopback 592 * address. Follows IPv4 practice - see in_ifinit(). 593 */ 594 ifra.ifra_dstaddr.sin6_len = sizeof(struct sockaddr_in6); 595 ifra.ifra_dstaddr.sin6_family = AF_INET6; 596 ifra.ifra_dstaddr.sin6_addr = in6addr_loopback; 597 598 ifra.ifra_addr.sin6_len = sizeof(struct sockaddr_in6); 599 ifra.ifra_addr.sin6_family = AF_INET6; 600 ifra.ifra_addr.sin6_addr = in6addr_loopback; 601 602 /* the loopback address should NEVER expire. */ 603 ifra.ifra_lifetime.ia6t_vltime = ND6_INFINITE_LIFETIME; 604 ifra.ifra_lifetime.ia6t_pltime = ND6_INFINITE_LIFETIME; 605 606 /* we don't need to perform DAD on loopback interfaces. */ 607 ifra.ifra_flags |= IN6_IFF_NODAD; 608 609 /* skip registration to the prefix list. XXX should be temporary. */ 610 ifra.ifra_flags |= IN6_IFF_NOPFX; 611 612 /* 613 * We are sure that this is a newly assigned address, so we can set 614 * NULL to the 3rd arg. 615 */ 616 if ((error = in6_update_ifa(ifp, &ifra, NULL)) != 0) { 617 log(LOG_ERR, "in6_ifattach_loopback: failed to configure " 618 "the loopback address on %s (errno=%d)\n", 619 if_name(ifp), error); 620 return(-1); 621 } 622 623 return 0; 624 } 625 626 /* 627 * compute NI group address, based on the current hostname setting. 628 * see draft-ietf-ipngwg-icmp-name-lookup-* (04 and later). 629 * 630 * when ifp == NULL, the caller is responsible for filling scopeid. 631 */ 632 int 633 in6_nigroup(ifp, name, namelen, in6) 634 struct ifnet *ifp; 635 const char *name; 636 int namelen; 637 struct in6_addr *in6; 638 { 639 const char *p; 640 u_char *q; 641 MD5_CTX ctxt; 642 u_int8_t digest[16]; 643 char l; 644 char n[64]; /* a single label must not exceed 63 chars */ 645 646 if (!namelen || !name) 647 return -1; 648 649 p = name; 650 while (p && *p && *p != '.' && p - name < namelen) 651 p++; 652 if (p - name > sizeof(n) - 1) 653 return -1; /* label too long */ 654 l = p - name; 655 strncpy(n, name, l); 656 n[(int)l] = '\0'; 657 for (q = n; *q; q++) { 658 if ('A' <= *q && *q <= 'Z') 659 *q = *q - 'A' + 'a'; 660 } 661 662 /* generate 8 bytes of pseudo-random value. */ 663 bzero(&ctxt, sizeof(ctxt)); 664 MD5Init(&ctxt); 665 MD5Update(&ctxt, &l, sizeof(l)); 666 MD5Update(&ctxt, n, l); 667 MD5Final(digest, &ctxt); 668 669 bzero(in6, sizeof(*in6)); 670 in6->s6_addr16[0] = htons(0xff02); 671 if (ifp) 672 in6->s6_addr16[1] = htons(ifp->if_index); 673 in6->s6_addr8[11] = 2; 674 bcopy(digest, &in6->s6_addr32[3], sizeof(in6->s6_addr32[3])); 675 676 return 0; 677 } 678 679 void 680 in6_nigroup_attach(name, namelen) 681 const char *name; 682 int namelen; 683 { 684 struct ifnet *ifp; 685 struct sockaddr_in6 mltaddr; 686 struct in6_multi *in6m; 687 int error; 688 689 bzero(&mltaddr, sizeof(mltaddr)); 690 mltaddr.sin6_family = AF_INET6; 691 mltaddr.sin6_len = sizeof(struct sockaddr_in6); 692 if (in6_nigroup(NULL, name, namelen, &mltaddr.sin6_addr) != 0) 693 return; 694 695 IFNET_RLOCK(); 696 for (ifp = ifnet.tqh_first; ifp; ifp = ifp->if_list.tqe_next) 697 { 698 mltaddr.sin6_addr.s6_addr16[1] = htons(ifp->if_index); 699 IN6_LOOKUP_MULTI(mltaddr.sin6_addr, ifp, in6m); 700 if (!in6m) { 701 if (!in6_addmulti(&mltaddr.sin6_addr, ifp, &error)) { 702 nd6log((LOG_ERR, "%s: failed to join %s " 703 "(errno=%d)\n", if_name(ifp), 704 ip6_sprintf(&mltaddr.sin6_addr), 705 error)); 706 } 707 } 708 } 709 IFNET_RUNLOCK(); 710 } 711 712 void 713 in6_nigroup_detach(name, namelen) 714 const char *name; 715 int namelen; 716 { 717 struct ifnet *ifp; 718 struct sockaddr_in6 mltaddr; 719 struct in6_multi *in6m; 720 721 bzero(&mltaddr, sizeof(mltaddr)); 722 mltaddr.sin6_family = AF_INET6; 723 mltaddr.sin6_len = sizeof(struct sockaddr_in6); 724 if (in6_nigroup(NULL, name, namelen, &mltaddr.sin6_addr) != 0) 725 return; 726 727 IFNET_RLOCK(); 728 for (ifp = ifnet.tqh_first; ifp; ifp = ifp->if_list.tqe_next) 729 { 730 mltaddr.sin6_addr.s6_addr16[1] = htons(ifp->if_index); 731 IN6_LOOKUP_MULTI(mltaddr.sin6_addr, ifp, in6m); 732 if (in6m) 733 in6_delmulti(in6m); 734 } 735 IFNET_RUNLOCK(); 736 } 737 738 /* 739 * XXX multiple loopback interface needs more care. for instance, 740 * nodelocal address needs to be configured onto only one of them. 741 * XXX multiple link-local address case 742 */ 743 void 744 in6_ifattach(ifp, altifp) 745 struct ifnet *ifp; 746 struct ifnet *altifp; /* secondary EUI64 source */ 747 { 748 static size_t if_indexlim = 8; 749 struct in6_ifaddr *ia; 750 struct in6_addr in6; 751 752 /* some of the interfaces are inherently not IPv6 capable */ 753 switch (ifp->if_type) { 754 #ifdef IFT_BRIDGE /*OpenBSD 2.8*/ 755 case IFT_BRIDGE: 756 return; 757 #endif 758 } 759 760 /* 761 * We have some arrays that should be indexed by if_index. 762 * since if_index will grow dynamically, they should grow too. 763 * struct in6_ifstat **in6_ifstat 764 * struct icmp6_ifstat **icmp6_ifstat 765 */ 766 if (in6_ifstat == NULL || icmp6_ifstat == NULL || 767 if_index >= if_indexlim) { 768 size_t n; 769 caddr_t q; 770 size_t olim; 771 772 olim = if_indexlim; 773 while (if_index >= if_indexlim) 774 if_indexlim <<= 1; 775 776 /* grow in6_ifstat */ 777 n = if_indexlim * sizeof(struct in6_ifstat *); 778 q = (caddr_t)malloc(n, M_IFADDR, M_WAITOK); 779 bzero(q, n); 780 if (in6_ifstat) { 781 bcopy((caddr_t)in6_ifstat, q, 782 olim * sizeof(struct in6_ifstat *)); 783 free((caddr_t)in6_ifstat, M_IFADDR); 784 } 785 in6_ifstat = (struct in6_ifstat **)q; 786 in6_ifstatmax = if_indexlim; 787 788 /* grow icmp6_ifstat */ 789 n = if_indexlim * sizeof(struct icmp6_ifstat *); 790 q = (caddr_t)malloc(n, M_IFADDR, M_WAITOK); 791 bzero(q, n); 792 if (icmp6_ifstat) { 793 bcopy((caddr_t)icmp6_ifstat, q, 794 olim * sizeof(struct icmp6_ifstat *)); 795 free((caddr_t)icmp6_ifstat, M_IFADDR); 796 } 797 icmp6_ifstat = (struct icmp6_ifstat **)q; 798 icmp6_ifstatmax = if_indexlim; 799 } 800 801 /* initialize scope identifiers */ 802 scope6_ifattach(ifp); 803 804 /* 805 * quirks based on interface type 806 */ 807 switch (ifp->if_type) { 808 #ifdef IFT_STF 809 case IFT_STF: 810 /* 811 * 6to4 interface is a very special kind of beast. 812 * no multicast, no linklocal. RFC2529 specifies how to make 813 * linklocals for 6to4 interface, but there's no use and 814 * it is rather harmful to have one. 815 */ 816 goto statinit; 817 #endif 818 default: 819 break; 820 } 821 822 /* 823 * usually, we require multicast capability to the interface 824 */ 825 if ((ifp->if_flags & IFF_MULTICAST) == 0) { 826 log(LOG_INFO, "in6_ifattach: " 827 "%s is not multicast capable, IPv6 not enabled\n", 828 if_name(ifp)); 829 return; 830 } 831 832 /* 833 * assign loopback address for loopback interface. 834 * XXX multiple loopback interface case. 835 */ 836 if ((ifp->if_flags & IFF_LOOPBACK) != 0) { 837 in6 = in6addr_loopback; 838 if (in6ifa_ifpwithaddr(ifp, &in6) == NULL) { 839 if (in6_ifattach_loopback(ifp) != 0) 840 return; 841 } 842 } 843 844 /* 845 * assign a link-local address, if there's none. 846 */ 847 if (ip6_auto_linklocal) { 848 ia = in6ifa_ifpforlinklocal(ifp, 0); 849 if (ia == NULL) { 850 if (in6_ifattach_linklocal(ifp, altifp) == 0) { 851 /* linklocal address assigned */ 852 } else { 853 /* failed to assign linklocal address. bark? */ 854 } 855 } 856 } 857 858 #ifdef IFT_STF /* XXX */ 859 statinit: 860 #endif 861 862 /* update dynamically. */ 863 if (in6_maxmtu < ifp->if_mtu) 864 in6_maxmtu = ifp->if_mtu; 865 866 if (in6_ifstat[ifp->if_index] == NULL) { 867 in6_ifstat[ifp->if_index] = (struct in6_ifstat *) 868 malloc(sizeof(struct in6_ifstat), M_IFADDR, M_WAITOK); 869 bzero(in6_ifstat[ifp->if_index], sizeof(struct in6_ifstat)); 870 } 871 if (icmp6_ifstat[ifp->if_index] == NULL) { 872 icmp6_ifstat[ifp->if_index] = (struct icmp6_ifstat *) 873 malloc(sizeof(struct icmp6_ifstat), M_IFADDR, M_WAITOK); 874 bzero(icmp6_ifstat[ifp->if_index], sizeof(struct icmp6_ifstat)); 875 } 876 877 /* initialize NDP variables */ 878 nd6_ifattach(ifp); 879 } 880 881 /* 882 * NOTE: in6_ifdetach() does not support loopback if at this moment. 883 * We don't need this function in bsdi, because interfaces are never removed 884 * from the ifnet list in bsdi. 885 */ 886 void 887 in6_ifdetach(ifp) 888 struct ifnet *ifp; 889 { 890 struct in6_ifaddr *ia, *oia; 891 struct ifaddr *ifa, *next; 892 struct rtentry *rt; 893 short rtflags; 894 struct sockaddr_in6 sin6; 895 struct in6_multi *in6m; 896 struct in6_multi *in6m_next; 897 898 /* nuke prefix list. this may try to remove some of ifaddrs as well */ 899 in6_purgeprefix(ifp); 900 901 /* remove neighbor management table */ 902 nd6_purge(ifp); 903 904 /* nuke any of IPv6 addresses we have */ 905 for (ifa = ifp->if_addrlist.tqh_first; ifa; ifa = next) 906 { 907 next = ifa->ifa_list.tqe_next; 908 if (ifa->ifa_addr->sa_family != AF_INET6) 909 continue; 910 in6_purgeaddr(ifa); 911 } 912 913 /* undo everything done by in6_ifattach(), just in case */ 914 for (ifa = ifp->if_addrlist.tqh_first; ifa; ifa = next) 915 { 916 next = ifa->ifa_list.tqe_next; 917 918 919 if (ifa->ifa_addr->sa_family != AF_INET6 920 || !IN6_IS_ADDR_LINKLOCAL(&satosin6(&ifa->ifa_addr)->sin6_addr)) { 921 continue; 922 } 923 924 ia = (struct in6_ifaddr *)ifa; 925 926 /* remove from the routing table */ 927 if ((ia->ia_flags & IFA_ROUTE) 928 && (rt = rtalloc1((struct sockaddr *)&ia->ia_addr, 0, 0UL))) { 929 rtflags = rt->rt_flags; 930 rtfree(rt); 931 rtrequest(RTM_DELETE, 932 (struct sockaddr *)&ia->ia_addr, 933 (struct sockaddr *)&ia->ia_addr, 934 (struct sockaddr *)&ia->ia_prefixmask, 935 rtflags, (struct rtentry **)0); 936 } 937 938 /* remove from the linked list */ 939 TAILQ_REMOVE(&ifp->if_addrlist, (struct ifaddr *)ia, ifa_list); 940 IFAFREE(&ia->ia_ifa); 941 942 /* also remove from the IPv6 address chain(itojun&jinmei) */ 943 oia = ia; 944 if (oia == (ia = in6_ifaddr)) 945 in6_ifaddr = ia->ia_next; 946 else { 947 while (ia->ia_next && (ia->ia_next != oia)) 948 ia = ia->ia_next; 949 if (ia->ia_next) 950 ia->ia_next = oia->ia_next; 951 else { 952 nd6log((LOG_ERR, 953 "%s: didn't unlink in6ifaddr from " 954 "list\n", if_name(ifp))); 955 } 956 } 957 958 IFAFREE(&oia->ia_ifa); 959 } 960 961 /* leave from all multicast groups joined */ 962 if (udbinfo.listhead != NULL) 963 in6_pcbpurgeif0(LIST_FIRST(udbinfo.listhead), ifp); 964 if (ripcbinfo.listhead != NULL) 965 in6_pcbpurgeif0(LIST_FIRST(ripcbinfo.listhead), ifp); 966 for (in6m = LIST_FIRST(&in6_multihead); in6m; in6m = in6m_next) { 967 in6m_next = LIST_NEXT(in6m, in6m_entry); 968 if (in6m->in6m_ifp != ifp) 969 continue; 970 in6_delmulti(in6m); 971 in6m = NULL; 972 } 973 974 /* 975 * remove neighbor management table. we call it twice just to make 976 * sure we nuke everything. maybe we need just one call. 977 * XXX: since the first call did not release addresses, some prefixes 978 * might remain. We should call nd6_purge() again to release the 979 * prefixes after removing all addresses above. 980 * (Or can we just delay calling nd6_purge until at this point?) 981 */ 982 nd6_purge(ifp); 983 984 /* remove route to link-local allnodes multicast (ff02::1) */ 985 bzero(&sin6, sizeof(sin6)); 986 sin6.sin6_len = sizeof(struct sockaddr_in6); 987 sin6.sin6_family = AF_INET6; 988 sin6.sin6_addr = in6addr_linklocal_allnodes; 989 sin6.sin6_addr.s6_addr16[1] = htons(ifp->if_index); 990 rt = rtalloc1((struct sockaddr *)&sin6, 0, 0UL); 991 if (rt && rt->rt_ifp == ifp) { 992 rtrequest(RTM_DELETE, (struct sockaddr *)rt_key(rt), 993 rt->rt_gateway, rt_mask(rt), rt->rt_flags, 0); 994 rtfree(rt); 995 } 996 } 997 998 void 999 in6_get_tmpifid(ifp, retbuf, baseid, generate) 1000 struct ifnet *ifp; 1001 u_int8_t *retbuf; 1002 const u_int8_t *baseid; 1003 int generate; 1004 { 1005 u_int8_t nullbuf[8]; 1006 struct nd_ifinfo *ndi = &nd_ifinfo[ifp->if_index]; 1007 1008 bzero(nullbuf, sizeof(nullbuf)); 1009 if (bcmp(ndi->randomid, nullbuf, sizeof(nullbuf)) == 0) { 1010 /* we've never created a random ID. Create a new one. */ 1011 generate = 1; 1012 } 1013 1014 if (generate) { 1015 bcopy(baseid, ndi->randomseed1, sizeof(ndi->randomseed1)); 1016 1017 /* generate_tmp_ifid will update seedn and buf */ 1018 (void)generate_tmp_ifid(ndi->randomseed0, ndi->randomseed1, 1019 ndi->randomid); 1020 } 1021 bcopy(ndi->randomid, retbuf, 8); 1022 } 1023 1024 void 1025 in6_tmpaddrtimer(ignored_arg) 1026 void *ignored_arg; 1027 { 1028 int i; 1029 struct nd_ifinfo *ndi; 1030 u_int8_t nullbuf[8]; 1031 int s = splnet(); 1032 1033 callout_reset(&in6_tmpaddrtimer_ch, 1034 (ip6_temp_preferred_lifetime - ip6_desync_factor - 1035 ip6_temp_regen_advance) * hz, 1036 in6_tmpaddrtimer, NULL); 1037 1038 bzero(nullbuf, sizeof(nullbuf)); 1039 for (i = 1; i < if_index + 1; i++) { 1040 ndi = &nd_ifinfo[i]; 1041 if (bcmp(ndi->randomid, nullbuf, sizeof(nullbuf)) != 0) { 1042 /* 1043 * We've been generating a random ID on this interface. 1044 * Create a new one. 1045 */ 1046 (void)generate_tmp_ifid(ndi->randomseed0, 1047 ndi->randomseed1, 1048 ndi->randomid); 1049 } 1050 } 1051 1052 splx(s); 1053 } 1054