1 /* 2 * Copyright (c) 1983, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions 7 * are met: 8 * 1. Redistributions of source code must retain the above copyright 9 * notice, this list of conditions and the following disclaimer. 10 * 2. Redistributions in binary form must reproduce the above copyright 11 * notice, this list of conditions and the following disclaimer in the 12 * documentation and/or other materials provided with the distribution. 13 * 3. All advertising materials mentioning features or use of this software 14 * must display the following acknowledgement: 15 * This product includes software developed by the University of 16 * California, Berkeley and its contributors. 17 * 4. Neither the name of the University nor the names of its contributors 18 * may be used to endorse or promote products derived from this software 19 * without specific prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 24 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 25 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 26 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 27 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 28 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 29 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 30 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 31 * SUCH DAMAGE. 32 */ 33 34 #if !defined(lint) && !defined(sgi) && !defined(__NetBSD__) 35 static char sccsid[] = "@(#)if.c 8.1 (Berkeley) 6/5/93"; 36 #elif defined(__NetBSD__) 37 static char rcsid[] = "$NetBSD$"; 38 #endif 39 #ident "$Revision: 1.22 $" 40 41 #include "defs.h" 42 #include "pathnames.h" 43 44 struct interface *ifnet; /* all interfaces */ 45 46 /* hash table for all interfaces, big enough to tolerate ridiculous 47 * numbers of IP aliases. Crazy numbers of aliases such as 7000 48 * still will not do well, but not just in looking up interfaces 49 * by name or address. 50 */ 51 #define AHASH_LEN 211 /* must be prime */ 52 #define AHASH(a) &ahash[(a)%AHASH_LEN] 53 struct interface *ahash[AHASH_LEN]; 54 55 #define BHASH_LEN 211 /* must be prime */ 56 #define BHASH(a) &bhash[(a)%BHASH_LEN] 57 struct interface *bhash[BHASH_LEN]; 58 59 struct interface *remote_if; /* remote interfaces */ 60 61 /* hash for physical interface names. 62 * Assume there are never more 100 or 200 real interfaces, and that 63 * aliases are put on the end of the hash chains. 64 */ 65 #define NHASH_LEN 97 66 struct interface *nhash[NHASH_LEN]; 67 68 int tot_interfaces; /* # of remote and local interfaces */ 69 int rip_interfaces; /* # of interfaces doing RIP */ 70 int foundloopback; /* valid flag for loopaddr */ 71 naddr loopaddr; /* our address on loopback */ 72 73 struct timeval ifinit_timer; 74 static struct timeval last_ifinit; 75 76 int have_ripv1_out; /* have a RIPv1 interface */ 77 int have_ripv1_in; 78 79 80 /* Link a new interface into the lists and hash tables. 81 */ 82 void 83 if_link(struct interface *ifp) 84 { 85 int i; 86 char *p; 87 struct interface **hifp; 88 89 ifp->int_prev = &ifnet; 90 ifp->int_next = ifnet; 91 if (ifnet != 0) 92 ifnet->int_prev = &ifp->int_next; 93 ifnet = ifp; 94 95 hifp = AHASH(ifp->int_addr); 96 ifp->int_ahash_prev = hifp; 97 ifp->int_ahash = *hifp; 98 if ((ifp->int_ahash = *hifp) != 0) 99 (*hifp)->int_ahash_prev = &ifp->int_ahash; 100 *hifp = ifp; 101 102 if (ifp->int_if_flags & IFF_BROADCAST) { 103 hifp = BHASH(ifp->int_brdaddr); 104 ifp->int_bhash = *hifp; 105 ifp->int_bhash_prev = hifp; 106 if ((ifp->int_bhash = *hifp) != 0) 107 (*hifp)->int_bhash_prev = &ifp->int_bhash; 108 *hifp = ifp; 109 } 110 111 if (ifp->int_state & IS_REMOTE) { 112 ifp->int_rlink_prev = &remote_if; 113 ifp->int_rlink = remote_if; 114 if (remote_if != 0) 115 remote_if->int_rlink_prev = &ifp->int_rlink; 116 remote_if = ifp; 117 } 118 119 for (i = 0, p = ifp->int_name; *p != '\0'; p++) 120 i += *p; 121 hifp = &nhash[i % NHASH_LEN]; 122 if (ifp->int_state & IS_ALIAS) { 123 /* put aliases on the end of the hash chain */ 124 while (*hifp != 0) 125 hifp = &(*hifp)->int_nhash; 126 } 127 ifp->int_nhash = *hifp; 128 ifp->int_nhash_prev = hifp; 129 if ((ifp->int_nhash = *hifp) != 0) 130 (*hifp)->int_nhash_prev = &ifp->int_nhash; 131 *hifp = ifp; 132 } 133 134 135 /* Find the interface with an address 136 */ 137 struct interface * 138 ifwithaddr(naddr addr, 139 int bcast, /* notice IFF_BROADCAST address */ 140 int remote) /* include IS_REMOTE interfaces */ 141 { 142 struct interface *ifp, *possible = 0; 143 144 remote = (remote == 0) ? IS_REMOTE : 0; 145 146 for (ifp = *AHASH(addr); ifp; ifp = ifp->int_ahash) { 147 if (ifp->int_addr != addr) 148 continue; 149 if ((ifp->int_state & remote) != 0) 150 continue; 151 if ((ifp->int_state & (IS_BROKE | IS_PASSIVE)) == 0) 152 return ifp; 153 possible = ifp; 154 } 155 156 if (possible || !bcast) 157 return possible; 158 159 for (ifp = *BHASH(addr); ifp; ifp = ifp->int_bhash) { 160 if (ifp->int_brdaddr != addr) 161 continue; 162 if ((ifp->int_state & remote) != 0) 163 continue; 164 if ((ifp->int_state & (IS_BROKE | IS_PASSIVE)) == 0) 165 return ifp; 166 possible = ifp; 167 } 168 169 return possible; 170 } 171 172 173 /* find the interface with a name 174 */ 175 struct interface * 176 ifwithname(char *name, /* "ec0" or whatever */ 177 naddr addr) /* 0 or network address */ 178 { 179 struct interface *ifp; 180 int i; 181 char *p; 182 183 for (;;) { 184 for (i = 0, p = name; *p != '\0'; p++) 185 i += *p; 186 ifp = nhash[i % NHASH_LEN]; 187 188 while (ifp != 0) { 189 /* If the network address is not specified, 190 * ignore any alias interfaces. Otherwise, look 191 * for the interface with the target name and address. 192 */ 193 if (!strcmp(ifp->int_name, name) 194 && ((addr == 0 && !(ifp->int_state & IS_ALIAS)) 195 || (ifp->int_addr == addr))) 196 return ifp; 197 ifp = ifp->int_nhash; 198 } 199 200 201 /* If there is no known interface, maybe there is a 202 * new interface. So just once look for new interfaces. 203 */ 204 if (last_ifinit.tv_sec == now.tv_sec 205 && last_ifinit.tv_usec == now.tv_usec) 206 return 0; 207 ifinit(); 208 } 209 } 210 211 212 struct interface * 213 ifwithindex(u_short index) 214 { 215 struct interface *ifp; 216 217 218 for (ifp = ifnet; 0 != ifp; ifp = ifp->int_next) { 219 if (ifp->int_index == index) 220 return ifp; 221 } 222 return 0; 223 } 224 225 226 /* Find an interface from which the specified address 227 * should have come from. Used for figuring out which 228 * interface a packet came in on. 229 */ 230 struct interface * 231 iflookup(naddr addr) 232 { 233 struct interface *ifp, *maybe; 234 235 maybe = 0; 236 for (;;) { 237 for (ifp = ifnet; ifp; ifp = ifp->int_next) { 238 if (ifp->int_if_flags & IFF_POINTOPOINT) { 239 /* finished with a match */ 240 if (ifp->int_dstaddr == addr) 241 return ifp; 242 243 } else { 244 /* finished with an exact match */ 245 if (ifp->int_addr == addr) 246 return ifp; 247 248 /* Look for the longest approximate match. 249 */ 250 if (on_net(addr, ifp->int_net, ifp->int_mask) 251 && (maybe == 0 252 || ifp->int_mask > maybe->int_mask)) 253 maybe = ifp; 254 } 255 } 256 257 if (maybe != 0 258 || (last_ifinit.tv_sec == now.tv_sec 259 && last_ifinit.tv_usec == now.tv_usec)) 260 return maybe; 261 262 /* If there is no known interface, maybe there is a 263 * new interface. So just once look for new interfaces. 264 */ 265 ifinit(); 266 } 267 } 268 269 270 /* Return the classical netmask for an IP address. 271 */ 272 naddr /* host byte order */ 273 std_mask(naddr addr) /* network byte order */ 274 { 275 NTOHL(addr); /* was a host, not a network */ 276 277 if (addr == 0) /* default route has mask 0 */ 278 return 0; 279 if (IN_CLASSA(addr)) 280 return IN_CLASSA_NET; 281 if (IN_CLASSB(addr)) 282 return IN_CLASSB_NET; 283 return IN_CLASSC_NET; 284 } 285 286 287 /* Find the netmask that would be inferred by RIPv1 listeners 288 * on the given interface for a given network. 289 * If no interface is specified, look for the best fitting interface. 290 */ 291 naddr 292 ripv1_mask_net(naddr addr, /* in network byte order */ 293 struct interface *ifp) /* as seen on this interface */ 294 { 295 naddr mask = 0; 296 297 if (addr == 0) /* default always has 0 mask */ 298 return mask; 299 300 if (ifp != 0) { 301 /* If the target network is that of the associated interface 302 * on which it arrived, then use the netmask of the interface. 303 */ 304 if (on_net(addr, ifp->int_net, ifp->int_std_mask)) 305 mask = ifp->int_ripv1_mask; 306 307 } else { 308 /* Examine all interfaces, and if it the target seems 309 * to have the same network number of an interface, use the 310 * netmask of that interface. If there is more than one 311 * such interface, prefer the interface with the longest 312 * match. 313 */ 314 for (ifp = ifnet; ifp != 0; ifp = ifp->int_next) { 315 if (on_net(addr, ifp->int_std_net, ifp->int_std_mask) 316 && ifp->int_ripv1_mask > mask) 317 mask = ifp->int_ripv1_mask; 318 } 319 } 320 321 /* Otherwise, make the classic A/B/C guess. 322 */ 323 if (mask == 0) 324 mask = std_mask(addr); 325 326 return mask; 327 } 328 329 330 naddr 331 ripv1_mask_host(naddr addr, /* in network byte order */ 332 struct interface *ifp) /* as seen on this interface */ 333 { 334 naddr mask = ripv1_mask_net(addr, ifp); 335 336 337 /* If the computed netmask does not mask the address, 338 * then assume it is a host address 339 */ 340 if ((ntohl(addr) & ~mask) != 0) 341 mask = HOST_MASK; 342 return mask; 343 } 344 345 346 /* See if a IP address looks reasonable as a destination 347 */ 348 int /* 0=bad */ 349 check_dst(naddr addr) 350 { 351 NTOHL(addr); 352 353 if (IN_CLASSA(addr)) { 354 if (addr == 0) 355 return 1; /* default */ 356 357 addr >>= IN_CLASSA_NSHIFT; 358 return (addr != 0 && addr != IN_LOOPBACKNET); 359 } 360 361 return (IN_CLASSB(addr) || IN_CLASSC(addr)); 362 } 363 364 365 /* See a new interface duplicates an existing interface. 366 */ 367 struct interface * 368 check_dup(naddr addr, /* IP address, so network byte order */ 369 naddr dstaddr, /* ditto */ 370 naddr mask, /* mask, so host byte order */ 371 int if_flags) 372 { 373 struct interface *ifp; 374 375 for (ifp = ifnet; 0 != ifp; ifp = ifp->int_next) { 376 if (ifp->int_mask != mask) 377 continue; 378 379 if (!iff_alive(ifp->int_if_flags)) 380 continue; 381 382 /* The local address can only be shared with a point-to- 383 * point link. 384 */ 385 if (ifp->int_addr == addr 386 && (((if_flags|ifp->int_if_flags) & IFF_POINTOPOINT) == 0)) 387 return ifp; 388 389 if (on_net(ifp->int_dstaddr, ntohl(dstaddr),mask)) 390 return ifp; 391 } 392 return 0; 393 } 394 395 396 /* See that a remote gateway is reachable. 397 * Note that the answer can change as real interfaces come and go. 398 */ 399 int /* 0=bad */ 400 check_remote(struct interface *ifp) 401 { 402 struct rt_entry *rt; 403 404 /* do not worry about other kinds */ 405 if (!(ifp->int_state & IS_REMOTE)) 406 return 1; 407 408 rt = rtfind(ifp->int_addr); 409 if (rt != 0 410 && rt->rt_ifp != 0 411 &&on_net(ifp->int_addr, 412 rt->rt_ifp->int_net, rt->rt_ifp->int_mask)) 413 return 1; 414 415 /* the gateway cannot be reached directly from one of our 416 * interfaces 417 */ 418 if (!(ifp->int_state & IS_BROKE)) { 419 msglog("unreachable gateway %s in "_PATH_GATEWAYS, 420 naddr_ntoa(ifp->int_addr)); 421 if_bad(ifp); 422 } 423 return 0; 424 } 425 426 427 /* Delete an interface. 428 */ 429 static void 430 ifdel(struct interface *ifp) 431 { 432 struct ip_mreq m; 433 struct interface *ifp1; 434 435 436 trace_if("Del", ifp); 437 438 ifp->int_state |= IS_BROKE; 439 440 /* unlink the interface 441 */ 442 *ifp->int_prev = ifp->int_next; 443 if (ifp->int_next != 0) 444 ifp->int_next->int_prev = ifp->int_prev; 445 *ifp->int_ahash_prev = ifp->int_ahash; 446 if (ifp->int_ahash != 0) 447 ifp->int_ahash->int_ahash_prev = ifp->int_ahash_prev; 448 if (ifp->int_if_flags & IFF_BROADCAST) { 449 *ifp->int_bhash_prev = ifp->int_bhash; 450 if (ifp->int_bhash != 0) 451 ifp->int_bhash->int_bhash_prev = ifp->int_bhash_prev; 452 } 453 if (ifp->int_state & IS_REMOTE) { 454 *ifp->int_rlink_prev = ifp->int_rlink; 455 if (ifp->int_rlink != 0) 456 ifp->int_rlink->int_rlink_prev = ifp->int_rlink_prev; 457 } 458 459 if (!(ifp->int_state & IS_ALIAS)) { 460 /* delete aliases when the main interface dies 461 */ 462 for (ifp1 = ifnet; 0 != ifp1; ifp1 = ifp1->int_next) { 463 if (ifp1 != ifp 464 && !strcmp(ifp->int_name, ifp1->int_name)) 465 ifdel(ifp1); 466 } 467 468 if ((ifp->int_if_flags & IFF_MULTICAST) 469 #ifdef MCAST_PPP_BUG 470 && !(ifp->int_if_flags & IFF_POINTOPOINT) 471 #endif 472 && rip_sock >= 0) { 473 m.imr_multiaddr.s_addr = htonl(INADDR_RIP_GROUP); 474 m.imr_interface.s_addr = ((ifp->int_if_flags 475 & IFF_POINTOPOINT) 476 ? ifp->int_dstaddr 477 : ifp->int_addr); 478 if (setsockopt(rip_sock,IPPROTO_IP,IP_DROP_MEMBERSHIP, 479 &m, sizeof(m)) < 0 480 && errno != EADDRNOTAVAIL 481 && !TRACEACTIONS) 482 LOGERR("setsockopt(IP_DROP_MEMBERSHIP RIP)"); 483 if (rip_sock_mcast == ifp) 484 rip_sock_mcast = 0; 485 } 486 if (ifp->int_rip_sock >= 0) { 487 (void)close(ifp->int_rip_sock); 488 ifp->int_rip_sock = -1; 489 fix_select(); 490 } 491 492 tot_interfaces--; 493 if (!IS_RIP_OFF(ifp->int_state)) 494 rip_interfaces--; 495 496 /* Zap all routes associated with this interface. 497 * Assume routes just using gateways beyond this interface will 498 * timeout naturally, and have probably already died. 499 */ 500 (void)rn_walktree(rhead, walk_bad, 0); 501 502 set_rdisc_mg(ifp, 0); 503 if_bad_rdisc(ifp); 504 } 505 506 free(ifp); 507 } 508 509 510 /* Mark an interface ill. 511 */ 512 void 513 if_sick(struct interface *ifp) 514 { 515 if (0 == (ifp->int_state & (IS_SICK | IS_BROKE))) { 516 ifp->int_state |= IS_SICK; 517 ifp->int_act_time = NEVER; 518 trace_if("Chg", ifp); 519 520 LIM_SEC(ifinit_timer, now.tv_sec+CHECK_BAD_INTERVAL); 521 } 522 } 523 524 525 /* Mark an interface dead. 526 */ 527 void 528 if_bad(struct interface *ifp) 529 { 530 struct interface *ifp1; 531 532 533 if (ifp->int_state & IS_BROKE) 534 return; 535 536 LIM_SEC(ifinit_timer, now.tv_sec+CHECK_BAD_INTERVAL); 537 538 ifp->int_state |= (IS_BROKE | IS_SICK); 539 ifp->int_act_time = NEVER; 540 ifp->int_query_time = NEVER; 541 ifp->int_data.ts = 0; 542 543 trace_if("Chg", ifp); 544 545 if (!(ifp->int_state & IS_ALIAS)) { 546 for (ifp1 = ifnet; 0 != ifp1; ifp1 = ifp1->int_next) { 547 if (ifp1 != ifp 548 && !strcmp(ifp->int_name, ifp1->int_name)) 549 if_bad(ifp1); 550 } 551 (void)rn_walktree(rhead, walk_bad, 0); 552 if_bad_rdisc(ifp); 553 } 554 } 555 556 557 /* Mark an interface alive 558 */ 559 int /* 1=it was dead */ 560 if_ok(struct interface *ifp, 561 char *type) 562 { 563 struct interface *ifp1; 564 565 566 if (!(ifp->int_state & IS_BROKE)) { 567 if (ifp->int_state & IS_SICK) { 568 trace_act("%sinterface %s to %s working better", 569 type, 570 ifp->int_name, naddr_ntoa(ifp->int_dstaddr)); 571 ifp->int_state &= ~IS_SICK; 572 } 573 return 0; 574 } 575 576 msglog("%sinterface %s to %s restored", 577 type, ifp->int_name, naddr_ntoa(ifp->int_dstaddr)); 578 ifp->int_state &= ~(IS_BROKE | IS_SICK); 579 ifp->int_data.ts = 0; 580 581 if (!(ifp->int_state & IS_ALIAS)) { 582 for (ifp1 = ifnet; 0 != ifp1; ifp1 = ifp1->int_next) { 583 if (ifp1 != ifp 584 && !strcmp(ifp->int_name, ifp1->int_name)) 585 if_ok(ifp1, type); 586 } 587 if_ok_rdisc(ifp); 588 } 589 590 if (ifp->int_state & IS_REMOTE) { 591 if (!addrouteforif(ifp)) 592 return 0; 593 } 594 return 1; 595 } 596 597 598 /* disassemble routing message 599 */ 600 void 601 rt_xaddrs(struct rt_addrinfo *info, 602 struct sockaddr *sa, 603 struct sockaddr *lim, 604 int addrs) 605 { 606 int i; 607 #ifdef _HAVE_SA_LEN 608 static struct sockaddr sa_zero; 609 #endif 610 #ifdef sgi 611 #define ROUNDUP(a) ((a) > 0 ? (1 + (((a) - 1) | (sizeof(__uint64_t) - 1))) \ 612 : sizeof(__uint64_t)) 613 #else 614 #define ROUNDUP(a) ((a) > 0 ? (1 + (((a) - 1) | (sizeof(long) - 1))) \ 615 : sizeof(long)) 616 #endif 617 618 619 bzero(info, sizeof(*info)); 620 info->rti_addrs = addrs; 621 for (i = 0; i < RTAX_MAX && sa < lim; i++) { 622 if ((addrs & (1 << i)) == 0) 623 continue; 624 #ifdef _HAVE_SA_LEN 625 info->rti_info[i] = (sa->sa_len != 0) ? sa : &sa_zero; 626 sa = (struct sockaddr *)((char*)(sa) 627 + ROUNDUP(sa->sa_len)); 628 #else 629 info->rti_info[i] = sa; 630 sa = (struct sockaddr *)((char*)(sa) 631 + ROUNDUP(_FAKE_SA_LEN_DST(sa))); 632 #endif 633 } 634 } 635 636 637 /* Find the network interfaces which have configured themselves. 638 * This must be done regularly, if only for extra addresses 639 * that come and go on interfaces. 640 */ 641 void 642 ifinit(void) 643 { 644 static char *sysctl_buf; 645 static size_t sysctl_buf_size = 0; 646 uint complaints = 0; 647 static u_int prev_complaints = 0; 648 # define COMP_NOT_INET 0x001 649 # define COMP_NOADDR 0x002 650 # define COMP_BADADDR 0x004 651 # define COMP_NODST 0x008 652 # define COMP_NOBADR 0x010 653 # define COMP_NOMASK 0x020 654 # define COMP_DUP 0x040 655 # define COMP_BAD_METRIC 0x080 656 # define COMP_NETMASK 0x100 657 658 struct interface ifs, ifs0, *ifp, *ifp1; 659 struct rt_entry *rt; 660 size_t needed; 661 int mib[6]; 662 struct if_msghdr *ifm; 663 struct ifa_msghdr *ifam, *ifam_lim, *ifam2; 664 int in, ierr, out, oerr; 665 struct intnet *intnetp; 666 struct rt_addrinfo info; 667 #ifdef SIOCGIFMETRIC 668 struct ifreq ifr; 669 #endif 670 671 672 last_ifinit = now; 673 ifinit_timer.tv_sec = now.tv_sec + (supplier 674 ? CHECK_ACT_INTERVAL 675 : CHECK_QUIET_INTERVAL); 676 677 /* mark all interfaces so we can get rid of thost that disappear */ 678 for (ifp = ifnet; 0 != ifp; ifp = ifp->int_next) 679 ifp->int_state &= ~(IS_CHECKED | IS_DUP); 680 681 /* Fetch the interface list, without too many system calls 682 * since we do it repeatedly. 683 */ 684 mib[0] = CTL_NET; 685 mib[1] = PF_ROUTE; 686 mib[2] = 0; 687 mib[3] = AF_INET; 688 mib[4] = NET_RT_IFLIST; 689 mib[5] = 0; 690 for (;;) { 691 if ((needed = sysctl_buf_size) != 0) { 692 if (sysctl(mib, 6, sysctl_buf,&needed, 0, 0) >= 0) 693 break; 694 if (errno != ENOMEM && errno != EFAULT) 695 BADERR(1, "ifinit: get interface table"); 696 free(sysctl_buf); 697 needed = 0; 698 } 699 if (sysctl(mib, 6, 0, &needed, 0, 0) < 0) 700 BADERR(1,"ifinit: route-sysctl-estimate"); 701 sysctl_buf = rtmalloc(sysctl_buf_size = needed, "ifinit"); 702 } 703 704 ifam_lim = (struct ifa_msghdr *)(sysctl_buf + needed); 705 for (ifam = (struct ifa_msghdr *)sysctl_buf; 706 ifam < ifam_lim; 707 ifam = ifam2) { 708 709 ifam2 = (struct ifa_msghdr*)((char*)ifam + ifam->ifam_msglen); 710 711 if (ifam->ifam_type == RTM_IFINFO) { 712 struct sockaddr_dl *sdl; 713 714 ifm = (struct if_msghdr *)ifam; 715 /* make prototype structure for the IP aliases 716 */ 717 bzero(&ifs0, sizeof(ifs0)); 718 ifs0.int_rip_sock = -1; 719 ifs0.int_index = ifm->ifm_index; 720 ifs0.int_if_flags = ifm->ifm_flags; 721 ifs0.int_state = IS_CHECKED; 722 ifs0.int_query_time = NEVER; 723 ifs0.int_act_time = now.tv_sec; 724 ifs0.int_data.ts = now.tv_sec; 725 ifs0.int_data.ipackets = ifm->ifm_data.ifi_ipackets; 726 ifs0.int_data.ierrors = ifm->ifm_data.ifi_ierrors; 727 ifs0.int_data.opackets = ifm->ifm_data.ifi_opackets; 728 ifs0.int_data.oerrors = ifm->ifm_data.ifi_oerrors; 729 #ifdef sgi 730 ifs0.int_data.odrops = ifm->ifm_data.ifi_odrops; 731 #endif 732 sdl = (struct sockaddr_dl *)(ifm + 1); 733 sdl->sdl_data[sdl->sdl_nlen] = 0; 734 strncpy(ifs0.int_name, sdl->sdl_data, 735 MIN(sizeof(ifs0.int_name), sdl->sdl_nlen)); 736 continue; 737 } 738 if (ifam->ifam_type != RTM_NEWADDR) { 739 logbad(1,"ifinit: out of sync"); 740 continue; 741 } 742 rt_xaddrs(&info, (struct sockaddr *)(ifam+1), 743 (struct sockaddr *)ifam2, 744 ifam->ifam_addrs); 745 746 /* Prepare for the next address of this interface, which 747 * will be an alias. 748 * Do not output RIP or Router-Discovery packets via aliases. 749 */ 750 bcopy(&ifs0, &ifs, sizeof(ifs)); 751 ifs0.int_state |= (IS_ALIAS | IS_NO_RIP | IS_NO_RDISC); 752 753 if (INFO_IFA(&info) == 0) { 754 if (iff_alive(ifs.int_if_flags)) { 755 if (!(prev_complaints & COMP_NOADDR)) 756 msglog("%s has no address", 757 ifs.int_name); 758 complaints |= COMP_NOADDR; 759 } 760 continue; 761 } 762 if (INFO_IFA(&info)->sa_family != AF_INET) { 763 if (iff_alive(ifs.int_if_flags)) { 764 if (!(prev_complaints & COMP_NOT_INET)) 765 trace_act("%s: not AF_INET", 766 ifs.int_name); 767 complaints |= COMP_NOT_INET; 768 } 769 continue; 770 } 771 772 ifs.int_addr = S_ADDR(INFO_IFA(&info)); 773 774 if (ntohl(ifs.int_addr)>>24 == 0 775 || ntohl(ifs.int_addr)>>24 == 0xff) { 776 if (iff_alive(ifs.int_if_flags)) { 777 if (!(prev_complaints & COMP_BADADDR)) 778 msglog("%s has a bad address", 779 ifs.int_name); 780 complaints |= COMP_BADADDR; 781 } 782 continue; 783 } 784 785 if (ifs.int_if_flags & IFF_LOOPBACK) { 786 ifs.int_state |= IS_PASSIVE | IS_NO_RIP | IS_NO_RDISC; 787 ifs.int_dstaddr = ifs.int_addr; 788 ifs.int_mask = HOST_MASK; 789 ifs.int_ripv1_mask = HOST_MASK; 790 ifs.int_std_mask = std_mask(ifs.int_dstaddr); 791 ifs.int_net = ntohl(ifs.int_dstaddr); 792 if (!foundloopback) { 793 foundloopback = 1; 794 loopaddr = ifs.int_addr; 795 } 796 797 } else if (ifs.int_if_flags & IFF_POINTOPOINT) { 798 if (INFO_BRD(&info) == 0 799 || INFO_BRD(&info)->sa_family != AF_INET) { 800 if (iff_alive(ifs.int_if_flags)) { 801 if (!(prev_complaints & COMP_NODST)) 802 msglog("%s has a bad" 803 " destination address", 804 ifs.int_name); 805 complaints |= COMP_NODST; 806 } 807 continue; 808 } 809 ifs.int_dstaddr = S_ADDR(INFO_BRD(&info)); 810 if (ntohl(ifs.int_dstaddr)>>24 == 0 811 || ntohl(ifs.int_dstaddr)>>24 == 0xff) { 812 if (iff_alive(ifs.int_if_flags)) { 813 if (!(prev_complaints & COMP_NODST)) 814 msglog("%s has a bad" 815 " destination address", 816 ifs.int_name); 817 complaints |= COMP_NODST; 818 } 819 continue; 820 } 821 ifs.int_mask = HOST_MASK; 822 ifs.int_ripv1_mask = ntohl(S_ADDR(INFO_MASK(&info))); 823 ifs.int_std_mask = std_mask(ifs.int_dstaddr); 824 ifs.int_net = ntohl(ifs.int_dstaddr); 825 826 } else { 827 if (INFO_MASK(&info) == 0) { 828 if (iff_alive(ifs.int_if_flags)) { 829 if (!(prev_complaints & COMP_NOMASK)) 830 msglog("%s has no netmask", 831 ifs.int_name); 832 complaints |= COMP_NOMASK; 833 } 834 continue; 835 } 836 ifs.int_dstaddr = ifs.int_addr; 837 ifs.int_mask = ntohl(S_ADDR(INFO_MASK(&info))); 838 ifs.int_ripv1_mask = ifs.int_mask; 839 ifs.int_std_mask = std_mask(ifs.int_addr); 840 ifs.int_net = ntohl(ifs.int_addr) & ifs.int_mask; 841 if (ifs.int_mask != ifs.int_std_mask) 842 ifs.int_state |= IS_SUBNET; 843 844 if (ifs.int_if_flags & IFF_BROADCAST) { 845 if (INFO_BRD(&info) == 0) { 846 if (iff_alive(ifs.int_if_flags)) { 847 if (!(prev_complaints 848 & COMP_NOBADR)) 849 msglog("%s has" 850 "no broadcast address", 851 ifs.int_name); 852 complaints |= COMP_NOBADR; 853 } 854 continue; 855 } 856 ifs.int_brdaddr = S_ADDR(INFO_BRD(&info)); 857 } 858 } 859 ifs.int_std_net = ifs.int_net & ifs.int_std_mask; 860 ifs.int_std_addr = htonl(ifs.int_std_net); 861 862 /* Use a minimum metric of one. Treat the interface metric 863 * (default 0) as an increment to the hop count of one. 864 * 865 * The metric obtained from the routing socket dump of 866 * interface addresses is wrong. It is not set by the 867 * SIOCSIFMETRIC ioctl. 868 */ 869 #ifdef SIOCGIFMETRIC 870 strncpy(ifr.ifr_name, ifs.int_name, sizeof(ifr.ifr_name)); 871 if (ioctl(rt_sock, SIOCGIFMETRIC, &ifr) < 0) { 872 DBGERR(1, "ioctl(SIOCGIFMETRIC)"); 873 ifs.int_metric = 0; 874 } else { 875 ifs.int_metric = ifr.ifr_metric; 876 } 877 #else 878 ifs.int_metric = ifam->ifam_metric; 879 #endif 880 if (ifs.int_metric > HOPCNT_INFINITY) { 881 ifs.int_metric = 0; 882 if (!(prev_complaints & COMP_BAD_METRIC) 883 && iff_alive(ifs.int_if_flags)) { 884 complaints |= COMP_BAD_METRIC; 885 msglog("%s has a metric of %d", 886 ifs.int_name, ifs.int_metric); 887 } 888 } 889 890 /* See if this is a familiar interface. 891 * If so, stop worrying about it if it is the same. 892 * Start it over if it now is to somewhere else, as happens 893 * frequently with PPP and SLIP. 894 */ 895 ifp = ifwithname(ifs.int_name, ((ifs.int_state & IS_ALIAS) 896 ? ifs.int_addr 897 : 0)); 898 if (ifp != 0) { 899 ifp->int_state |= IS_CHECKED; 900 901 if (0 != ((ifp->int_if_flags ^ ifs.int_if_flags) 902 & (IFF_BROADCAST 903 | IFF_LOOPBACK 904 | IFF_POINTOPOINT 905 | IFF_MULTICAST)) 906 || 0 != ((ifp->int_state ^ ifs.int_state) 907 & IS_ALIAS) 908 || ifp->int_addr != ifs.int_addr 909 || ifp->int_brdaddr != ifs.int_brdaddr 910 || ifp->int_dstaddr != ifs.int_dstaddr 911 || ifp->int_mask != ifs.int_mask 912 || ifp->int_metric != ifs.int_metric) { 913 /* Forget old information about 914 * a changed interface. 915 */ 916 trace_act("interface %s has changed", 917 ifp->int_name); 918 ifdel(ifp); 919 ifp = 0; 920 } 921 } 922 923 if (ifp != 0) { 924 /* The primary representative of an alias worries 925 * about how things are working. 926 */ 927 if (ifp->int_state & IS_ALIAS) 928 continue; 929 930 /* note interfaces that have been turned off 931 */ 932 if (!iff_alive(ifs.int_if_flags)) { 933 if (iff_alive(ifp->int_if_flags)) { 934 msglog("interface %s to %s turned off", 935 ifp->int_name, 936 naddr_ntoa(ifp->int_dstaddr)); 937 if_bad(ifp); 938 ifp->int_if_flags &= ~IFF_UP_RUNNING; 939 } 940 continue; 941 } 942 /* or that were off and are now ok */ 943 if (!iff_alive(ifp->int_if_flags)) { 944 ifp->int_if_flags |= IFF_UP_RUNNING; 945 (void)if_ok(ifp, ""); 946 } 947 948 /* If it has been long enough, 949 * see if the interface is broken. 950 */ 951 if (now.tv_sec < ifp->int_data.ts+CHECK_BAD_INTERVAL) 952 continue; 953 954 in = ifs.int_data.ipackets - ifp->int_data.ipackets; 955 ierr = ifs.int_data.ierrors - ifp->int_data.ierrors; 956 out = ifs.int_data.opackets - ifp->int_data.opackets; 957 oerr = ifs.int_data.oerrors - ifp->int_data.oerrors; 958 #ifdef sgi 959 /* Through at least IRIX 6.2, PPP and SLIP 960 * count packets dropped by the filters. 961 * But FDDI rings stuck non-operational count 962 * dropped packets as they wait for improvement. 963 */ 964 if (!(ifp->int_if_flags & IFF_POINTOPOINT)) 965 oerr += (ifs.int_data.odrops 966 - ifp->int_data.odrops); 967 #endif 968 /* If the interface just awoke, restart the counters. 969 */ 970 if (ifp->int_data.ts == 0) { 971 ifp->int_data = ifs.int_data; 972 continue; 973 } 974 ifp->int_data = ifs.int_data; 975 976 /* Withhold judgement when the short error 977 * counters wrap or the interface is reset. 978 */ 979 if (ierr < 0 || in < 0 || oerr < 0 || out < 0) { 980 LIM_SEC(ifinit_timer, 981 now.tv_sec+CHECK_BAD_INTERVAL); 982 continue; 983 } 984 985 /* Withhold judgement when there is no traffic 986 */ 987 if (in == 0 && out == 0 && ierr == 0 && oerr == 0) 988 continue; 989 990 /* It is bad if input or output is not working. 991 * Require presistent problems before marking it dead. 992 */ 993 if ((in <= ierr && ierr > 0) 994 || (out <= oerr && oerr > 0)) { 995 if (!(ifp->int_state & IS_SICK)) { 996 trace_act("interface %s to %s" 997 " sick: in=%d ierr=%d" 998 " out=%d oerr=%d", 999 ifp->int_name, 1000 naddr_ntoa(ifp->int_dstaddr), 1001 in, ierr, out, oerr); 1002 if_sick(ifp); 1003 continue; 1004 } 1005 if (!(ifp->int_state & IS_BROKE)) { 1006 msglog("interface %s to %s broken:" 1007 " in=%d ierr=%d out=%d oerr=%d", 1008 ifp->int_name, 1009 naddr_ntoa(ifp->int_dstaddr), 1010 in, ierr, out, oerr); 1011 if_bad(ifp); 1012 } 1013 continue; 1014 } 1015 1016 /* otherwise, it is active and healthy 1017 */ 1018 ifp->int_act_time = now.tv_sec; 1019 (void)if_ok(ifp, ""); 1020 continue; 1021 } 1022 1023 /* This is a new interface. 1024 * If it is dead, forget it. 1025 */ 1026 if (!iff_alive(ifs.int_if_flags)) 1027 continue; 1028 1029 /* If it duplicates an existing interface, 1030 * complain about it, mark the other one 1031 * duplicated, and forget this one. 1032 */ 1033 ifp = check_dup(ifs.int_addr,ifs.int_dstaddr,ifs.int_mask, 1034 ifs.int_if_flags); 1035 if (ifp != 0) { 1036 if (!(prev_complaints & COMP_DUP)) { 1037 complaints |= COMP_DUP; 1038 msglog("%s (%s%s%s) is duplicated by" 1039 " %s (%s%s%s)", 1040 ifs.int_name, 1041 addrname(ifs.int_addr,ifs.int_mask,1), 1042 ((ifs.int_if_flags & IFF_POINTOPOINT) 1043 ? "-->" : ""), 1044 ((ifs.int_if_flags & IFF_POINTOPOINT) 1045 ? naddr_ntoa(ifs.int_dstaddr) : ""), 1046 ifp->int_name, 1047 addrname(ifp->int_addr,ifp->int_mask,1), 1048 ((ifp->int_if_flags & IFF_POINTOPOINT) 1049 ? "-->" : ""), 1050 ((ifp->int_if_flags & IFF_POINTOPOINT) 1051 ? naddr_ntoa(ifp->int_dstaddr) : "")); 1052 } 1053 ifp->int_state |= IS_DUP; 1054 continue; 1055 } 1056 1057 if (0 == (ifs.int_if_flags & (IFF_POINTOPOINT | IFF_BROADCAST)) 1058 && !(ifs.int_state & IS_PASSIVE)) { 1059 trace_act("%s is neither broadcast, point-to-point," 1060 " nor loopback", 1061 ifs.int_name); 1062 if (!(ifs.int_state & IFF_MULTICAST)) 1063 ifs.int_state |= IS_NO_RDISC; 1064 } 1065 1066 1067 /* It is new and ok. Add it to the list of interfaces 1068 */ 1069 ifp = (struct interface *)rtmalloc(sizeof(*ifp), "ifinit"); 1070 bcopy(&ifs, ifp, sizeof(*ifp)); 1071 get_parms(ifp); 1072 if_link(ifp); 1073 trace_if("Add", ifp); 1074 1075 /* Notice likely bad netmask. 1076 */ 1077 if (!(prev_complaints & COMP_NETMASK) 1078 && !(ifp->int_if_flags & IFF_POINTOPOINT) 1079 && ifp->int_addr != RIP_DEFAULT) { 1080 for (ifp1 = ifnet; 0 != ifp1; ifp1 = ifp1->int_next) { 1081 if (ifp1->int_mask == ifp->int_mask) 1082 continue; 1083 if (ifp1->int_if_flags & IFF_POINTOPOINT) 1084 continue; 1085 if (ifp1->int_dstaddr == RIP_DEFAULT) 1086 continue; 1087 if (on_net(ifp->int_dstaddr, 1088 ifp1->int_net, ifp1->int_mask) 1089 || on_net(ifp1->int_dstaddr, 1090 ifp->int_net, ifp->int_mask)) { 1091 msglog("possible netmask problem" 1092 " between %s:%s and %s:%s", 1093 ifp->int_name, 1094 addrname(htonl(ifp->int_net), 1095 ifp->int_mask, 1), 1096 ifp1->int_name, 1097 addrname(htonl(ifp1->int_net), 1098 ifp1->int_mask, 1)); 1099 complaints |= COMP_NETMASK; 1100 } 1101 } 1102 } 1103 1104 if (!(ifp->int_state & IS_ALIAS)) { 1105 /* Count the # of directly connected networks. 1106 */ 1107 if (!(ifp->int_if_flags & IFF_LOOPBACK)) 1108 tot_interfaces++; 1109 if (!IS_RIP_OFF(ifp->int_state)) 1110 rip_interfaces++; 1111 1112 /* turn on router discovery and RIP If needed */ 1113 if_ok_rdisc(ifp); 1114 rip_on(ifp); 1115 } 1116 } 1117 1118 /* If we are multi-homed and have at least two interfaces 1119 * listening to RIP, then output by default. 1120 */ 1121 if (!supplier_set && rip_interfaces > 1) 1122 set_supplier(); 1123 1124 /* If we are multi-homed, optionally advertise a route to 1125 * our main address. 1126 */ 1127 if (advertise_mhome 1128 || (tot_interfaces > 1 1129 && mhome 1130 && (ifp = ifwithaddr(myaddr, 0, 0)) != 0 1131 && foundloopback)) { 1132 advertise_mhome = 1; 1133 rt = rtget(myaddr, HOST_MASK); 1134 if (rt != 0) { 1135 if (rt->rt_ifp != ifp 1136 || rt->rt_router != loopaddr) { 1137 rtdelete(rt); 1138 rt = 0; 1139 } else { 1140 rtchange(rt, rt->rt_state | RS_MHOME, 1141 loopaddr, loopaddr, 1142 0, 0, ifp, rt->rt_time, 0); 1143 } 1144 } 1145 if (rt == 0) 1146 rtadd(myaddr, HOST_MASK, loopaddr, loopaddr, 1147 0, 0, RS_MHOME, ifp); 1148 } 1149 1150 for (ifp = ifnet; ifp != 0; ifp = ifp1) { 1151 ifp1 = ifp->int_next; /* because we may delete it */ 1152 1153 /* Forget any interfaces that have disappeared. 1154 */ 1155 if (!(ifp->int_state & (IS_CHECKED | IS_REMOTE))) { 1156 trace_act("interface %s has disappeared", 1157 ifp->int_name); 1158 ifdel(ifp); 1159 continue; 1160 } 1161 1162 if ((ifp->int_state & IS_BROKE) 1163 && !(ifp->int_state & IS_PASSIVE)) 1164 LIM_SEC(ifinit_timer, now.tv_sec+CHECK_BAD_INTERVAL); 1165 1166 /* If we ever have a RIPv1 interface, assume we always will. 1167 * It might come back if it ever goes away. 1168 */ 1169 if (!(ifp->int_state & IS_NO_RIPV1_OUT) && supplier) 1170 have_ripv1_out = 1; 1171 if (!(ifp->int_state & IS_NO_RIPV1_IN)) 1172 have_ripv1_in = 1; 1173 } 1174 1175 for (ifp = ifnet; ifp != 0; ifp = ifp->int_next) { 1176 /* Ensure there is always a network route for interfaces, 1177 * after any dead interfaces have been deleted, which 1178 * might affect routes for point-to-point links. 1179 */ 1180 if (!addrouteforif(ifp)) 1181 continue; 1182 1183 /* Add routes to the local end of point-to-point interfaces 1184 * using loopback. 1185 */ 1186 if ((ifp->int_if_flags & IFF_POINTOPOINT) 1187 && !(ifp->int_state & IS_REMOTE) 1188 && foundloopback) { 1189 /* Delete any routes to the network address through 1190 * foreign routers. Remove even static routes. 1191 */ 1192 del_static(ifp->int_addr, HOST_MASK, 0); 1193 rt = rtget(ifp->int_addr, HOST_MASK); 1194 if (rt != 0 && rt->rt_router != loopaddr) { 1195 rtdelete(rt); 1196 rt = 0; 1197 } 1198 if (rt != 0) { 1199 if (!(rt->rt_state & RS_LOCAL) 1200 || rt->rt_metric > ifp->int_metric) { 1201 ifp1 = ifp; 1202 } else { 1203 ifp1 = rt->rt_ifp; 1204 } 1205 rtchange(rt,((rt->rt_state & ~RS_NET_SYN) 1206 | (RS_IF|RS_LOCAL)), 1207 loopaddr, loopaddr, 1208 0, 0, ifp1, rt->rt_time, 0); 1209 } else { 1210 rtadd(ifp->int_addr, HOST_MASK, 1211 loopaddr, loopaddr, 1212 0, 0, (RS_IF | RS_LOCAL), ifp); 1213 } 1214 } 1215 } 1216 1217 /* add the authority routes */ 1218 for (intnetp = intnets; intnetp!=0; intnetp = intnetp->intnet_next) { 1219 rt = rtget(intnetp->intnet_addr, intnetp->intnet_mask); 1220 if (rt != 0 1221 && !(rt->rt_state & RS_NO_NET_SYN) 1222 && !(rt->rt_state & RS_NET_INT)) { 1223 rtdelete(rt); 1224 rt = 0; 1225 } 1226 if (rt == 0) 1227 rtadd(intnetp->intnet_addr, intnetp->intnet_mask, 1228 loopaddr, loopaddr, intnetp->intnet_metric-1, 1229 0, RS_NET_SYN | RS_NET_INT, 0); 1230 } 1231 1232 prev_complaints = complaints; 1233 } 1234 1235 1236 static void 1237 check_net_syn(struct interface *ifp) 1238 { 1239 struct rt_entry *rt; 1240 1241 1242 /* Turn on the need to automatically synthesize a network route 1243 * for this interface only if we are running RIPv1 on some other 1244 * interface that is on a different class-A,B,or C network. 1245 */ 1246 if (have_ripv1_out || have_ripv1_in) { 1247 ifp->int_state |= IS_NEED_NET_SYN; 1248 rt = rtget(ifp->int_std_addr, ifp->int_std_mask); 1249 if (rt != 0 1250 && 0 == (rt->rt_state & RS_NO_NET_SYN) 1251 && (!(rt->rt_state & RS_NET_SYN) 1252 || rt->rt_metric > ifp->int_metric)) { 1253 rtdelete(rt); 1254 rt = 0; 1255 } 1256 if (rt == 0) 1257 rtadd(ifp->int_std_addr, ifp->int_std_mask, 1258 ifp->int_addr, ifp->int_addr, 1259 ifp->int_metric, 0, RS_NET_SYN, ifp); 1260 1261 } else { 1262 ifp->int_state &= ~IS_NEED_NET_SYN; 1263 1264 rt = rtget(ifp->int_std_addr, 1265 ifp->int_std_mask); 1266 if (rt != 0 1267 && (rt->rt_state & RS_NET_SYN) 1268 && rt->rt_ifp == ifp) 1269 rtbad_sub(rt); 1270 } 1271 } 1272 1273 1274 /* Add route for interface if not currently installed. 1275 * Create route to other end if a point-to-point link, 1276 * otherwise a route to this (sub)network. 1277 */ 1278 int /* 0=bad interface */ 1279 addrouteforif(struct interface *ifp) 1280 { 1281 struct rt_entry *rt; 1282 naddr dst, gate; 1283 1284 1285 /* skip sick interfaces 1286 */ 1287 if (ifp->int_state & IS_BROKE) 1288 return 0; 1289 1290 /* If the interface on a subnet, then install a RIPv1 route to 1291 * the network as well (unless it is sick). 1292 */ 1293 if (ifp->int_state & IS_SUBNET) 1294 check_net_syn(ifp); 1295 1296 gate = ifp->int_addr; 1297 dst = (0 != (ifp->int_if_flags & (IFF_POINTOPOINT | IFF_LOOPBACK)) 1298 ? ifp->int_dstaddr 1299 : htonl(ifp->int_net)); 1300 1301 /* If we are going to send packets to the gateway, 1302 * it must be reachable using our physical interfaces 1303 */ 1304 if ((ifp->int_state & IS_REMOTE) 1305 && !(ifp->int_state & IS_EXTERNAL) 1306 && !check_remote(ifp)) 1307 return 0; 1308 1309 /* We are finished if the correct main interface route exists. 1310 * The right route must be for the right interface, not synthesized 1311 * from a subnet, be a "gateway" or not as appropriate, and so forth. 1312 */ 1313 del_static(dst, ifp->int_mask, 0); 1314 rt = rtget(dst, ifp->int_mask); 1315 if (rt != 0) { 1316 if ((rt->rt_ifp != ifp 1317 || rt->rt_router != ifp->int_addr) 1318 && (!(ifp->int_state & IS_DUP) 1319 || rt->rt_ifp == 0 1320 || (rt->rt_ifp->int_state & IS_BROKE))) { 1321 rtdelete(rt); 1322 rt = 0; 1323 } else { 1324 rtchange(rt, ((rt->rt_state | RS_IF) 1325 & ~(RS_NET_SYN | RS_LOCAL)), 1326 ifp->int_addr, ifp->int_addr, 1327 ifp->int_metric, 0, ifp, now.tv_sec, 0); 1328 } 1329 } 1330 if (rt == 0) { 1331 if (ifp->int_transitions++ > 0) 1332 trace_act("re-install interface %s", 1333 ifp->int_name); 1334 1335 rtadd(dst, ifp->int_mask, gate, gate, 1336 ifp->int_metric, 0, RS_IF, ifp); 1337 } 1338 1339 return 1; 1340 } 1341