1 /* $OpenBSD: hello.c,v 1.58 2019/12/12 00:10:29 yasuoka Exp $ */ 2 3 /* 4 * Copyright (c) 2013, 2016 Renato Westphal <renato@openbsd.org> 5 * Copyright (c) 2009 Michele Marchetto <michele@openbsd.org> 6 * 7 * Permission to use, copy, modify, and distribute this software for any 8 * purpose with or without fee is hereby granted, provided that the above 9 * copyright notice and this permission notice appear in all copies. 10 * 11 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 12 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 13 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 14 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 15 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 16 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 17 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 18 */ 19 20 #include <sys/types.h> 21 #include <arpa/inet.h> 22 #include <string.h> 23 24 #include "ldpd.h" 25 #include "ldpe.h" 26 #include "log.h" 27 28 static int gen_hello_prms_tlv(struct ibuf *buf, uint16_t, uint16_t); 29 static int gen_opt4_hello_prms_tlv(struct ibuf *, uint16_t, uint32_t); 30 static int gen_opt16_hello_prms_tlv(struct ibuf *, uint16_t, uint8_t *); 31 static int gen_ds_hello_prms_tlv(struct ibuf *, uint32_t); 32 static int tlv_decode_hello_prms(char *, uint16_t, uint16_t *, uint16_t *); 33 static int tlv_decode_opt_hello_prms(char *, uint16_t, int *, int, 34 union ldpd_addr *, uint32_t *, uint16_t *); 35 36 int 37 send_hello(enum hello_type type, struct iface_af *ia, struct tnbr *tnbr) 38 { 39 int af; 40 union ldpd_addr dst; 41 uint16_t size, holdtime = 0, flags = 0; 42 int fd = 0; 43 struct ibuf *buf; 44 int err = 0; 45 46 switch (type) { 47 case HELLO_LINK: 48 af = ia->af; 49 holdtime = ia->hello_holdtime; 50 flags = 0; 51 fd = (ldp_af_global_get(&global, af))->ldp_disc_socket; 52 53 /* multicast destination address */ 54 switch (af) { 55 case AF_INET: 56 if (!(leconf->ipv4.flags & F_LDPD_AF_NO_GTSM)) 57 flags |= F_HELLO_GTSM; 58 dst.v4 = global.mcast_addr_v4; 59 break; 60 case AF_INET6: 61 dst.v6 = global.mcast_addr_v6; 62 break; 63 default: 64 fatalx("send_hello: unknown af"); 65 } 66 break; 67 case HELLO_TARGETED: 68 af = tnbr->af; 69 holdtime = tnbr->hello_holdtime; 70 flags = F_HELLO_TARGETED; 71 if ((tnbr->flags & F_TNBR_CONFIGURED) || tnbr->pw_count) 72 flags |= F_HELLO_REQ_TARG; 73 fd = (ldp_af_global_get(&global, af))->ldp_edisc_socket; 74 75 /* unicast destination address */ 76 dst = tnbr->addr; 77 break; 78 default: 79 fatalx("send_hello: unknown hello type"); 80 } 81 82 /* calculate message size */ 83 size = LDP_HDR_SIZE + LDP_MSG_SIZE + sizeof(struct hello_prms_tlv); 84 switch (af) { 85 case AF_INET: 86 size += sizeof(struct hello_prms_opt4_tlv); 87 break; 88 case AF_INET6: 89 size += sizeof(struct hello_prms_opt16_tlv); 90 break; 91 default: 92 fatalx("send_hello: unknown af"); 93 } 94 size += sizeof(struct hello_prms_opt4_tlv); 95 if (ldp_is_dual_stack(leconf)) 96 size += sizeof(struct hello_prms_opt4_tlv); 97 98 /* generate message */ 99 if ((buf = ibuf_open(size)) == NULL) 100 fatal(__func__); 101 102 err |= gen_ldp_hdr(buf, size); 103 size -= LDP_HDR_SIZE; 104 err |= gen_msg_hdr(buf, MSG_TYPE_HELLO, size); 105 err |= gen_hello_prms_tlv(buf, holdtime, flags); 106 107 /* 108 * RFC 7552 - Section 6.1: 109 * "An LSR MUST include only the transport address whose address 110 * family is the same as that of the IP packet carrying the Hello 111 * message". 112 */ 113 switch (af) { 114 case AF_INET: 115 err |= gen_opt4_hello_prms_tlv(buf, TLV_TYPE_IPV4TRANSADDR, 116 leconf->ipv4.trans_addr.v4.s_addr); 117 break; 118 case AF_INET6: 119 err |= gen_opt16_hello_prms_tlv(buf, TLV_TYPE_IPV6TRANSADDR, 120 leconf->ipv6.trans_addr.v6.s6_addr); 121 break; 122 default: 123 fatalx("send_hello: unknown af"); 124 } 125 126 err |= gen_opt4_hello_prms_tlv(buf, TLV_TYPE_CONFIG, 127 htonl(global.conf_seqnum)); 128 129 /* 130 * RFC 7552 - Section 6.1.1: 131 * "A Dual-stack LSR (i.e., an LSR supporting Dual-stack LDP for a peer) 132 * MUST include the Dual-Stack capability TLV in all of its LDP Hellos". 133 */ 134 if (ldp_is_dual_stack(leconf)) 135 err |= gen_ds_hello_prms_tlv(buf, leconf->trans_pref); 136 137 if (err) { 138 ibuf_free(buf); 139 return (-1); 140 } 141 142 send_packet(fd, af, &dst, ia, buf->buf, buf->wpos); 143 ibuf_free(buf); 144 145 return (0); 146 } 147 148 void 149 recv_hello(struct in_addr lsr_id, struct ldp_msg *msg, int af, 150 union ldpd_addr *src, struct iface *iface, int multicast, char *buf, 151 uint16_t len) 152 { 153 struct adj *adj = NULL; 154 struct nbr *nbr, *nbrt; 155 uint16_t holdtime, flags; 156 int tlvs_rcvd; 157 int ds_tlv; 158 union ldpd_addr trans_addr; 159 uint32_t scope_id = 0; 160 uint32_t conf_seqnum; 161 uint16_t trans_pref; 162 int r; 163 struct hello_source source; 164 struct iface_af *ia = NULL; 165 struct tnbr *tnbr = NULL; 166 167 r = tlv_decode_hello_prms(buf, len, &holdtime, &flags); 168 if (r == -1) { 169 log_debug("%s: lsr-id %s: failed to decode params", __func__, 170 inet_ntoa(lsr_id)); 171 return; 172 } 173 /* safety checks */ 174 if (holdtime != 0 && holdtime < MIN_HOLDTIME) { 175 log_debug("%s: lsr-id %s: invalid hello holdtime (%u)", 176 __func__, inet_ntoa(lsr_id), holdtime); 177 return; 178 } 179 if (multicast && (flags & F_HELLO_TARGETED)) { 180 log_debug("%s: lsr-id %s: multicast targeted hello", __func__, 181 inet_ntoa(lsr_id)); 182 return; 183 } 184 if (!multicast && !((flags & F_HELLO_TARGETED))) { 185 log_debug("%s: lsr-id %s: unicast link hello", __func__, 186 inet_ntoa(lsr_id)); 187 return; 188 } 189 buf += r; 190 len -= r; 191 192 r = tlv_decode_opt_hello_prms(buf, len, &tlvs_rcvd, af, &trans_addr, 193 &conf_seqnum, &trans_pref); 194 if (r == -1) { 195 log_debug("%s: lsr-id %s: failed to decode optional params", 196 __func__, inet_ntoa(lsr_id)); 197 return; 198 } 199 if (r != len) { 200 log_debug("%s: lsr-id %s: unexpected data in message", 201 __func__, inet_ntoa(lsr_id)); 202 return; 203 } 204 205 /* implicit transport address */ 206 if (!(tlvs_rcvd & F_HELLO_TLV_RCVD_ADDR)) 207 trans_addr = *src; 208 if (bad_addr(af, &trans_addr)) { 209 log_debug("%s: lsr-id %s: invalid transport address %s", 210 __func__, inet_ntoa(lsr_id), log_addr(af, &trans_addr)); 211 return; 212 } 213 if (af == AF_INET6 && IN6_IS_SCOPE_EMBED(&trans_addr.v6)) { 214 /* 215 * RFC 7552 - Section 6.1: 216 * "An LSR MUST use a global unicast IPv6 address in an IPv6 217 * Transport Address optional object of outgoing targeted 218 * Hellos and check for the same in incoming targeted Hellos 219 * (i.e., MUST discard the targeted Hello if it failed the 220 * check)". 221 */ 222 if (flags & F_HELLO_TARGETED) { 223 log_debug("%s: lsr-id %s: invalid targeted hello " 224 "transport address %s", __func__, inet_ntoa(lsr_id), 225 log_addr(af, &trans_addr)); 226 return; 227 } 228 scope_id = iface->ifindex; 229 } 230 231 memset(&source, 0, sizeof(source)); 232 source.lsr_id = lsr_id; 233 if (flags & F_HELLO_TARGETED) { 234 /* 235 * RFC 7552 - Section 5.2: 236 * "The link-local IPv6 addresses MUST NOT be used as the 237 * targeted LDP Hello packet's source or destination addresses". 238 */ 239 if (af == AF_INET6 && IN6_IS_SCOPE_EMBED(&src->v6)) { 240 log_debug("%s: lsr-id %s: targeted hello with " 241 "link-local source address", __func__, 242 inet_ntoa(lsr_id)); 243 return; 244 } 245 246 tnbr = tnbr_find(leconf, af, src); 247 248 /* remove the dynamic tnbr if the 'R' bit was cleared */ 249 if (tnbr && (tnbr->flags & F_TNBR_DYNAMIC) && 250 !((flags & F_HELLO_REQ_TARG))) { 251 tnbr->flags &= ~F_TNBR_DYNAMIC; 252 tnbr = tnbr_check(tnbr); 253 } 254 255 if (!tnbr) { 256 if (!((flags & F_HELLO_REQ_TARG) && 257 ((ldp_af_conf_get(leconf, af))->flags & 258 F_LDPD_AF_THELLO_ACCEPT))) 259 return; 260 261 tnbr = tnbr_new(leconf, af, src); 262 tnbr->flags |= F_TNBR_DYNAMIC; 263 tnbr_update(tnbr); 264 LIST_INSERT_HEAD(&leconf->tnbr_list, tnbr, entry); 265 } 266 267 source.type = HELLO_TARGETED; 268 source.target = tnbr; 269 } else { 270 ia = iface_af_get(iface, af); 271 source.type = HELLO_LINK; 272 source.link.ia = ia; 273 source.link.src_addr = *src; 274 } 275 276 adj = adj_find(&source); 277 nbr = nbr_find_ldpid(lsr_id.s_addr); 278 279 /* check dual-stack tlv */ 280 ds_tlv = (tlvs_rcvd & F_HELLO_TLV_RCVD_DS) ? 1 : 0; 281 if (ds_tlv && trans_pref != leconf->trans_pref) { 282 /* 283 * RFC 7552 - Section 6.1.1: 284 * "If the Dual-Stack capability TLV is present and the remote 285 * preference does not match the local preference (or does not 286 * get recognized), then the LSR MUST discard the Hello message 287 * and log an error. 288 * If an LDP session was already in place, then the LSR MUST 289 * send a fatal Notification message with status code of 290 * 'Transport Connection Mismatch' and reset the session". 291 */ 292 log_debug("%s: lsr-id %s: remote transport preference does not " 293 "match the local preference", __func__, inet_ntoa(lsr_id)); 294 if (nbr) 295 session_shutdown(nbr, S_TRANS_MISMTCH, msg->id, 296 msg->type); 297 if (adj) 298 adj_del(adj, S_SHUTDOWN); 299 return; 300 } 301 302 /* 303 * Check for noncompliant dual-stack neighbor according to 304 * RFC 7552 section 6.1.1. 305 */ 306 if (nbr && !ds_tlv) { 307 switch (af) { 308 case AF_INET: 309 if (nbr_adj_count(nbr, AF_INET6) > 0) { 310 session_shutdown(nbr, S_DS_NONCMPLNCE, 311 msg->id, msg->type); 312 return; 313 } 314 break; 315 case AF_INET6: 316 if (nbr_adj_count(nbr, AF_INET) > 0) { 317 session_shutdown(nbr, S_DS_NONCMPLNCE, 318 msg->id, msg->type); 319 return; 320 } 321 break; 322 default: 323 fatalx("recv_hello: unknown af"); 324 } 325 } 326 327 /* 328 * Protections against misconfigured networks and buggy implementations. 329 */ 330 if (nbr && nbr->af == af && 331 (ldp_addrcmp(af, &nbr->raddr, &trans_addr) || 332 nbr->raddr_scope != scope_id)) { 333 log_warnx("%s: lsr-id %s: hello packet advertising a different " 334 "transport address", __func__, inet_ntoa(lsr_id)); 335 if (adj) 336 adj_del(adj, S_SHUTDOWN); 337 return; 338 } 339 if (nbr == NULL) { 340 nbrt = nbr_find_addr(af, &trans_addr); 341 if (nbrt) { 342 log_debug("%s: transport address %s is already being " 343 "used by lsr-id %s", __func__, log_addr(af, 344 &trans_addr), inet_ntoa(nbrt->id)); 345 if (adj) 346 adj_del(adj, S_SHUTDOWN); 347 return; 348 } 349 } 350 351 if (adj == NULL) { 352 adj = adj_new(lsr_id, &source, &trans_addr); 353 if (nbr) { 354 adj->nbr = nbr; 355 LIST_INSERT_HEAD(&nbr->adj_list, adj, nbr_entry); 356 } 357 } 358 359 /* 360 * If the hello adjacency's address-family doesn't match the local 361 * preference, then an adjacency is still created but we don't attempt 362 * to start an LDP session. 363 */ 364 if (nbr == NULL && (!ds_tlv || 365 ((trans_pref == DUAL_STACK_LDPOV4 && af == AF_INET) || 366 (trans_pref == DUAL_STACK_LDPOV6 && af == AF_INET6)))) 367 nbr = nbr_new(lsr_id, af, ds_tlv, &trans_addr, scope_id); 368 369 /* dynamic LDPv4 GTSM negotiation as per RFC 6720 */ 370 if (nbr) { 371 if (flags & F_HELLO_GTSM) 372 nbr->flags |= F_NBR_GTSM_NEGOTIATED; 373 else 374 nbr->flags &= ~F_NBR_GTSM_NEGOTIATED; 375 } 376 377 /* update neighbor's configuration sequence number */ 378 if (nbr && (tlvs_rcvd & F_HELLO_TLV_RCVD_CONF)) { 379 if (conf_seqnum > nbr->conf_seqnum && 380 nbr_pending_idtimer(nbr)) 381 nbr_stop_idtimer(nbr); 382 nbr->conf_seqnum = conf_seqnum; 383 } 384 385 /* always update the holdtime to properly handle runtime changes */ 386 switch (source.type) { 387 case HELLO_LINK: 388 if (holdtime == 0) 389 holdtime = LINK_DFLT_HOLDTIME; 390 391 adj->holdtime = min(ia->hello_holdtime, holdtime); 392 break; 393 case HELLO_TARGETED: 394 if (holdtime == 0) 395 holdtime = TARGETED_DFLT_HOLDTIME; 396 397 adj->holdtime = min(tnbr->hello_holdtime, holdtime); 398 } 399 if (adj->holdtime != INFINITE_HOLDTIME) 400 adj_start_itimer(adj); 401 else 402 adj_stop_itimer(adj); 403 404 if (nbr && nbr->state == NBR_STA_PRESENT && !nbr_pending_idtimer(nbr) && 405 nbr_session_active_role(nbr) && !nbr_pending_connect(nbr)) 406 nbr_establish_connection(nbr); 407 } 408 409 static int 410 gen_hello_prms_tlv(struct ibuf *buf, uint16_t holdtime, uint16_t flags) 411 { 412 struct hello_prms_tlv parms; 413 414 memset(&parms, 0, sizeof(parms)); 415 parms.type = htons(TLV_TYPE_COMMONHELLO); 416 parms.length = htons(sizeof(parms.holdtime) + sizeof(parms.flags)); 417 parms.holdtime = htons(holdtime); 418 parms.flags = htons(flags); 419 420 return (ibuf_add(buf, &parms, sizeof(parms))); 421 } 422 423 static int 424 gen_opt4_hello_prms_tlv(struct ibuf *buf, uint16_t type, uint32_t value) 425 { 426 struct hello_prms_opt4_tlv parms; 427 428 memset(&parms, 0, sizeof(parms)); 429 parms.type = htons(type); 430 parms.length = htons(sizeof(parms.value)); 431 parms.value = value; 432 433 return (ibuf_add(buf, &parms, sizeof(parms))); 434 } 435 436 static int 437 gen_opt16_hello_prms_tlv(struct ibuf *buf, uint16_t type, uint8_t *value) 438 { 439 struct hello_prms_opt16_tlv parms; 440 441 memset(&parms, 0, sizeof(parms)); 442 parms.type = htons(type); 443 parms.length = htons(sizeof(parms.value)); 444 memcpy(&parms.value, value, sizeof(parms.value)); 445 446 return (ibuf_add(buf, &parms, sizeof(parms))); 447 } 448 449 static int 450 gen_ds_hello_prms_tlv(struct ibuf *buf, uint32_t value) 451 { 452 if (leconf->flags & F_LDPD_DS_CISCO_INTEROP) 453 value = htonl(value); 454 else 455 value = htonl(value << 28); 456 457 return (gen_opt4_hello_prms_tlv(buf, TLV_TYPE_DUALSTACK, value)); 458 } 459 460 static int 461 tlv_decode_hello_prms(char *buf, uint16_t len, uint16_t *holdtime, 462 uint16_t *flags) 463 { 464 struct hello_prms_tlv tlv; 465 466 if (len < sizeof(tlv)) 467 return (-1); 468 memcpy(&tlv, buf, sizeof(tlv)); 469 470 if (tlv.type != htons(TLV_TYPE_COMMONHELLO)) 471 return (-1); 472 if (ntohs(tlv.length) != sizeof(tlv) - TLV_HDR_SIZE) 473 return (-1); 474 475 *holdtime = ntohs(tlv.holdtime); 476 *flags = ntohs(tlv.flags); 477 478 return (sizeof(tlv)); 479 } 480 481 static int 482 tlv_decode_opt_hello_prms(char *buf, uint16_t len, int *tlvs_rcvd, int af, 483 union ldpd_addr *addr, uint32_t *conf_number, uint16_t *trans_pref) 484 { 485 struct tlv tlv; 486 uint16_t tlv_len; 487 int total = 0; 488 489 *tlvs_rcvd = 0; 490 memset(addr, 0, sizeof(*addr)); 491 *conf_number = 0; 492 *trans_pref = 0; 493 494 /* 495 * RFC 7552 - Section 6.1: 496 * "An LSR SHOULD accept the Hello message that contains both IPv4 and 497 * IPv6 Transport Address optional objects but MUST use only the 498 * transport address whose address family is the same as that of the 499 * IP packet carrying the Hello message. An LSR SHOULD accept only 500 * the first Transport Address optional object for a given address 501 * family in the received Hello message and ignore the rest if the 502 * LSR receives more than one Transport Address optional object for a 503 * given address family". 504 */ 505 while (len >= sizeof(tlv)) { 506 memcpy(&tlv, buf, TLV_HDR_SIZE); 507 tlv_len = ntohs(tlv.length); 508 if (tlv_len + TLV_HDR_SIZE > len) 509 return (-1); 510 buf += TLV_HDR_SIZE; 511 len -= TLV_HDR_SIZE; 512 total += TLV_HDR_SIZE; 513 514 switch (ntohs(tlv.type)) { 515 case TLV_TYPE_IPV4TRANSADDR: 516 if (tlv_len != sizeof(addr->v4)) 517 return (-1); 518 if (af != AF_INET) 519 return (-1); 520 if (*tlvs_rcvd & F_HELLO_TLV_RCVD_ADDR) 521 break; 522 memcpy(&addr->v4, buf, sizeof(addr->v4)); 523 *tlvs_rcvd |= F_HELLO_TLV_RCVD_ADDR; 524 break; 525 case TLV_TYPE_IPV6TRANSADDR: 526 if (tlv_len != sizeof(addr->v6)) 527 return (-1); 528 if (af != AF_INET6) 529 return (-1); 530 if (*tlvs_rcvd & F_HELLO_TLV_RCVD_ADDR) 531 break; 532 memcpy(&addr->v6, buf, sizeof(addr->v6)); 533 *tlvs_rcvd |= F_HELLO_TLV_RCVD_ADDR; 534 break; 535 case TLV_TYPE_CONFIG: 536 if (tlv_len != sizeof(uint32_t)) 537 return (-1); 538 memcpy(conf_number, buf, sizeof(uint32_t)); 539 *tlvs_rcvd |= F_HELLO_TLV_RCVD_CONF; 540 break; 541 case TLV_TYPE_DUALSTACK: 542 if (tlv_len != sizeof(uint32_t)) 543 return (-1); 544 /* 545 * RFC 7552 - Section 6.1: 546 * "A Single-stack LSR does not need to use the 547 * Dual-Stack capability in Hello messages and SHOULD 548 * ignore this capability if received". 549 */ 550 if (!ldp_is_dual_stack(leconf)) 551 break; 552 /* Shame on you, Cisco! */ 553 if (leconf->flags & F_LDPD_DS_CISCO_INTEROP) { 554 memcpy(trans_pref, buf + sizeof(uint16_t), 555 sizeof(uint16_t)); 556 *trans_pref = ntohs(*trans_pref); 557 } else { 558 memcpy(trans_pref, buf , sizeof(uint16_t)); 559 *trans_pref = ntohs(*trans_pref) >> 12; 560 } 561 *tlvs_rcvd |= F_HELLO_TLV_RCVD_DS; 562 break; 563 default: 564 /* if unknown flag set, ignore TLV */ 565 if (!(ntohs(tlv.type) & UNKNOWN_FLAG)) 566 return (-1); 567 break; 568 } 569 buf += tlv_len; 570 len -= tlv_len; 571 total += tlv_len; 572 } 573 574 return (total); 575 } 576