1 /* $OpenBSD: ldpe.c,v 1.24 2014/07/12 20:16:38 krw Exp $ */ 2 3 /* 4 * Copyright (c) 2005 Claudio Jeker <claudio@openbsd.org> 5 * Copyright (c) 2004, 2008 Esben Norby <norby@openbsd.org> 6 * Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org> 7 * 8 * Permission to use, copy, modify, and distribute this software for any 9 * purpose with or without fee is hereby granted, provided that the above 10 * copyright notice and this permission notice appear in all copies. 11 * 12 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 13 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 14 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 15 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 16 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 17 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 18 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 19 */ 20 21 #include <sys/types.h> 22 #include <sys/socket.h> 23 #include <sys/queue.h> 24 #include <netinet/in.h> 25 #include <arpa/inet.h> 26 #include <net/if_types.h> 27 #include <stdlib.h> 28 #include <signal.h> 29 #include <string.h> 30 #include <fcntl.h> 31 #include <pwd.h> 32 #include <unistd.h> 33 #include <event.h> 34 #include <err.h> 35 #include <errno.h> 36 #include <stdio.h> 37 #include <stdlib.h> 38 39 #include "ldp.h" 40 #include "ldpd.h" 41 #include "ldpe.h" 42 #include "lde.h" 43 #include "control.h" 44 #include "log.h" 45 46 extern struct nbr_id_head nbrs_by_id; 47 RB_PROTOTYPE(nbr_id_head, nbr, id_tree, nbr_id_compare) 48 49 void ldpe_sig_handler(int, short, void *); 50 void ldpe_shutdown(void); 51 52 struct ldpd_conf *leconf = NULL, *nconf; 53 struct imsgev *iev_main; 54 struct imsgev *iev_lde; 55 56 /* ARGSUSED */ 57 void 58 ldpe_sig_handler(int sig, short event, void *bula) 59 { 60 switch (sig) { 61 case SIGINT: 62 case SIGTERM: 63 ldpe_shutdown(); 64 /* NOTREACHED */ 65 default: 66 fatalx("unexpected signal"); 67 } 68 } 69 70 /* label distribution protocol engine */ 71 pid_t 72 ldpe(struct ldpd_conf *xconf, int pipe_parent2ldpe[2], int pipe_ldpe2lde[2], 73 int pipe_parent2lde[2]) 74 { 75 struct iface *iface; 76 struct tnbr *tnbr; 77 struct passwd *pw; 78 struct event ev_sigint, ev_sigterm; 79 struct sockaddr_in disc_addr, sess_addr; 80 pid_t pid; 81 82 switch (pid = fork()) { 83 case -1: 84 fatal("cannot fork"); 85 case 0: 86 break; 87 default: 88 return (pid); 89 } 90 91 leconf = xconf; 92 93 setproctitle("ldp engine"); 94 ldpd_process = PROC_LDP_ENGINE; 95 96 /* create ldpd control socket outside chroot */ 97 if (control_init() == -1) 98 fatalx("control socket setup failed"); 99 100 /* create the discovery UDP socket */ 101 disc_addr.sin_family = AF_INET; 102 disc_addr.sin_port = htons(LDP_PORT); 103 disc_addr.sin_addr.s_addr = INADDR_ANY; 104 105 if ((xconf->ldp_discovery_socket = socket(AF_INET, SOCK_DGRAM, 106 IPPROTO_UDP)) == -1) 107 fatal("error creating discovery socket"); 108 109 if (if_set_reuse(xconf->ldp_discovery_socket, 1) == -1) 110 fatal("if_set_reuse"); 111 112 if (bind(xconf->ldp_discovery_socket, (struct sockaddr *)&disc_addr, 113 sizeof(disc_addr)) == -1) 114 fatal("error binding discovery socket"); 115 116 /* set some defaults */ 117 if (if_set_mcast_ttl(xconf->ldp_discovery_socket, 118 IP_DEFAULT_MULTICAST_TTL) == -1) 119 fatal("if_set_mcast_ttl"); 120 if (if_set_mcast_loop(xconf->ldp_discovery_socket) == -1) 121 fatal("if_set_mcast_loop"); 122 if (if_set_tos(xconf->ldp_discovery_socket, 123 IPTOS_PREC_INTERNETCONTROL) == -1) 124 fatal("if_set_tos"); 125 if (if_set_recvif(xconf->ldp_discovery_socket, 1) == -1) 126 fatal("if_set_recvif"); 127 if_set_recvbuf(xconf->ldp_discovery_socket); 128 129 /* create the extended discovery UDP socket */ 130 disc_addr.sin_family = AF_INET; 131 disc_addr.sin_port = htons(LDP_PORT); 132 disc_addr.sin_addr.s_addr = xconf->rtr_id.s_addr; 133 134 if ((xconf->ldp_ediscovery_socket = socket(AF_INET, SOCK_DGRAM, 135 IPPROTO_UDP)) == -1) 136 fatal("error creating extended discovery socket"); 137 138 if (if_set_reuse(xconf->ldp_ediscovery_socket, 1) == -1) 139 fatal("if_set_reuse"); 140 141 if (bind(xconf->ldp_ediscovery_socket, (struct sockaddr *)&disc_addr, 142 sizeof(disc_addr)) == -1) 143 fatal("error binding extended discovery socket"); 144 145 /* set some defaults */ 146 if (if_set_tos(xconf->ldp_ediscovery_socket, 147 IPTOS_PREC_INTERNETCONTROL) == -1) 148 fatal("if_set_tos"); 149 if (if_set_recvif(xconf->ldp_ediscovery_socket, 1) == -1) 150 fatal("if_set_recvif"); 151 if_set_recvbuf(xconf->ldp_ediscovery_socket); 152 153 /* create the session TCP socket */ 154 sess_addr.sin_family = AF_INET; 155 sess_addr.sin_port = htons(LDP_PORT); 156 sess_addr.sin_addr.s_addr = INADDR_ANY; 157 158 if ((xconf->ldp_session_socket = socket(AF_INET, SOCK_STREAM, 159 IPPROTO_TCP)) == -1) 160 fatal("error creating session socket"); 161 162 if (if_set_reuse(xconf->ldp_session_socket, 1) == -1) 163 fatal("if_set_reuse"); 164 165 if (bind(xconf->ldp_session_socket, (struct sockaddr *)&sess_addr, 166 sizeof(sess_addr)) == -1) 167 fatal("error binding session socket"); 168 169 if (listen(xconf->ldp_session_socket, LDP_BACKLOG) == -1) 170 fatal("error in listen on session socket"); 171 172 /* set some defaults */ 173 if (if_set_tos(xconf->ldp_session_socket, 174 IPTOS_PREC_INTERNETCONTROL) == -1) 175 fatal("if_set_tos"); 176 session_socket_blockmode(xconf->ldp_session_socket, BM_NONBLOCK); 177 178 if ((pw = getpwnam(LDPD_USER)) == NULL) 179 fatal("getpwnam"); 180 181 if (chroot(pw->pw_dir) == -1) 182 fatal("chroot"); 183 if (chdir("/") == -1) 184 fatal("chdir(\"/\")"); 185 186 if (setgroups(1, &pw->pw_gid) || 187 setresgid(pw->pw_gid, pw->pw_gid, pw->pw_gid) || 188 setresuid(pw->pw_uid, pw->pw_uid, pw->pw_uid)) 189 fatal("can't drop privileges"); 190 191 event_init(); 192 accept_init(); 193 194 /* setup signal handler */ 195 signal_set(&ev_sigint, SIGINT, ldpe_sig_handler, NULL); 196 signal_set(&ev_sigterm, SIGTERM, ldpe_sig_handler, NULL); 197 signal_add(&ev_sigint, NULL); 198 signal_add(&ev_sigterm, NULL); 199 signal(SIGPIPE, SIG_IGN); 200 signal(SIGHUP, SIG_IGN); 201 202 /* setup pipes */ 203 close(pipe_parent2ldpe[0]); 204 close(pipe_ldpe2lde[1]); 205 close(pipe_parent2lde[0]); 206 close(pipe_parent2lde[1]); 207 208 if ((iev_lde = malloc(sizeof(struct imsgev))) == NULL || 209 (iev_main = malloc(sizeof(struct imsgev))) == NULL) 210 fatal(NULL); 211 imsg_init(&iev_lde->ibuf, pipe_ldpe2lde[0]); 212 iev_lde->handler = ldpe_dispatch_lde; 213 imsg_init(&iev_main->ibuf, pipe_parent2ldpe[1]); 214 iev_main->handler = ldpe_dispatch_main; 215 216 /* setup event handler */ 217 iev_lde->events = EV_READ; 218 event_set(&iev_lde->ev, iev_lde->ibuf.fd, iev_lde->events, 219 iev_lde->handler, iev_lde); 220 event_add(&iev_lde->ev, NULL); 221 222 iev_main->events = EV_READ; 223 event_set(&iev_main->ev, iev_main->ibuf.fd, iev_main->events, 224 iev_main->handler, iev_main); 225 event_add(&iev_main->ev, NULL); 226 227 event_set(&leconf->disc_ev, leconf->ldp_discovery_socket, 228 EV_READ|EV_PERSIST, disc_recv_packet, NULL); 229 event_add(&leconf->disc_ev, NULL); 230 231 event_set(&leconf->edisc_ev, leconf->ldp_ediscovery_socket, 232 EV_READ|EV_PERSIST, disc_recv_packet, NULL); 233 event_add(&leconf->edisc_ev, NULL); 234 235 accept_add(leconf->ldp_session_socket, session_accept, NULL); 236 /* listen on ldpd control socket */ 237 TAILQ_INIT(&ctl_conns); 238 control_listen(); 239 240 if ((pkt_ptr = calloc(1, IBUF_READ_SIZE)) == NULL) 241 fatal("ldpe"); 242 243 /* initialize interfaces */ 244 LIST_FOREACH(iface, &leconf->iface_list, entry) 245 if_init(xconf, iface); 246 247 /* start configured targeted neighbors */ 248 LIST_FOREACH(tnbr, &leconf->tnbr_list, entry) 249 tnbr_init(xconf, tnbr); 250 251 event_dispatch(); 252 253 ldpe_shutdown(); 254 /* NOTREACHED */ 255 return (0); 256 } 257 258 void 259 ldpe_shutdown(void) 260 { 261 struct iface *iface; 262 struct tnbr *tnbr; 263 264 /* stop all interfaces */ 265 while ((iface = LIST_FIRST(&leconf->iface_list)) != NULL) { 266 if (if_fsm(iface, IF_EVT_DOWN)) { 267 log_debug("error stopping interface %s", 268 iface->name); 269 } 270 LIST_REMOVE(iface, entry); 271 if_del(iface); 272 } 273 274 /* stop all targeted neighbors */ 275 while ((tnbr = LIST_FIRST(&leconf->tnbr_list)) != NULL) { 276 LIST_REMOVE(tnbr, entry); 277 tnbr_del(tnbr); 278 } 279 280 close(leconf->ldp_discovery_socket); 281 close(leconf->ldp_session_socket); 282 283 /* clean up */ 284 msgbuf_write(&iev_lde->ibuf.w); 285 msgbuf_clear(&iev_lde->ibuf.w); 286 free(iev_lde); 287 msgbuf_write(&iev_main->ibuf.w); 288 msgbuf_clear(&iev_main->ibuf.w); 289 free(iev_main); 290 free(leconf); 291 free(pkt_ptr); 292 293 log_info("ldp engine exiting"); 294 _exit(0); 295 } 296 297 /* imesg */ 298 int 299 ldpe_imsg_compose_parent(int type, pid_t pid, void *data, u_int16_t datalen) 300 { 301 return (imsg_compose_event(iev_main, type, 0, pid, -1, data, datalen)); 302 } 303 304 int 305 ldpe_imsg_compose_lde(int type, u_int32_t peerid, pid_t pid, 306 void *data, u_int16_t datalen) 307 { 308 return (imsg_compose_event(iev_lde, type, peerid, pid, -1, 309 data, datalen)); 310 } 311 312 /* ARGSUSED */ 313 void 314 ldpe_dispatch_main(int fd, short event, void *bula) 315 { 316 struct imsg imsg; 317 struct imsgev *iev = bula; 318 struct imsgbuf *ibuf = &iev->ibuf; 319 struct iface *iface = NULL; 320 struct if_addr *if_addr = NULL, *a; 321 struct kif *kif; 322 struct kaddr *kaddr; 323 int n, shut = 0; 324 struct nbr *nbr; 325 326 if (event & EV_READ) { 327 if ((n = imsg_read(ibuf)) == -1) 328 fatal("imsg_read error"); 329 if (n == 0) /* connection closed */ 330 shut = 1; 331 } 332 if (event & EV_WRITE) { 333 if ((n = msgbuf_write(&ibuf->w)) == -1 && errno != EAGAIN) 334 fatal("ldpe_dispatch_main: msgbuf_write"); 335 if (n == 0) 336 shut = 1; 337 } 338 339 for (;;) { 340 if ((n = imsg_get(ibuf, &imsg)) == -1) 341 fatal("ldpe_dispatch_main: imsg_read error"); 342 if (n == 0) 343 break; 344 345 switch (imsg.hdr.type) { 346 case IMSG_IFSTATUS: 347 case IMSG_IFUP: 348 case IMSG_IFDOWN: 349 if (imsg.hdr.len != IMSG_HEADER_SIZE + 350 sizeof(struct kif)) 351 fatalx("IFINFO imsg with wrong len"); 352 353 kif = imsg.data; 354 iface = if_lookup(kif->ifindex); 355 if (!iface) 356 break; 357 358 iface->flags = kif->flags; 359 iface->linkstate = kif->link_state; 360 switch (imsg.hdr.type) { 361 case IMSG_IFUP: 362 if_fsm(iface, IF_EVT_UP); 363 break; 364 case IMSG_IFDOWN: 365 if_fsm(iface, IF_EVT_DOWN); 366 break; 367 default: 368 break; 369 } 370 break; 371 case IMSG_NEWADDR: 372 if (imsg.hdr.len != IMSG_HEADER_SIZE + 373 sizeof(struct kaddr)) 374 fatalx("NEWADDR imsg with wrong len"); 375 kaddr = imsg.data; 376 377 if ((if_addr = calloc(1, sizeof(*if_addr))) == NULL) 378 fatal("ldpe_dispatch_main"); 379 380 if_addr->addr.s_addr = kaddr->addr.s_addr; 381 if_addr->mask.s_addr = kaddr->mask.s_addr; 382 if_addr->dstbrd.s_addr = kaddr->dstbrd.s_addr; 383 384 LIST_INSERT_HEAD(&leconf->addr_list, if_addr, 385 global_entry); 386 RB_FOREACH(nbr, nbr_id_head, &nbrs_by_id) { 387 if (nbr->state != NBR_STA_OPER) 388 continue; 389 send_address(nbr, if_addr); 390 } 391 392 iface = if_lookup(kaddr->ifindex); 393 if (iface) { 394 LIST_INSERT_HEAD(&iface->addr_list, if_addr, 395 iface_entry); 396 if_fsm(iface, IF_EVT_NEWADDR); 397 } 398 break; 399 case IMSG_DELADDR: 400 if (imsg.hdr.len != IMSG_HEADER_SIZE + 401 sizeof(struct kaddr)) 402 fatalx("DELADDR imsg with wrong len"); 403 kaddr = imsg.data; 404 405 LIST_FOREACH(a, &leconf->addr_list, global_entry) 406 if (a->addr.s_addr == kaddr->addr.s_addr && 407 a->mask.s_addr == kaddr->mask.s_addr && 408 a->dstbrd.s_addr == kaddr->dstbrd.s_addr) 409 break; 410 if_addr = a; 411 if (!if_addr) 412 break; 413 414 LIST_REMOVE(if_addr, global_entry); 415 RB_FOREACH(nbr, nbr_id_head, &nbrs_by_id) { 416 if (nbr->state != NBR_STA_OPER) 417 continue; 418 send_address_withdraw(nbr, if_addr); 419 } 420 421 iface = if_lookup(kaddr->ifindex); 422 if (iface) { 423 LIST_REMOVE(if_addr, iface_entry); 424 if_fsm(iface, IF_EVT_DELADDR); 425 } 426 free(if_addr); 427 break; 428 case IMSG_RECONF_CONF: 429 break; 430 case IMSG_RECONF_IFACE: 431 break; 432 case IMSG_RECONF_END: 433 break; 434 case IMSG_CTL_KROUTE: 435 case IMSG_CTL_KROUTE_ADDR: 436 case IMSG_CTL_IFINFO: 437 case IMSG_CTL_END: 438 control_imsg_relay(&imsg); 439 break; 440 default: 441 log_debug("ldpe_dispatch_main: error handling imsg %d", 442 imsg.hdr.type); 443 break; 444 } 445 imsg_free(&imsg); 446 } 447 if (!shut) 448 imsg_event_add(iev); 449 else { 450 /* this pipe is dead, so remove the event handler */ 451 event_del(&iev->ev); 452 event_loopexit(NULL); 453 } 454 } 455 456 /* ARGSUSED */ 457 void 458 ldpe_dispatch_lde(int fd, short event, void *bula) 459 { 460 struct imsgev *iev = bula; 461 struct imsgbuf *ibuf = &iev->ibuf; 462 struct imsg imsg; 463 struct map map; 464 struct notify_msg nm; 465 int n, shut = 0; 466 struct nbr *nbr = NULL; 467 468 if (event & EV_READ) { 469 if ((n = imsg_read(ibuf)) == -1) 470 fatal("imsg_read error"); 471 if (n == 0) /* connection closed */ 472 shut = 1; 473 } 474 if (event & EV_WRITE) { 475 if ((n = msgbuf_write(&ibuf->w)) == -1 && errno != EAGAIN) 476 fatal("ldpe_dispatch_lde: msgbuf_write"); 477 if (n == 0) 478 shut = 1; 479 } 480 481 for (;;) { 482 if ((n = imsg_get(ibuf, &imsg)) == -1) 483 fatal("ldpe_dispatch_lde: imsg_read error"); 484 if (n == 0) 485 break; 486 487 switch (imsg.hdr.type) { 488 case IMSG_MAPPING_ADD: 489 case IMSG_RELEASE_ADD: 490 case IMSG_REQUEST_ADD: 491 if (imsg.hdr.len - IMSG_HEADER_SIZE != sizeof(map)) 492 fatalx("invalid size of map request"); 493 memcpy(&map, imsg.data, sizeof(map)); 494 495 nbr = nbr_find_peerid(imsg.hdr.peerid); 496 if (nbr == NULL) { 497 log_debug("ldpe_dispatch_lde: cannot find " 498 "neighbor"); 499 return; 500 } 501 if (nbr->state != NBR_STA_OPER) 502 return; 503 504 switch (imsg.hdr.type) { 505 case IMSG_MAPPING_ADD: 506 nbr_mapping_add(nbr, &nbr->mapping_list, &map); 507 break; 508 case IMSG_RELEASE_ADD: 509 nbr_mapping_add(nbr, &nbr->release_list, &map); 510 break; 511 case IMSG_REQUEST_ADD: 512 nbr_mapping_add(nbr, &nbr->request_list, &map); 513 break; 514 } 515 break; 516 case IMSG_MAPPING_ADD_END: 517 case IMSG_RELEASE_ADD_END: 518 case IMSG_REQUEST_ADD_END: 519 nbr = nbr_find_peerid(imsg.hdr.peerid); 520 if (nbr == NULL) { 521 log_debug("ldpe_dispatch_lde: cannot find " 522 "neighbor"); 523 return; 524 } 525 if (nbr->state != NBR_STA_OPER) 526 return; 527 528 switch (imsg.hdr.type) { 529 case IMSG_MAPPING_ADD_END: 530 send_labelmessage(nbr, MSG_TYPE_LABELMAPPING, 531 &nbr->mapping_list); 532 break; 533 case IMSG_RELEASE_ADD_END: 534 send_labelmessage(nbr, MSG_TYPE_LABELRELEASE, 535 &nbr->release_list); 536 break; 537 case IMSG_REQUEST_ADD_END: 538 send_labelmessage(nbr, MSG_TYPE_LABELREQUEST, 539 &nbr->request_list); 540 break; 541 } 542 break; 543 case IMSG_NOTIFICATION_SEND: 544 if (imsg.hdr.len - IMSG_HEADER_SIZE != sizeof(nm)) 545 fatalx("invalid size of OE request"); 546 memcpy(&nm, imsg.data, sizeof(nm)); 547 548 nbr = nbr_find_peerid(imsg.hdr.peerid); 549 if (nbr == NULL) { 550 log_debug("ldpe_dispatch_lde: cannot find " 551 "neighbor"); 552 return; 553 } 554 if (nbr->state != NBR_STA_OPER) 555 return; 556 557 send_notification_nbr(nbr, nm.status, 558 htonl(nm.messageid), htonl(nm.type)); 559 break; 560 case IMSG_CTL_END: 561 case IMSG_CTL_SHOW_LIB: 562 control_imsg_relay(&imsg); 563 break; 564 default: 565 log_debug("ldpe_dispatch_lde: error handling imsg %d", 566 imsg.hdr.type); 567 break; 568 } 569 imsg_free(&imsg); 570 } 571 if (!shut) 572 imsg_event_add(iev); 573 else { 574 /* this pipe is dead, so remove the event handler */ 575 event_del(&iev->ev); 576 event_loopexit(NULL); 577 } 578 } 579 580 u_int32_t 581 ldpe_router_id(void) 582 { 583 return (leconf->rtr_id.s_addr); 584 } 585 586 void 587 ldpe_iface_ctl(struct ctl_conn *c, unsigned int idx) 588 { 589 struct iface *iface; 590 struct ctl_iface *ictl; 591 592 LIST_FOREACH(iface, &leconf->iface_list, entry) { 593 if (idx == 0 || idx == iface->ifindex) { 594 ictl = if_to_ctl(iface); 595 imsg_compose_event(&c->iev, 596 IMSG_CTL_SHOW_INTERFACE, 597 0, 0, -1, ictl, sizeof(struct ctl_iface)); 598 } 599 } 600 } 601