1 /* $OpenBSD: lde.c,v 1.84 2024/11/21 13:38:14 claudio Exp $ */ 2 3 /* 4 * Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org> 5 * Copyright (c) 2004, 2005 Claudio Jeker <claudio@openbsd.org> 6 * Copyright (c) 2004 Esben Norby <norby@openbsd.org> 7 * Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org> 8 * 9 * Permission to use, copy, modify, and distribute this software for any 10 * purpose with or without fee is hereby granted, provided that the above 11 * copyright notice and this permission notice appear in all copies. 12 * 13 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 14 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 15 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 16 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 17 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 18 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 19 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 20 */ 21 22 #include <sys/types.h> 23 #include <sys/time.h> 24 #include <sys/socket.h> 25 #include <netinet/in.h> 26 #include <netmpls/mpls.h> 27 #include <arpa/inet.h> 28 #include <errno.h> 29 #include <stdlib.h> 30 #include <signal.h> 31 #include <string.h> 32 #include <pwd.h> 33 #include <unistd.h> 34 #include <limits.h> 35 36 #include "ldp.h" 37 #include "ldpd.h" 38 #include "ldpe.h" 39 #include "log.h" 40 #include "lde.h" 41 42 static void lde_sig_handler(int sig, short, void *); 43 static __dead void lde_shutdown(void); 44 static int lde_imsg_compose_parent(int, pid_t, void *, uint16_t); 45 static void lde_dispatch_imsg(int, short, void *); 46 static void lde_dispatch_parent(int, short, void *); 47 static __inline int lde_nbr_compare(struct lde_nbr *, 48 struct lde_nbr *); 49 static struct lde_nbr *lde_nbr_new(uint32_t, struct lde_nbr *); 50 static void lde_nbr_del(struct lde_nbr *); 51 static struct lde_nbr *lde_nbr_find(uint32_t); 52 static void lde_nbr_clear(void); 53 static void lde_nbr_addr_update(struct lde_nbr *, 54 struct lde_addr *, int); 55 static void lde_map_free(void *); 56 static int lde_address_add(struct lde_nbr *, struct lde_addr *); 57 static int lde_address_del(struct lde_nbr *, struct lde_addr *); 58 static void lde_address_list_free(struct lde_nbr *); 59 60 RB_GENERATE(nbr_tree, lde_nbr, entry, lde_nbr_compare) 61 62 struct ldpd_conf *ldeconf; 63 struct nbr_tree lde_nbrs = RB_INITIALIZER(&lde_nbrs); 64 65 static struct imsgev *iev_ldpe; 66 static struct imsgev *iev_main; 67 68 static void 69 lde_sig_handler(int sig, short event, void *arg) 70 { 71 /* 72 * signal handler rules don't apply, libevent decouples for us 73 */ 74 75 switch (sig) { 76 case SIGINT: 77 case SIGTERM: 78 lde_shutdown(); 79 /* NOTREACHED */ 80 default: 81 fatalx("unexpected signal"); 82 } 83 } 84 85 /* label decision engine */ 86 void 87 lde(int debug, int verbose) 88 { 89 struct event ev_sigint, ev_sigterm; 90 struct timeval now; 91 struct passwd *pw; 92 93 ldeconf = config_new_empty(); 94 95 log_init(debug); 96 log_verbose(verbose); 97 98 setproctitle("label decision engine"); 99 ldpd_process = PROC_LDE_ENGINE; 100 log_procname = "lde"; 101 102 if ((pw = getpwnam(LDPD_USER)) == NULL) 103 fatal("getpwnam"); 104 105 if (chroot(pw->pw_dir) == -1) 106 fatal("chroot"); 107 if (chdir("/") == -1) 108 fatal("chdir(\"/\")"); 109 110 if (setgroups(1, &pw->pw_gid) || 111 setresgid(pw->pw_gid, pw->pw_gid, pw->pw_gid) || 112 setresuid(pw->pw_uid, pw->pw_uid, pw->pw_uid)) 113 fatal("can't drop privileges"); 114 115 if (pledge("stdio recvfd", NULL) == -1) 116 fatal("pledge"); 117 118 event_init(); 119 120 /* setup signal handler */ 121 signal_set(&ev_sigint, SIGINT, lde_sig_handler, NULL); 122 signal_set(&ev_sigterm, SIGTERM, lde_sig_handler, NULL); 123 signal_add(&ev_sigint, NULL); 124 signal_add(&ev_sigterm, NULL); 125 signal(SIGPIPE, SIG_IGN); 126 signal(SIGHUP, SIG_IGN); 127 128 /* setup pipe and event handler to the parent process */ 129 if ((iev_main = malloc(sizeof(struct imsgev))) == NULL) 130 fatal(NULL); 131 if (imsgbuf_init(&iev_main->ibuf, 3) == -1) 132 fatal(NULL); 133 imsgbuf_allow_fdpass(&iev_main->ibuf); 134 iev_main->handler = lde_dispatch_parent; 135 iev_main->events = EV_READ; 136 event_set(&iev_main->ev, iev_main->ibuf.fd, iev_main->events, 137 iev_main->handler, iev_main); 138 event_add(&iev_main->ev, NULL); 139 140 /* setup and start the LIB garbage collector */ 141 evtimer_set(&gc_timer, lde_gc_timer, NULL); 142 lde_gc_start_timer(); 143 144 gettimeofday(&now, NULL); 145 global.uptime = now.tv_sec; 146 147 event_dispatch(); 148 149 lde_shutdown(); 150 } 151 152 static __dead void 153 lde_shutdown(void) 154 { 155 /* close pipes */ 156 imsgbuf_clear(&iev_ldpe->ibuf); 157 close(iev_ldpe->ibuf.fd); 158 imsgbuf_clear(&iev_main->ibuf); 159 close(iev_main->ibuf.fd); 160 161 lde_gc_stop_timer(); 162 lde_nbr_clear(); 163 fec_tree_clear(); 164 165 config_clear(ldeconf); 166 167 free(iev_ldpe); 168 free(iev_main); 169 170 log_info("label decision engine exiting"); 171 exit(0); 172 } 173 174 /* imesg */ 175 static int 176 lde_imsg_compose_parent(int type, pid_t pid, void *data, uint16_t datalen) 177 { 178 return (imsg_compose_event(iev_main, type, 0, pid, -1, data, datalen)); 179 } 180 181 int 182 lde_imsg_compose_ldpe(int type, uint32_t peerid, pid_t pid, void *data, 183 uint16_t datalen) 184 { 185 return (imsg_compose_event(iev_ldpe, type, peerid, pid, 186 -1, data, datalen)); 187 } 188 189 static void 190 lde_dispatch_imsg(int fd, short event, void *bula) 191 { 192 struct imsgev *iev = bula; 193 struct imsgbuf *ibuf = &iev->ibuf; 194 struct imsg imsg; 195 struct lde_nbr *ln; 196 struct map map; 197 struct lde_addr lde_addr; 198 struct notify_msg nm; 199 ssize_t n; 200 int shut = 0, verbose; 201 202 if (event & EV_READ) { 203 if ((n = imsgbuf_read(ibuf)) == -1) 204 fatal("imsgbuf_read error"); 205 if (n == 0) /* connection closed */ 206 shut = 1; 207 } 208 if (event & EV_WRITE) { 209 if (imsgbuf_write(ibuf) == -1) { 210 if (errno == EPIPE) /* connection closed */ 211 shut = 1; 212 else 213 fatal("imsgbuf_write"); 214 } 215 } 216 217 for (;;) { 218 if ((n = imsg_get(ibuf, &imsg)) == -1) 219 fatal("lde_dispatch_imsg: imsg_get error"); 220 if (n == 0) 221 break; 222 223 switch (imsg.hdr.type) { 224 case IMSG_LABEL_MAPPING_FULL: 225 ln = lde_nbr_find(imsg.hdr.peerid); 226 if (ln == NULL) { 227 log_debug("%s: cannot find lde neighbor", 228 __func__); 229 break; 230 } 231 232 fec_snap(ln); 233 break; 234 case IMSG_LABEL_MAPPING: 235 case IMSG_LABEL_REQUEST: 236 case IMSG_LABEL_RELEASE: 237 case IMSG_LABEL_WITHDRAW: 238 case IMSG_LABEL_ABORT: 239 if (imsg.hdr.len - IMSG_HEADER_SIZE != sizeof(map)) 240 fatalx("lde_dispatch_imsg: wrong imsg len"); 241 memcpy(&map, imsg.data, sizeof(map)); 242 243 ln = lde_nbr_find(imsg.hdr.peerid); 244 if (ln == NULL) { 245 log_debug("%s: cannot find lde neighbor", 246 __func__); 247 break; 248 } 249 250 switch (imsg.hdr.type) { 251 case IMSG_LABEL_MAPPING: 252 lde_check_mapping(&map, ln); 253 break; 254 case IMSG_LABEL_REQUEST: 255 lde_check_request(&map, ln); 256 break; 257 case IMSG_LABEL_RELEASE: 258 lde_check_release(&map, ln); 259 break; 260 case IMSG_LABEL_WITHDRAW: 261 lde_check_withdraw(&map, ln); 262 break; 263 case IMSG_LABEL_ABORT: 264 /* not necessary */ 265 break; 266 } 267 break; 268 case IMSG_ADDRESS_ADD: 269 if (imsg.hdr.len - IMSG_HEADER_SIZE != sizeof(lde_addr)) 270 fatalx("lde_dispatch_imsg: wrong imsg len"); 271 memcpy(&lde_addr, imsg.data, sizeof(lde_addr)); 272 273 ln = lde_nbr_find(imsg.hdr.peerid); 274 if (ln == NULL) { 275 log_debug("%s: cannot find lde neighbor", 276 __func__); 277 break; 278 } 279 if (lde_address_add(ln, &lde_addr) < 0) { 280 log_debug("%s: cannot add address %s, it " 281 "already exists", __func__, 282 log_addr(lde_addr.af, &lde_addr.addr)); 283 } 284 break; 285 case IMSG_ADDRESS_DEL: 286 if (imsg.hdr.len - IMSG_HEADER_SIZE != sizeof(lde_addr)) 287 fatalx("lde_dispatch_imsg: wrong imsg len"); 288 memcpy(&lde_addr, imsg.data, sizeof(lde_addr)); 289 290 ln = lde_nbr_find(imsg.hdr.peerid); 291 if (ln == NULL) { 292 log_debug("%s: cannot find lde neighbor", 293 __func__); 294 break; 295 } 296 if (lde_address_del(ln, &lde_addr) < 0) { 297 log_debug("%s: cannot delete address %s, it " 298 "does not exist", __func__, 299 log_addr(lde_addr.af, &lde_addr.addr)); 300 } 301 break; 302 case IMSG_NOTIFICATION: 303 if (imsg.hdr.len - IMSG_HEADER_SIZE != sizeof(nm)) 304 fatalx("lde_dispatch_imsg: wrong imsg len"); 305 memcpy(&nm, imsg.data, sizeof(nm)); 306 307 ln = lde_nbr_find(imsg.hdr.peerid); 308 if (ln == NULL) { 309 log_debug("%s: cannot find lde neighbor", 310 __func__); 311 break; 312 } 313 314 switch (nm.status_code) { 315 case S_PW_STATUS: 316 l2vpn_recv_pw_status(ln, &nm); 317 break; 318 case S_ENDOFLIB: 319 /* 320 * Do nothing for now. Should be useful in 321 * the future when we implement LDP-IGP 322 * Synchronization (RFC 5443) and Graceful 323 * Restart (RFC 3478). 324 */ 325 default: 326 break; 327 } 328 break; 329 case IMSG_NEIGHBOR_UP: 330 if (imsg.hdr.len - IMSG_HEADER_SIZE != 331 sizeof(struct lde_nbr)) 332 fatalx("lde_dispatch_imsg: wrong imsg len"); 333 334 if (lde_nbr_find(imsg.hdr.peerid)) 335 fatalx("lde_dispatch_imsg: " 336 "neighbor already exists"); 337 lde_nbr_new(imsg.hdr.peerid, imsg.data); 338 break; 339 case IMSG_NEIGHBOR_DOWN: 340 lde_nbr_del(lde_nbr_find(imsg.hdr.peerid)); 341 break; 342 case IMSG_CTL_SHOW_LIB: 343 rt_dump(imsg.hdr.pid); 344 345 lde_imsg_compose_ldpe(IMSG_CTL_END, 0, 346 imsg.hdr.pid, NULL, 0); 347 break; 348 case IMSG_CTL_SHOW_L2VPN_PW: 349 l2vpn_pw_ctl(imsg.hdr.pid); 350 351 lde_imsg_compose_ldpe(IMSG_CTL_END, 0, 352 imsg.hdr.pid, NULL, 0); 353 break; 354 case IMSG_CTL_SHOW_L2VPN_BINDING: 355 l2vpn_binding_ctl(imsg.hdr.pid); 356 357 lde_imsg_compose_ldpe(IMSG_CTL_END, 0, 358 imsg.hdr.pid, NULL, 0); 359 break; 360 case IMSG_CTL_LOG_VERBOSE: 361 /* already checked by ldpe */ 362 memcpy(&verbose, imsg.data, sizeof(verbose)); 363 log_verbose(verbose); 364 break; 365 default: 366 log_debug("%s: unexpected imsg %d", __func__, 367 imsg.hdr.type); 368 break; 369 } 370 imsg_free(&imsg); 371 } 372 if (!shut) 373 imsg_event_add(iev); 374 else { 375 /* this pipe is dead, so remove the event handler */ 376 event_del(&iev->ev); 377 event_loopexit(NULL); 378 } 379 } 380 381 static void 382 lde_dispatch_parent(int fd, short event, void *bula) 383 { 384 static struct ldpd_conf *nconf; 385 struct iface *niface; 386 struct tnbr *ntnbr; 387 struct nbr_params *nnbrp; 388 static struct l2vpn *nl2vpn; 389 struct l2vpn_if *nlif; 390 struct l2vpn_pw *npw; 391 struct imsg imsg; 392 struct kroute kr; 393 struct imsgev *iev = bula; 394 struct imsgbuf *ibuf = &iev->ibuf; 395 ssize_t n; 396 int shut = 0; 397 struct fec fec; 398 399 if (event & EV_READ) { 400 if ((n = imsgbuf_read(ibuf)) == -1) 401 fatal("imsgbuf_read error"); 402 if (n == 0) /* connection closed */ 403 shut = 1; 404 } 405 if (event & EV_WRITE) { 406 if (imsgbuf_write(ibuf) == -1) { 407 if (errno == EPIPE) /* connection closed */ 408 shut = 1; 409 else 410 fatal("imsgbuf_write"); 411 } 412 } 413 414 for (;;) { 415 if ((n = imsg_get(ibuf, &imsg)) == -1) 416 fatal("lde_dispatch_parent: imsg_get error"); 417 if (n == 0) 418 break; 419 420 switch (imsg.hdr.type) { 421 case IMSG_NETWORK_ADD: 422 case IMSG_NETWORK_DEL: 423 if (imsg.hdr.len != IMSG_HEADER_SIZE + sizeof(kr)) { 424 log_warnx("%s: wrong imsg len", __func__); 425 break; 426 } 427 memcpy(&kr, imsg.data, sizeof(kr)); 428 429 switch (kr.af) { 430 case AF_INET: 431 fec.type = FEC_TYPE_IPV4; 432 fec.u.ipv4.prefix = kr.prefix.v4; 433 fec.u.ipv4.prefixlen = kr.prefixlen; 434 break; 435 case AF_INET6: 436 fec.type = FEC_TYPE_IPV6; 437 fec.u.ipv6.prefix = kr.prefix.v6; 438 fec.u.ipv6.prefixlen = kr.prefixlen; 439 break; 440 default: 441 fatalx("lde_dispatch_parent: unknown af"); 442 } 443 444 switch (imsg.hdr.type) { 445 case IMSG_NETWORK_ADD: 446 lde_kernel_insert(&fec, kr.af, &kr.nexthop, 447 kr.priority, kr.flags & F_CONNECTED, NULL); 448 break; 449 case IMSG_NETWORK_DEL: 450 lde_kernel_remove(&fec, kr.af, &kr.nexthop, 451 kr.priority); 452 break; 453 } 454 break; 455 case IMSG_SOCKET_IPC: 456 if (iev_ldpe) { 457 log_warnx("%s: received unexpected imsg fd " 458 "to ldpe", __func__); 459 break; 460 } 461 if ((fd = imsg_get_fd(&imsg)) == -1) { 462 log_warnx("%s: expected to receive imsg fd to " 463 "ldpe but didn't receive any", __func__); 464 break; 465 } 466 467 if ((iev_ldpe = malloc(sizeof(struct imsgev))) == NULL) 468 fatal(NULL); 469 if (imsgbuf_init(&iev_ldpe->ibuf, fd) == -1) 470 fatal(NULL); 471 iev_ldpe->handler = lde_dispatch_imsg; 472 iev_ldpe->events = EV_READ; 473 event_set(&iev_ldpe->ev, iev_ldpe->ibuf.fd, 474 iev_ldpe->events, iev_ldpe->handler, iev_ldpe); 475 event_add(&iev_ldpe->ev, NULL); 476 break; 477 case IMSG_RECONF_CONF: 478 if ((nconf = malloc(sizeof(struct ldpd_conf))) == 479 NULL) 480 fatal(NULL); 481 memcpy(nconf, imsg.data, sizeof(struct ldpd_conf)); 482 483 LIST_INIT(&nconf->iface_list); 484 LIST_INIT(&nconf->tnbr_list); 485 LIST_INIT(&nconf->nbrp_list); 486 LIST_INIT(&nconf->l2vpn_list); 487 LIST_INIT(&nconf->auth_list); 488 break; 489 case IMSG_RECONF_IFACE: 490 if ((niface = malloc(sizeof(struct iface))) == NULL) 491 fatal(NULL); 492 memcpy(niface, imsg.data, sizeof(struct iface)); 493 494 LIST_INIT(&niface->addr_list); 495 LIST_INIT(&niface->ipv4.adj_list); 496 LIST_INIT(&niface->ipv6.adj_list); 497 niface->ipv4.iface = niface; 498 niface->ipv6.iface = niface; 499 500 LIST_INSERT_HEAD(&nconf->iface_list, niface, entry); 501 break; 502 case IMSG_RECONF_TNBR: 503 if ((ntnbr = malloc(sizeof(struct tnbr))) == NULL) 504 fatal(NULL); 505 memcpy(ntnbr, imsg.data, sizeof(struct tnbr)); 506 507 LIST_INSERT_HEAD(&nconf->tnbr_list, ntnbr, entry); 508 break; 509 case IMSG_RECONF_NBRP: 510 if ((nnbrp = malloc(sizeof(struct nbr_params))) == NULL) 511 fatal(NULL); 512 memcpy(nnbrp, imsg.data, sizeof(struct nbr_params)); 513 514 LIST_INSERT_HEAD(&nconf->nbrp_list, nnbrp, entry); 515 break; 516 case IMSG_RECONF_L2VPN: 517 if ((nl2vpn = malloc(sizeof(struct l2vpn))) == NULL) 518 fatal(NULL); 519 memcpy(nl2vpn, imsg.data, sizeof(struct l2vpn)); 520 521 LIST_INIT(&nl2vpn->if_list); 522 LIST_INIT(&nl2vpn->pw_list); 523 524 LIST_INSERT_HEAD(&nconf->l2vpn_list, nl2vpn, entry); 525 break; 526 case IMSG_RECONF_L2VPN_IF: 527 if ((nlif = malloc(sizeof(struct l2vpn_if))) == NULL) 528 fatal(NULL); 529 memcpy(nlif, imsg.data, sizeof(struct l2vpn_if)); 530 531 nlif->l2vpn = nl2vpn; 532 LIST_INSERT_HEAD(&nl2vpn->if_list, nlif, entry); 533 break; 534 case IMSG_RECONF_L2VPN_PW: 535 if ((npw = malloc(sizeof(struct l2vpn_pw))) == NULL) 536 fatal(NULL); 537 memcpy(npw, imsg.data, sizeof(struct l2vpn_pw)); 538 539 npw->l2vpn = nl2vpn; 540 LIST_INSERT_HEAD(&nl2vpn->pw_list, npw, entry); 541 break; 542 case IMSG_RECONF_CONF_AUTH: { 543 struct ldp_auth *auth; 544 545 auth = malloc(sizeof(*auth)); 546 if (auth == NULL) 547 fatal(NULL); 548 549 memcpy(auth, imsg.data, sizeof(*auth)); 550 551 LIST_INSERT_HEAD(&nconf->auth_list, auth, entry); 552 break; 553 } 554 case IMSG_RECONF_END: 555 merge_config(ldeconf, nconf); 556 nconf = NULL; 557 break; 558 default: 559 log_debug("%s: unexpected imsg %d", __func__, 560 imsg.hdr.type); 561 break; 562 } 563 imsg_free(&imsg); 564 } 565 if (!shut) 566 imsg_event_add(iev); 567 else { 568 /* this pipe is dead, so remove the event handler */ 569 event_del(&iev->ev); 570 event_loopexit(NULL); 571 } 572 } 573 574 uint32_t 575 lde_assign_label(void) 576 { 577 static uint32_t label = MPLS_LABEL_RESERVED_MAX; 578 579 /* XXX some checks needed */ 580 label++; 581 return (label); 582 } 583 584 void 585 lde_send_change_klabel(struct fec_node *fn, struct fec_nh *fnh) 586 { 587 struct kroute kr; 588 struct kpw kpw; 589 struct l2vpn_pw *pw; 590 591 switch (fn->fec.type) { 592 case FEC_TYPE_IPV4: 593 memset(&kr, 0, sizeof(kr)); 594 kr.af = AF_INET; 595 kr.prefix.v4 = fn->fec.u.ipv4.prefix; 596 kr.prefixlen = fn->fec.u.ipv4.prefixlen; 597 kr.nexthop.v4 = fnh->nexthop.v4; 598 kr.local_label = fn->local_label; 599 kr.remote_label = fnh->remote_label; 600 kr.priority = fnh->priority; 601 602 lde_imsg_compose_parent(IMSG_KLABEL_CHANGE, 0, &kr, 603 sizeof(kr)); 604 605 if (fn->fec.u.ipv4.prefixlen == 32) 606 l2vpn_sync_pws(AF_INET, (union ldpd_addr *) 607 &fn->fec.u.ipv4.prefix); 608 break; 609 case FEC_TYPE_IPV6: 610 memset(&kr, 0, sizeof(kr)); 611 kr.af = AF_INET6; 612 kr.prefix.v6 = fn->fec.u.ipv6.prefix; 613 kr.prefixlen = fn->fec.u.ipv6.prefixlen; 614 kr.nexthop.v6 = fnh->nexthop.v6; 615 kr.local_label = fn->local_label; 616 kr.remote_label = fnh->remote_label; 617 kr.priority = fnh->priority; 618 619 lde_imsg_compose_parent(IMSG_KLABEL_CHANGE, 0, &kr, 620 sizeof(kr)); 621 622 if (fn->fec.u.ipv6.prefixlen == 128) 623 l2vpn_sync_pws(AF_INET6, (union ldpd_addr *) 624 &fn->fec.u.ipv6.prefix); 625 break; 626 case FEC_TYPE_PWID: 627 if (fn->local_label == NO_LABEL || 628 fnh->remote_label == NO_LABEL) 629 return; 630 631 pw = (struct l2vpn_pw *) fn->data; 632 pw->flags |= F_PW_STATUS_UP; 633 634 memset(&kpw, 0, sizeof(kpw)); 635 kpw.ifindex = pw->ifindex; 636 kpw.pw_type = fn->fec.u.pwid.type; 637 kpw.af = pw->af; 638 kpw.nexthop = pw->addr; 639 kpw.local_label = fn->local_label; 640 kpw.remote_label = fnh->remote_label; 641 kpw.flags = pw->flags; 642 643 lde_imsg_compose_parent(IMSG_KPWLABEL_CHANGE, 0, &kpw, 644 sizeof(kpw)); 645 break; 646 } 647 } 648 649 void 650 lde_send_delete_klabel(struct fec_node *fn, struct fec_nh *fnh) 651 { 652 struct kroute kr; 653 struct kpw kpw; 654 struct l2vpn_pw *pw; 655 656 switch (fn->fec.type) { 657 case FEC_TYPE_IPV4: 658 memset(&kr, 0, sizeof(kr)); 659 kr.af = AF_INET; 660 kr.prefix.v4 = fn->fec.u.ipv4.prefix; 661 kr.prefixlen = fn->fec.u.ipv4.prefixlen; 662 kr.nexthop.v4 = fnh->nexthop.v4; 663 kr.local_label = fn->local_label; 664 kr.remote_label = fnh->remote_label; 665 kr.priority = fnh->priority; 666 667 lde_imsg_compose_parent(IMSG_KLABEL_DELETE, 0, &kr, 668 sizeof(kr)); 669 670 if (fn->fec.u.ipv4.prefixlen == 32) 671 l2vpn_sync_pws(AF_INET, (union ldpd_addr *) 672 &fn->fec.u.ipv4.prefix); 673 break; 674 case FEC_TYPE_IPV6: 675 memset(&kr, 0, sizeof(kr)); 676 kr.af = AF_INET6; 677 kr.prefix.v6 = fn->fec.u.ipv6.prefix; 678 kr.prefixlen = fn->fec.u.ipv6.prefixlen; 679 kr.nexthop.v6 = fnh->nexthop.v6; 680 kr.local_label = fn->local_label; 681 kr.remote_label = fnh->remote_label; 682 kr.priority = fnh->priority; 683 684 lde_imsg_compose_parent(IMSG_KLABEL_DELETE, 0, &kr, 685 sizeof(kr)); 686 687 if (fn->fec.u.ipv6.prefixlen == 128) 688 l2vpn_sync_pws(AF_INET6, (union ldpd_addr *) 689 &fn->fec.u.ipv6.prefix); 690 break; 691 case FEC_TYPE_PWID: 692 pw = (struct l2vpn_pw *) fn->data; 693 if (!(pw->flags & F_PW_STATUS_UP)) 694 return; 695 pw->flags &= ~F_PW_STATUS_UP; 696 697 memset(&kpw, 0, sizeof(kpw)); 698 kpw.ifindex = pw->ifindex; 699 kpw.pw_type = fn->fec.u.pwid.type; 700 kpw.af = pw->af; 701 kpw.nexthop = pw->addr; 702 kpw.local_label = fn->local_label; 703 kpw.remote_label = fnh->remote_label; 704 kpw.flags = pw->flags; 705 706 lde_imsg_compose_parent(IMSG_KPWLABEL_DELETE, 0, &kpw, 707 sizeof(kpw)); 708 break; 709 } 710 } 711 712 void 713 lde_fec2map(struct fec *fec, struct map *map) 714 { 715 memset(map, 0, sizeof(*map)); 716 717 switch (fec->type) { 718 case FEC_TYPE_IPV4: 719 map->type = MAP_TYPE_PREFIX; 720 map->fec.prefix.af = AF_INET; 721 map->fec.prefix.prefix.v4 = fec->u.ipv4.prefix; 722 map->fec.prefix.prefixlen = fec->u.ipv4.prefixlen; 723 break; 724 case FEC_TYPE_IPV6: 725 map->type = MAP_TYPE_PREFIX; 726 map->fec.prefix.af = AF_INET6; 727 map->fec.prefix.prefix.v6 = fec->u.ipv6.prefix; 728 map->fec.prefix.prefixlen = fec->u.ipv6.prefixlen; 729 break; 730 case FEC_TYPE_PWID: 731 map->type = MAP_TYPE_PWID; 732 map->fec.pwid.type = fec->u.pwid.type; 733 map->fec.pwid.group_id = 0; 734 map->flags |= F_MAP_PW_ID; 735 map->fec.pwid.pwid = fec->u.pwid.pwid; 736 break; 737 } 738 } 739 740 void 741 lde_map2fec(struct map *map, struct in_addr lsr_id, struct fec *fec) 742 { 743 memset(fec, 0, sizeof(*fec)); 744 745 switch (map->type) { 746 case MAP_TYPE_PREFIX: 747 switch (map->fec.prefix.af) { 748 case AF_INET: 749 fec->type = FEC_TYPE_IPV4; 750 fec->u.ipv4.prefix = map->fec.prefix.prefix.v4; 751 fec->u.ipv4.prefixlen = map->fec.prefix.prefixlen; 752 break; 753 case AF_INET6: 754 fec->type = FEC_TYPE_IPV6; 755 fec->u.ipv6.prefix = map->fec.prefix.prefix.v6; 756 fec->u.ipv6.prefixlen = map->fec.prefix.prefixlen; 757 break; 758 default: 759 fatalx("lde_map2fec: unknown af"); 760 break; 761 } 762 break; 763 case MAP_TYPE_PWID: 764 fec->type = FEC_TYPE_PWID; 765 fec->u.pwid.type = map->fec.pwid.type; 766 fec->u.pwid.pwid = map->fec.pwid.pwid; 767 fec->u.pwid.lsr_id = lsr_id; 768 break; 769 } 770 } 771 772 void 773 lde_send_labelmapping(struct lde_nbr *ln, struct fec_node *fn, int single) 774 { 775 struct lde_req *lre; 776 struct lde_map *me; 777 struct map map; 778 struct l2vpn_pw *pw; 779 780 /* 781 * This function skips SL.1 - 3 and SL.9 - 14 because the label 782 * allocation is done way earlier (because of the merging nature of 783 * ldpd). 784 */ 785 786 lde_fec2map(&fn->fec, &map); 787 switch (fn->fec.type) { 788 case FEC_TYPE_IPV4: 789 if (!ln->v4_enabled) 790 return; 791 break; 792 case FEC_TYPE_IPV6: 793 if (!ln->v6_enabled) 794 return; 795 break; 796 case FEC_TYPE_PWID: 797 pw = (struct l2vpn_pw *) fn->data; 798 if (pw == NULL || pw->lsr_id.s_addr != ln->id.s_addr) 799 /* not the remote end of the pseudowire */ 800 return; 801 802 map.flags |= F_MAP_PW_IFMTU; 803 map.fec.pwid.ifmtu = pw->l2vpn->mtu; 804 if (pw->flags & F_PW_CWORD) 805 map.flags |= F_MAP_PW_CWORD; 806 if (pw->flags & F_PW_STATUSTLV) { 807 map.flags |= F_MAP_PW_STATUS; 808 /* VPLS are always up */ 809 map.pw_status = PW_FORWARDING; 810 } 811 break; 812 } 813 map.label = fn->local_label; 814 815 /* SL.6: is there a pending request for this mapping? */ 816 lre = (struct lde_req *)fec_find(&ln->recv_req, &fn->fec); 817 if (lre) { 818 /* set label request msg id in the mapping response. */ 819 map.requestid = lre->msg_id; 820 map.flags = F_MAP_REQ_ID; 821 822 /* SL.7: delete record of pending request */ 823 lde_req_del(ln, lre, 0); 824 } 825 826 /* SL.4: send label mapping */ 827 lde_imsg_compose_ldpe(IMSG_MAPPING_ADD, ln->peerid, 0, 828 &map, sizeof(map)); 829 if (single) 830 lde_imsg_compose_ldpe(IMSG_MAPPING_ADD_END, ln->peerid, 0, 831 NULL, 0); 832 833 /* SL.5: record sent label mapping */ 834 me = (struct lde_map *)fec_find(&ln->sent_map, &fn->fec); 835 if (me == NULL) 836 me = lde_map_add(ln, fn, 1); 837 me->map = map; 838 } 839 840 void 841 lde_send_labelwithdraw(struct lde_nbr *ln, struct fec_node *fn, 842 struct map *wcard, struct status_tlv *st) 843 { 844 struct lde_wdraw *lw; 845 struct map map; 846 struct fec *f; 847 struct l2vpn_pw *pw; 848 849 if (fn) { 850 lde_fec2map(&fn->fec, &map); 851 switch (fn->fec.type) { 852 case FEC_TYPE_IPV4: 853 if (!ln->v4_enabled) 854 return; 855 break; 856 case FEC_TYPE_IPV6: 857 if (!ln->v6_enabled) 858 return; 859 break; 860 case FEC_TYPE_PWID: 861 pw = (struct l2vpn_pw *) fn->data; 862 if (pw == NULL || pw->lsr_id.s_addr != ln->id.s_addr) 863 /* not the remote end of the pseudowire */ 864 return; 865 866 if (pw->flags & F_PW_CWORD) 867 map.flags |= F_MAP_PW_CWORD; 868 break; 869 } 870 map.label = fn->local_label; 871 } else 872 memcpy(&map, wcard, sizeof(map)); 873 874 if (st) { 875 map.st.status_code = st->status_code; 876 map.st.msg_id = st->msg_id; 877 map.st.msg_type = st->msg_type; 878 map.flags |= F_MAP_STATUS; 879 } 880 881 /* SWd.1: send label withdraw. */ 882 lde_imsg_compose_ldpe(IMSG_WITHDRAW_ADD, ln->peerid, 0, 883 &map, sizeof(map)); 884 lde_imsg_compose_ldpe(IMSG_WITHDRAW_ADD_END, ln->peerid, 0, NULL, 0); 885 886 /* SWd.2: record label withdraw. */ 887 if (fn) { 888 lw = (struct lde_wdraw *)fec_find(&ln->sent_wdraw, &fn->fec); 889 if (lw == NULL) 890 lw = lde_wdraw_add(ln, fn); 891 lw->label = map.label; 892 } else { 893 struct lde_map *me; 894 895 RB_FOREACH(f, fec_tree, &ft) { 896 fn = (struct fec_node *)f; 897 me = (struct lde_map *)fec_find(&ln->sent_map, &fn->fec); 898 if (lde_wildcard_apply(wcard, &fn->fec, me) == 0) 899 continue; 900 901 lw = (struct lde_wdraw *)fec_find(&ln->sent_wdraw, 902 &fn->fec); 903 if (lw == NULL) 904 lw = lde_wdraw_add(ln, fn); 905 lw->label = map.label; 906 } 907 } 908 } 909 910 void 911 lde_send_labelwithdraw_wcard(struct lde_nbr *ln, uint32_t label) 912 { 913 struct map wcard; 914 915 memset(&wcard, 0, sizeof(wcard)); 916 wcard.type = MAP_TYPE_WILDCARD; 917 wcard.label = label; 918 lde_send_labelwithdraw(ln, NULL, &wcard, NULL); 919 } 920 921 void 922 lde_send_labelwithdraw_twcard_prefix(struct lde_nbr *ln, uint16_t af, 923 uint32_t label) 924 { 925 struct map wcard; 926 927 memset(&wcard, 0, sizeof(wcard)); 928 wcard.type = MAP_TYPE_TYPED_WCARD; 929 wcard.fec.twcard.type = MAP_TYPE_PREFIX; 930 wcard.fec.twcard.u.prefix_af = af; 931 wcard.label = label; 932 lde_send_labelwithdraw(ln, NULL, &wcard, NULL); 933 } 934 935 void 936 lde_send_labelwithdraw_twcard_pwid(struct lde_nbr *ln, uint16_t pw_type, 937 uint32_t label) 938 { 939 struct map wcard; 940 941 memset(&wcard, 0, sizeof(wcard)); 942 wcard.type = MAP_TYPE_TYPED_WCARD; 943 wcard.fec.twcard.type = MAP_TYPE_PWID; 944 wcard.fec.twcard.u.pw_type = pw_type; 945 wcard.label = label; 946 lde_send_labelwithdraw(ln, NULL, &wcard, NULL); 947 } 948 949 void 950 lde_send_labelwithdraw_pwid_wcard(struct lde_nbr *ln, uint16_t pw_type, 951 uint32_t group_id) 952 { 953 struct map wcard; 954 955 memset(&wcard, 0, sizeof(wcard)); 956 wcard.type = MAP_TYPE_PWID; 957 wcard.fec.pwid.type = pw_type; 958 wcard.fec.pwid.group_id = group_id; 959 /* we can not append a Label TLV when using PWid group wildcards. */ 960 wcard.label = NO_LABEL; 961 lde_send_labelwithdraw(ln, NULL, &wcard, NULL); 962 } 963 964 void 965 lde_send_labelrelease(struct lde_nbr *ln, struct fec_node *fn, 966 struct map *wcard, uint32_t label) 967 { 968 struct map map; 969 struct l2vpn_pw *pw; 970 971 if (fn) { 972 lde_fec2map(&fn->fec, &map); 973 switch (fn->fec.type) { 974 case FEC_TYPE_IPV4: 975 if (!ln->v4_enabled) 976 return; 977 break; 978 case FEC_TYPE_IPV6: 979 if (!ln->v6_enabled) 980 return; 981 break; 982 case FEC_TYPE_PWID: 983 pw = (struct l2vpn_pw *) fn->data; 984 if (pw == NULL || pw->lsr_id.s_addr != ln->id.s_addr) 985 /* not the remote end of the pseudowire */ 986 return; 987 988 if (pw->flags & F_PW_CWORD) 989 map.flags |= F_MAP_PW_CWORD; 990 break; 991 } 992 } else 993 memcpy(&map, wcard, sizeof(map)); 994 map.label = label; 995 996 lde_imsg_compose_ldpe(IMSG_RELEASE_ADD, ln->peerid, 0, 997 &map, sizeof(map)); 998 lde_imsg_compose_ldpe(IMSG_RELEASE_ADD_END, ln->peerid, 0, NULL, 0); 999 } 1000 1001 void 1002 lde_send_notification(struct lde_nbr *ln, uint32_t status_code, uint32_t msg_id, 1003 uint16_t msg_type) 1004 { 1005 struct notify_msg nm; 1006 1007 memset(&nm, 0, sizeof(nm)); 1008 nm.status_code = status_code; 1009 /* 'msg_id' and 'msg_type' should be in network byte order */ 1010 nm.msg_id = msg_id; 1011 nm.msg_type = msg_type; 1012 1013 lde_imsg_compose_ldpe(IMSG_NOTIFICATION_SEND, ln->peerid, 0, 1014 &nm, sizeof(nm)); 1015 } 1016 1017 void 1018 lde_send_notification_eol_prefix(struct lde_nbr *ln, int af) 1019 { 1020 struct notify_msg nm; 1021 1022 memset(&nm, 0, sizeof(nm)); 1023 nm.status_code = S_ENDOFLIB; 1024 nm.fec.type = MAP_TYPE_TYPED_WCARD; 1025 nm.fec.fec.twcard.type = MAP_TYPE_PREFIX; 1026 nm.fec.fec.twcard.u.prefix_af = af; 1027 nm.flags |= F_NOTIF_FEC; 1028 1029 lde_imsg_compose_ldpe(IMSG_NOTIFICATION_SEND, ln->peerid, 0, 1030 &nm, sizeof(nm)); 1031 } 1032 1033 void 1034 lde_send_notification_eol_pwid(struct lde_nbr *ln, uint16_t pw_type) 1035 { 1036 struct notify_msg nm; 1037 1038 memset(&nm, 0, sizeof(nm)); 1039 nm.status_code = S_ENDOFLIB; 1040 nm.fec.type = MAP_TYPE_TYPED_WCARD; 1041 nm.fec.fec.twcard.type = MAP_TYPE_PWID; 1042 nm.fec.fec.twcard.u.pw_type = pw_type; 1043 nm.flags |= F_NOTIF_FEC; 1044 1045 lde_imsg_compose_ldpe(IMSG_NOTIFICATION_SEND, ln->peerid, 0, 1046 &nm, sizeof(nm)); 1047 } 1048 1049 static __inline int 1050 lde_nbr_compare(struct lde_nbr *a, struct lde_nbr *b) 1051 { 1052 return (a->peerid - b->peerid); 1053 } 1054 1055 static struct lde_nbr * 1056 lde_nbr_new(uint32_t peerid, struct lde_nbr *new) 1057 { 1058 struct lde_nbr *ln; 1059 1060 if ((ln = calloc(1, sizeof(*ln))) == NULL) 1061 fatal(__func__); 1062 1063 ln->id = new->id; 1064 ln->v4_enabled = new->v4_enabled; 1065 ln->v6_enabled = new->v6_enabled; 1066 ln->flags = new->flags; 1067 ln->peerid = peerid; 1068 fec_init(&ln->recv_map); 1069 fec_init(&ln->sent_map); 1070 fec_init(&ln->recv_req); 1071 fec_init(&ln->sent_req); 1072 fec_init(&ln->sent_wdraw); 1073 1074 TAILQ_INIT(&ln->addr_list); 1075 1076 if (RB_INSERT(nbr_tree, &lde_nbrs, ln) != NULL) 1077 fatalx("lde_nbr_new: RB_INSERT failed"); 1078 1079 return (ln); 1080 } 1081 1082 static void 1083 lde_nbr_del(struct lde_nbr *ln) 1084 { 1085 struct fec *f; 1086 struct fec_node *fn; 1087 struct fec_nh *fnh; 1088 struct l2vpn_pw *pw; 1089 1090 if (ln == NULL) 1091 return; 1092 1093 /* uninstall received mappings */ 1094 RB_FOREACH(f, fec_tree, &ft) { 1095 fn = (struct fec_node *)f; 1096 1097 LIST_FOREACH(fnh, &fn->nexthops, entry) { 1098 switch (f->type) { 1099 case FEC_TYPE_IPV4: 1100 case FEC_TYPE_IPV6: 1101 if (!lde_address_find(ln, fnh->af, 1102 &fnh->nexthop)) 1103 continue; 1104 break; 1105 case FEC_TYPE_PWID: 1106 if (f->u.pwid.lsr_id.s_addr != ln->id.s_addr) 1107 continue; 1108 pw = (struct l2vpn_pw *) fn->data; 1109 if (pw) 1110 l2vpn_pw_reset(pw); 1111 break; 1112 default: 1113 break; 1114 } 1115 1116 lde_send_delete_klabel(fn, fnh); 1117 fnh->remote_label = NO_LABEL; 1118 } 1119 } 1120 1121 lde_address_list_free(ln); 1122 1123 fec_clear(&ln->recv_map, lde_map_free); 1124 fec_clear(&ln->sent_map, lde_map_free); 1125 fec_clear(&ln->recv_req, free); 1126 fec_clear(&ln->sent_req, free); 1127 fec_clear(&ln->sent_wdraw, free); 1128 1129 RB_REMOVE(nbr_tree, &lde_nbrs, ln); 1130 1131 free(ln); 1132 } 1133 1134 static struct lde_nbr * 1135 lde_nbr_find(uint32_t peerid) 1136 { 1137 struct lde_nbr ln; 1138 1139 ln.peerid = peerid; 1140 1141 return (RB_FIND(nbr_tree, &lde_nbrs, &ln)); 1142 } 1143 1144 struct lde_nbr * 1145 lde_nbr_find_by_lsrid(struct in_addr addr) 1146 { 1147 struct lde_nbr *ln; 1148 1149 RB_FOREACH(ln, nbr_tree, &lde_nbrs) 1150 if (ln->id.s_addr == addr.s_addr) 1151 return (ln); 1152 1153 return (NULL); 1154 } 1155 1156 struct lde_nbr * 1157 lde_nbr_find_by_addr(int af, union ldpd_addr *addr) 1158 { 1159 struct lde_nbr *ln; 1160 1161 RB_FOREACH(ln, nbr_tree, &lde_nbrs) 1162 if (lde_address_find(ln, af, addr) != NULL) 1163 return (ln); 1164 1165 return (NULL); 1166 } 1167 1168 static void 1169 lde_nbr_clear(void) 1170 { 1171 struct lde_nbr *ln; 1172 1173 while ((ln = RB_ROOT(&lde_nbrs)) != NULL) 1174 lde_nbr_del(ln); 1175 } 1176 1177 static void 1178 lde_nbr_addr_update(struct lde_nbr *ln, struct lde_addr *lde_addr, int removed) 1179 { 1180 struct fec *fec; 1181 struct fec_node *fn; 1182 struct fec_nh *fnh; 1183 struct lde_map *me; 1184 1185 RB_FOREACH(fec, fec_tree, &ln->recv_map) { 1186 fn = (struct fec_node *)fec_find(&ft, fec); 1187 switch (fec->type) { 1188 case FEC_TYPE_IPV4: 1189 if (lde_addr->af != AF_INET) 1190 continue; 1191 break; 1192 case FEC_TYPE_IPV6: 1193 if (lde_addr->af != AF_INET6) 1194 continue; 1195 break; 1196 default: 1197 continue; 1198 } 1199 1200 LIST_FOREACH(fnh, &fn->nexthops, entry) { 1201 if (ldp_addrcmp(fnh->af, &fnh->nexthop, 1202 &lde_addr->addr)) 1203 continue; 1204 1205 if (removed) { 1206 lde_send_delete_klabel(fn, fnh); 1207 fnh->remote_label = NO_LABEL; 1208 } else { 1209 me = (struct lde_map *)fec; 1210 fnh->remote_label = me->map.label; 1211 lde_send_change_klabel(fn, fnh); 1212 } 1213 break; 1214 } 1215 } 1216 } 1217 1218 struct lde_map * 1219 lde_map_add(struct lde_nbr *ln, struct fec_node *fn, int sent) 1220 { 1221 struct lde_map *me; 1222 1223 me = calloc(1, sizeof(*me)); 1224 if (me == NULL) 1225 fatal(__func__); 1226 1227 me->fec = fn->fec; 1228 me->nexthop = ln; 1229 1230 if (sent) { 1231 LIST_INSERT_HEAD(&fn->upstream, me, entry); 1232 if (fec_insert(&ln->sent_map, &me->fec)) 1233 log_warnx("failed to add %s to sent map", 1234 log_fec(&me->fec)); 1235 /* XXX on failure more cleanup is needed */ 1236 } else { 1237 LIST_INSERT_HEAD(&fn->downstream, me, entry); 1238 if (fec_insert(&ln->recv_map, &me->fec)) 1239 log_warnx("failed to add %s to recv map", 1240 log_fec(&me->fec)); 1241 } 1242 1243 return (me); 1244 } 1245 1246 void 1247 lde_map_del(struct lde_nbr *ln, struct lde_map *me, int sent) 1248 { 1249 if (sent) 1250 fec_remove(&ln->sent_map, &me->fec); 1251 else 1252 fec_remove(&ln->recv_map, &me->fec); 1253 1254 lde_map_free(me); 1255 } 1256 1257 static void 1258 lde_map_free(void *ptr) 1259 { 1260 struct lde_map *map = ptr; 1261 1262 LIST_REMOVE(map, entry); 1263 free(map); 1264 } 1265 1266 struct lde_req * 1267 lde_req_add(struct lde_nbr *ln, struct fec *fec, int sent) 1268 { 1269 struct fec_tree *t; 1270 struct lde_req *lre; 1271 1272 t = sent ? &ln->sent_req : &ln->recv_req; 1273 1274 lre = calloc(1, sizeof(*lre)); 1275 if (lre != NULL) { 1276 lre->fec = *fec; 1277 1278 if (fec_insert(t, &lre->fec)) { 1279 log_warnx("failed to add %s to %s req", 1280 log_fec(&lre->fec), sent ? "sent" : "recv"); 1281 free(lre); 1282 return (NULL); 1283 } 1284 } 1285 1286 return (lre); 1287 } 1288 1289 void 1290 lde_req_del(struct lde_nbr *ln, struct lde_req *lre, int sent) 1291 { 1292 if (sent) 1293 fec_remove(&ln->sent_req, &lre->fec); 1294 else 1295 fec_remove(&ln->recv_req, &lre->fec); 1296 1297 free(lre); 1298 } 1299 1300 struct lde_wdraw * 1301 lde_wdraw_add(struct lde_nbr *ln, struct fec_node *fn) 1302 { 1303 struct lde_wdraw *lw; 1304 1305 lw = calloc(1, sizeof(*lw)); 1306 if (lw == NULL) 1307 fatal(__func__); 1308 1309 lw->fec = fn->fec; 1310 1311 if (fec_insert(&ln->sent_wdraw, &lw->fec)) 1312 log_warnx("failed to add %s to sent wdraw", 1313 log_fec(&lw->fec)); 1314 1315 return (lw); 1316 } 1317 1318 void 1319 lde_wdraw_del(struct lde_nbr *ln, struct lde_wdraw *lw) 1320 { 1321 fec_remove(&ln->sent_wdraw, &lw->fec); 1322 free(lw); 1323 } 1324 1325 void 1326 lde_change_egress_label(int af, int was_implicit) 1327 { 1328 struct lde_nbr *ln; 1329 struct fec *f; 1330 struct fec_node *fn; 1331 1332 RB_FOREACH(ln, nbr_tree, &lde_nbrs) { 1333 /* explicit withdraw */ 1334 if (was_implicit) 1335 lde_send_labelwithdraw_wcard(ln, MPLS_LABEL_IMPLNULL); 1336 else { 1337 if (ln->v4_enabled) 1338 lde_send_labelwithdraw_wcard(ln, 1339 MPLS_LABEL_IPV4NULL); 1340 if (ln->v6_enabled) 1341 lde_send_labelwithdraw_wcard(ln, 1342 MPLS_LABEL_IPV6NULL); 1343 } 1344 1345 /* advertise new label of connected prefixes */ 1346 RB_FOREACH(f, fec_tree, &ft) { 1347 fn = (struct fec_node *)f; 1348 if (fn->local_label > MPLS_LABEL_RESERVED_MAX) 1349 continue; 1350 1351 switch (af) { 1352 case AF_INET: 1353 if (fn->fec.type != FEC_TYPE_IPV4) 1354 continue; 1355 break; 1356 case AF_INET6: 1357 if (fn->fec.type != FEC_TYPE_IPV6) 1358 continue; 1359 break; 1360 default: 1361 fatalx("lde_change_egress_label: unknown af"); 1362 } 1363 1364 fn->local_label = egress_label(fn->fec.type); 1365 lde_send_labelmapping(ln, fn, 0); 1366 } 1367 1368 lde_imsg_compose_ldpe(IMSG_MAPPING_ADD_END, ln->peerid, 0, 1369 NULL, 0); 1370 } 1371 } 1372 1373 static int 1374 lde_address_add(struct lde_nbr *ln, struct lde_addr *lde_addr) 1375 { 1376 struct lde_addr *new; 1377 1378 if (lde_address_find(ln, lde_addr->af, &lde_addr->addr) != NULL) 1379 return (-1); 1380 1381 if ((new = calloc(1, sizeof(*new))) == NULL) 1382 fatal(__func__); 1383 1384 new->af = lde_addr->af; 1385 new->addr = lde_addr->addr; 1386 TAILQ_INSERT_TAIL(&ln->addr_list, new, entry); 1387 1388 /* reevaluate the previously received mappings from this neighbor */ 1389 lde_nbr_addr_update(ln, lde_addr, 0); 1390 1391 return (0); 1392 } 1393 1394 static int 1395 lde_address_del(struct lde_nbr *ln, struct lde_addr *lde_addr) 1396 { 1397 lde_addr = lde_address_find(ln, lde_addr->af, &lde_addr->addr); 1398 if (lde_addr == NULL) 1399 return (-1); 1400 1401 /* reevaluate the previously received mappings from this neighbor */ 1402 lde_nbr_addr_update(ln, lde_addr, 1); 1403 1404 TAILQ_REMOVE(&ln->addr_list, lde_addr, entry); 1405 free(lde_addr); 1406 1407 return (0); 1408 } 1409 1410 struct lde_addr * 1411 lde_address_find(struct lde_nbr *ln, int af, union ldpd_addr *addr) 1412 { 1413 struct lde_addr *lde_addr; 1414 1415 TAILQ_FOREACH(lde_addr, &ln->addr_list, entry) 1416 if (lde_addr->af == af && 1417 ldp_addrcmp(af, &lde_addr->addr, addr) == 0) 1418 return (lde_addr); 1419 1420 return (NULL); 1421 } 1422 1423 static void 1424 lde_address_list_free(struct lde_nbr *ln) 1425 { 1426 struct lde_addr *lde_addr; 1427 1428 while ((lde_addr = TAILQ_FIRST(&ln->addr_list)) != NULL) { 1429 TAILQ_REMOVE(&ln->addr_list, lde_addr, entry); 1430 free(lde_addr); 1431 } 1432 } 1433