1 /* BGP open message handling
2 * Copyright (C) 1998, 1999 Kunihiro Ishiguro
4 * This file is part of GNU Zebra.
6 * GNU Zebra is free software; you can redistribute it and/or modify it
7 * under the terms of the GNU General Public License as published by the
8 * Free Software Foundation; either version 2, or (at your option) any
11 * GNU Zebra is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
16 * You should have received a copy of the GNU General Public License along
17 * with this program; see the file COPYING; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
34 #include "bgpd/bgpd.h"
35 #include "bgpd/bgp_attr.h"
36 #include "bgpd/bgp_debug.h"
37 #include "bgpd/bgp_errors.h"
38 #include "bgpd/bgp_fsm.h"
39 #include "bgpd/bgp_packet.h"
40 #include "bgpd/bgp_open.h"
41 #include "bgpd/bgp_aspath.h"
42 #include "bgpd/bgp_vty.h"
43 #include "bgpd/bgp_memory.h"
45 /* BGP-4 Multiprotocol Extentions lead us to the complex world. We can
46 negotiate remote peer supports extentions or not. But if
47 remote-peer doesn't supports negotiation process itself. We would
48 like to do manual configuration.
50 So there is many configurable point. First of all we want set each
51 peer whether we send capability negotiation to the peer or not.
52 Next, if we send capability to the peer we want to set my capability
53 inforation at each peer. */
55 void bgp_capability_vty_out(struct vty
*vty
, struct peer
*peer
, bool use_json
,
56 json_object
*json_neigh
)
60 struct capability_mp_data mpc
;
61 struct capability_header
*hdr
;
62 json_object
*json_cap
= NULL
;
65 json_cap
= json_object_new_object();
67 pnt
= peer
->notify
.data
;
68 end
= pnt
+ peer
->notify
.length
;
71 if (pnt
+ sizeof(struct capability_mp_data
) + 2 > end
)
74 hdr
= (struct capability_header
*)pnt
;
75 if (pnt
+ hdr
->length
+ 2 > end
)
78 memcpy(&mpc
, pnt
+ 2, sizeof(struct capability_mp_data
));
80 if (hdr
->code
== CAPABILITY_CODE_MP
) {
84 (void)bgp_map_afi_safi_iana2int(ntohs(mpc
.afi
),
85 mpc
.safi
, &afi
, &safi
);
90 json_object_string_add(
92 "capabilityErrorMultiProtocolAfi",
96 json_object_string_add(
98 "capabilityErrorMultiProtocolAfi",
102 json_object_string_add(
104 "capabilityErrorMultiProtocolAfi",
110 "capabilityErrorMultiProtocolAfiUnknown",
116 json_object_string_add(
118 "capabilityErrorMultiProtocolSafi",
122 json_object_string_add(
124 "capabilityErrorMultiProtocolSafi",
127 case SAFI_LABELED_UNICAST
:
128 json_object_string_add(
130 "capabilityErrorMultiProtocolSafi",
134 json_object_string_add(
136 "capabilityErrorMultiProtocolSafi",
140 json_object_string_add(
142 "capabilityErrorMultiProtocolSafi",
146 json_object_string_add(
148 "capabilityErrorMultiProtocolSafi",
152 json_object_string_add(
154 "capabilityErrorMultiProtocolSafi",
160 "capabilityErrorMultiProtocolSafiUnknown",
166 " Capability error for: Multi protocol ");
169 vty_out(vty
, "AFI IPv4, ");
172 vty_out(vty
, "AFI IPv6, ");
175 vty_out(vty
, "AFI L2VPN, ");
178 vty_out(vty
, "AFI Unknown %d, ",
184 vty_out(vty
, "SAFI Unicast");
187 vty_out(vty
, "SAFI Multicast");
189 case SAFI_LABELED_UNICAST
:
190 vty_out(vty
, "SAFI Labeled-unicast");
193 vty_out(vty
, "SAFI MPLS-labeled VPN");
196 vty_out(vty
, "SAFI ENCAP");
199 vty_out(vty
, "SAFI FLOWSPEC");
202 vty_out(vty
, "SAFI EVPN");
205 vty_out(vty
, "SAFI Unknown %d ",
211 } else if (hdr
->code
>= 128) {
215 "capabilityErrorVendorSpecificCapabilityCode",
219 " Capability error: vendor specific capability code %d",
225 "capabilityErrorUnknownCapabilityCode",
229 " Capability error: unknown capability code %d",
232 pnt
+= hdr
->length
+ 2;
235 json_object_object_add(json_neigh
, "capabilityErrors",
239 static void bgp_capability_mp_data(struct stream
*s
,
240 struct capability_mp_data
*mpc
)
242 mpc
->afi
= stream_getw(s
);
243 mpc
->reserved
= stream_getc(s
);
244 mpc
->safi
= stream_getc(s
);
247 /* Set negotiated capability value. */
248 static int bgp_capability_mp(struct peer
*peer
, struct capability_header
*hdr
)
250 struct capability_mp_data mpc
;
251 struct stream
*s
= BGP_INPUT(peer
);
255 /* Verify length is 4 */
256 if (hdr
->length
!= 4) {
258 EC_BGP_CAPABILITY_INVALID_LENGTH
,
259 "MP Cap: Received invalid length %d, non-multiple of 4",
264 bgp_capability_mp_data(s
, &mpc
);
266 if (bgp_debug_neighbor_events(peer
))
267 zlog_debug("%s OPEN has MP_EXT CAP for afi/safi: %s/%s",
268 peer
->host
, iana_afi2str(mpc
.afi
),
269 iana_safi2str(mpc
.safi
));
271 /* Convert AFI, SAFI to internal values, check. */
272 if (bgp_map_afi_safi_iana2int(mpc
.afi
, mpc
.safi
, &afi
, &safi
))
275 /* Now safi remapped, and afi/safi are valid array indices */
276 peer
->afc_recv
[afi
][safi
] = 1;
278 if (peer
->afc
[afi
][safi
])
279 peer
->afc_nego
[afi
][safi
] = 1;
286 static void bgp_capability_orf_not_support(struct peer
*peer
, iana_afi_t afi
,
287 iana_safi_t safi
, uint8_t type
,
290 if (bgp_debug_neighbor_events(peer
))
292 "%s Addr-family %d/%d has ORF type/mode %d/%d not supported",
293 peer
->host
, afi
, safi
, type
, mode
);
296 static const struct message orf_type_str
[] = {
297 {ORF_TYPE_PREFIX
, "Prefixlist"},
298 {ORF_TYPE_PREFIX_OLD
, "Prefixlist (old)"},
301 static const struct message orf_mode_str
[] = {{ORF_MODE_RECEIVE
, "Receive"},
302 {ORF_MODE_SEND
, "Send"},
303 {ORF_MODE_BOTH
, "Both"},
306 static int bgp_capability_orf_entry(struct peer
*peer
,
307 struct capability_header
*hdr
)
309 struct stream
*s
= BGP_INPUT(peer
);
310 struct capability_mp_data mpc
;
314 iana_safi_t pkt_safi
;
318 uint16_t sm_cap
= 0; /* capability send-mode receive */
319 uint16_t rm_cap
= 0; /* capability receive-mode receive */
322 /* ORF Entry header */
323 bgp_capability_mp_data(s
, &mpc
);
324 num
= stream_getc(s
);
328 if (bgp_debug_neighbor_events(peer
))
329 zlog_debug("%s ORF Cap entry for afi/safi: %s/%s", peer
->host
,
330 iana_afi2str(mpc
.afi
), iana_safi2str(mpc
.safi
));
332 /* Convert AFI, SAFI to internal values, check. */
333 if (bgp_map_afi_safi_iana2int(pkt_afi
, pkt_safi
, &afi
, &safi
)) {
335 "%s Addr-family %d/%d not supported. Ignoring the ORF capability",
336 peer
->host
, pkt_afi
, pkt_safi
);
343 /* validate number field */
344 if (CAPABILITY_CODE_ORF_LEN
+ (num
* 2) > hdr
->length
) {
346 "%s ORF Capability entry length error, Cap length %u, num %u",
347 peer
->host
, hdr
->length
, num
);
348 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
349 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
353 for (i
= 0; i
< num
; i
++) {
354 type
= stream_getc(s
);
355 mode
= stream_getc(s
);
357 /* ORF Mode error check */
361 case ORF_MODE_RECEIVE
:
364 bgp_capability_orf_not_support(peer
, pkt_afi
, pkt_safi
,
368 /* ORF Type and afi/safi error checks */
369 /* capcode versus type */
371 case CAPABILITY_CODE_ORF
:
373 case ORF_TYPE_PREFIX
:
376 bgp_capability_orf_not_support(
377 peer
, pkt_afi
, pkt_safi
, type
, mode
);
381 case CAPABILITY_CODE_ORF_OLD
:
383 case ORF_TYPE_PREFIX_OLD
:
386 bgp_capability_orf_not_support(
387 peer
, pkt_afi
, pkt_safi
, type
, mode
);
392 bgp_capability_orf_not_support(peer
, pkt_afi
, pkt_safi
,
398 if (!((afi
== AFI_IP
&& safi
== SAFI_UNICAST
)
399 || (afi
== AFI_IP
&& safi
== SAFI_MULTICAST
)
400 || (afi
== AFI_IP6
&& safi
== SAFI_UNICAST
))) {
401 bgp_capability_orf_not_support(peer
, pkt_afi
, pkt_safi
,
406 if (bgp_debug_neighbor_events(peer
))
408 "%s OPEN has %s ORF capability as %s for afi/safi: %s/%s",
410 lookup_msg(orf_type_str
, type
, NULL
),
411 lookup_msg(orf_mode_str
, mode
, NULL
),
412 iana_afi2str(pkt_afi
), iana_safi2str(pkt_safi
));
414 if (hdr
->code
== CAPABILITY_CODE_ORF
) {
415 sm_cap
= PEER_CAP_ORF_PREFIX_SM_RCV
;
416 rm_cap
= PEER_CAP_ORF_PREFIX_RM_RCV
;
417 } else if (hdr
->code
== CAPABILITY_CODE_ORF_OLD
) {
418 sm_cap
= PEER_CAP_ORF_PREFIX_SM_OLD_RCV
;
419 rm_cap
= PEER_CAP_ORF_PREFIX_RM_OLD_RCV
;
421 bgp_capability_orf_not_support(peer
, pkt_afi
, pkt_safi
,
428 SET_FLAG(peer
->af_cap
[afi
][safi
], sm_cap
);
429 SET_FLAG(peer
->af_cap
[afi
][safi
], rm_cap
);
432 SET_FLAG(peer
->af_cap
[afi
][safi
], sm_cap
);
434 case ORF_MODE_RECEIVE
:
435 SET_FLAG(peer
->af_cap
[afi
][safi
], rm_cap
);
442 static int bgp_capability_restart(struct peer
*peer
,
443 struct capability_header
*caphdr
)
445 struct stream
*s
= BGP_INPUT(peer
);
446 uint16_t restart_flag_time
;
447 size_t end
= stream_get_getp(s
) + caphdr
->length
;
449 /* Verify length is a multiple of 4 */
450 if ((caphdr
->length
- 2) % 4) {
452 EC_BGP_CAPABILITY_INVALID_LENGTH
,
453 "Restart Cap: Received invalid length %d, non-multiple of 4",
458 SET_FLAG(peer
->cap
, PEER_CAP_RESTART_RCV
);
459 restart_flag_time
= stream_getw(s
);
460 if (CHECK_FLAG(restart_flag_time
, RESTART_R_BIT
))
461 SET_FLAG(peer
->cap
, PEER_CAP_RESTART_BIT_RCV
);
463 UNSET_FLAG(peer
->cap
, PEER_CAP_RESTART_BIT_RCV
);
465 UNSET_FLAG(restart_flag_time
, 0xF000);
466 peer
->v_gr_restart
= restart_flag_time
;
468 if (bgp_debug_neighbor_events(peer
)) {
469 zlog_debug("%s OPEN has Graceful Restart capability",
471 zlog_debug("%s Peer has%srestarted. Restart Time : %d",
473 CHECK_FLAG(peer
->cap
, PEER_CAP_RESTART_BIT_RCV
)
479 while (stream_get_getp(s
) + 4 <= end
) {
482 iana_afi_t pkt_afi
= stream_getw(s
);
483 iana_safi_t pkt_safi
= stream_getc(s
);
484 uint8_t flag
= stream_getc(s
);
486 /* Convert AFI, SAFI to internal values, check. */
487 if (bgp_map_afi_safi_iana2int(pkt_afi
, pkt_safi
, &afi
, &safi
)) {
488 if (bgp_debug_neighbor_events(peer
))
490 "%s Addr-family %s/%s(afi/safi) not supported. Ignore the Graceful Restart capability for this AFI/SAFI",
491 peer
->host
, iana_afi2str(pkt_afi
),
492 iana_safi2str(pkt_safi
));
493 } else if (!peer
->afc
[afi
][safi
]) {
494 if (bgp_debug_neighbor_events(peer
))
496 "%s Addr-family %s/%s(afi/safi) not enabled. Ignore the Graceful Restart capability",
497 peer
->host
, iana_afi2str(pkt_afi
),
498 iana_safi2str(pkt_safi
));
500 if (bgp_debug_neighbor_events(peer
))
502 "%s Address family %s is%spreserved",
503 peer
->host
, get_afi_safi_str(afi
, safi
, false),
505 peer
->af_cap
[afi
][safi
],
506 PEER_CAP_RESTART_AF_PRESERVE_RCV
)
510 SET_FLAG(peer
->af_cap
[afi
][safi
],
511 PEER_CAP_RESTART_AF_RCV
);
512 if (CHECK_FLAG(flag
, RESTART_F_BIT
))
513 SET_FLAG(peer
->af_cap
[afi
][safi
],
514 PEER_CAP_RESTART_AF_PRESERVE_RCV
);
520 /* Unlike other capability parsing routines, this one returns 0 on error */
521 static as_t
bgp_capability_as4(struct peer
*peer
, struct capability_header
*hdr
)
523 SET_FLAG(peer
->cap
, PEER_CAP_AS4_RCV
);
525 if (hdr
->length
!= CAPABILITY_CODE_AS4_LEN
) {
526 flog_err(EC_BGP_PKT_OPEN
,
527 "%s AS4 capability has incorrect data length %d",
528 peer
->host
, hdr
->length
);
532 as_t as4
= stream_getl(BGP_INPUT(peer
));
534 if (BGP_DEBUG(as4
, AS4
))
536 "%s [AS4] about to set cap PEER_CAP_AS4_RCV, got as4 %u",
541 static int bgp_capability_ext_message(struct peer
*peer
,
542 struct capability_header
*hdr
)
544 if (hdr
->length
!= CAPABILITY_CODE_EXT_MESSAGE_LEN
) {
547 "%s: BGP Extended Message capability has incorrect data length %d",
548 peer
->host
, hdr
->length
);
552 SET_FLAG(peer
->cap
, PEER_CAP_EXTENDED_MESSAGE_RCV
);
557 static int bgp_capability_addpath(struct peer
*peer
,
558 struct capability_header
*hdr
)
560 struct stream
*s
= BGP_INPUT(peer
);
561 size_t end
= stream_get_getp(s
) + hdr
->length
;
563 SET_FLAG(peer
->cap
, PEER_CAP_ADDPATH_RCV
);
565 /* Verify length is a multiple of 4 */
566 if (hdr
->length
% 4) {
568 EC_BGP_CAPABILITY_INVALID_LENGTH
,
569 "Add Path: Received invalid length %d, non-multiple of 4",
574 while (stream_get_getp(s
) + 4 <= end
) {
577 iana_afi_t pkt_afi
= stream_getw(s
);
578 iana_safi_t pkt_safi
= stream_getc(s
);
579 uint8_t send_receive
= stream_getc(s
);
581 if (bgp_debug_neighbor_events(peer
))
583 "%s OPEN has AddPath CAP for afi/safi: %s/%s%s%s",
584 peer
->host
, iana_afi2str(pkt_afi
),
585 iana_safi2str(pkt_safi
),
586 (send_receive
& BGP_ADDPATH_RX
) ? ", receive"
588 (send_receive
& BGP_ADDPATH_TX
) ? ", transmit"
591 /* Convert AFI, SAFI to internal values, check. */
592 if (bgp_map_afi_safi_iana2int(pkt_afi
, pkt_safi
, &afi
, &safi
)) {
593 if (bgp_debug_neighbor_events(peer
))
595 "%s Addr-family %s/%s(afi/safi) not supported. Ignore the Addpath Attribute for this AFI/SAFI",
596 peer
->host
, iana_afi2str(pkt_afi
),
597 iana_safi2str(pkt_safi
));
599 } else if (!peer
->afc
[afi
][safi
]) {
600 if (bgp_debug_neighbor_events(peer
))
602 "%s Addr-family %s/%s(afi/safi) not enabled. Ignore the AddPath capability for this AFI/SAFI",
603 peer
->host
, iana_afi2str(pkt_afi
),
604 iana_safi2str(pkt_safi
));
608 if (send_receive
& BGP_ADDPATH_RX
)
609 SET_FLAG(peer
->af_cap
[afi
][safi
],
610 PEER_CAP_ADDPATH_AF_RX_RCV
);
612 if (send_receive
& BGP_ADDPATH_TX
)
613 SET_FLAG(peer
->af_cap
[afi
][safi
],
614 PEER_CAP_ADDPATH_AF_TX_RCV
);
620 static int bgp_capability_enhe(struct peer
*peer
, struct capability_header
*hdr
)
622 struct stream
*s
= BGP_INPUT(peer
);
623 size_t end
= stream_get_getp(s
) + hdr
->length
;
625 /* Verify length is a multiple of 4 */
626 if (hdr
->length
% 6) {
628 EC_BGP_CAPABILITY_INVALID_LENGTH
,
629 "Extended NH: Received invalid length %d, non-multiple of 6",
634 while (stream_get_getp(s
) + 6 <= end
) {
635 iana_afi_t pkt_afi
= stream_getw(s
);
637 iana_safi_t pkt_safi
= stream_getw(s
);
639 iana_afi_t pkt_nh_afi
= stream_getw(s
);
642 if (bgp_debug_neighbor_events(peer
))
644 "%s Received with afi/safi/next-hop afi: %s/%s/%u",
645 peer
->host
, iana_afi2str(pkt_afi
),
646 iana_safi2str(pkt_safi
), pkt_nh_afi
);
648 /* Convert AFI, SAFI to internal values, check. */
649 if (bgp_map_afi_safi_iana2int(pkt_afi
, pkt_safi
, &afi
, &safi
)) {
650 if (bgp_debug_neighbor_events(peer
))
652 "%s Addr-family %s/%s(afi/safi) not supported. Ignore the ENHE Attribute for this AFI/SAFI",
653 peer
->host
, iana_afi2str(pkt_afi
),
654 iana_safi2str(pkt_safi
));
658 /* RFC 5549 specifies use of this capability only for IPv4 AFI,
660 * the Nexthop AFI being IPv6. A future spec may introduce other
661 * possibilities, so we ignore other values with a log. Also,
663 * SAFI_UNICAST and SAFI_LABELED_UNICAST are currently supported
666 nh_afi
= afi_iana2int(pkt_nh_afi
);
668 if (afi
!= AFI_IP
|| nh_afi
!= AFI_IP6
669 || !(safi
== SAFI_UNICAST
|| safi
== SAFI_MPLS_VPN
670 || safi
== SAFI_LABELED_UNICAST
)) {
672 EC_BGP_CAPABILITY_INVALID_DATA
,
673 "%s Unexpected afi/safi/next-hop afi: %s/%s/%u in Extended Next-hop capability, ignoring",
674 peer
->host
, iana_afi2str(pkt_afi
),
675 iana_safi2str(pkt_safi
), pkt_nh_afi
);
679 SET_FLAG(peer
->af_cap
[afi
][safi
], PEER_CAP_ENHE_AF_RCV
);
681 if (CHECK_FLAG(peer
->af_cap
[afi
][safi
], PEER_CAP_ENHE_AF_ADV
))
682 SET_FLAG(peer
->af_cap
[afi
][safi
],
683 PEER_CAP_ENHE_AF_NEGO
);
686 SET_FLAG(peer
->cap
, PEER_CAP_ENHE_RCV
);
691 static int bgp_capability_hostname(struct peer
*peer
,
692 struct capability_header
*hdr
)
694 struct stream
*s
= BGP_INPUT(peer
);
695 char str
[BGP_MAX_HOSTNAME
+ 1];
696 size_t end
= stream_get_getp(s
) + hdr
->length
;
699 SET_FLAG(peer
->cap
, PEER_CAP_HOSTNAME_RCV
);
701 len
= stream_getc(s
);
702 if (stream_get_getp(s
) + len
> end
) {
704 EC_BGP_CAPABILITY_INVALID_DATA
,
705 "%s: Received malformed hostname capability from peer %s",
706 __func__
, peer
->host
);
710 if (len
> BGP_MAX_HOSTNAME
) {
711 stream_get(str
, s
, BGP_MAX_HOSTNAME
);
712 stream_forward_getp(s
, len
- BGP_MAX_HOSTNAME
);
713 len
= BGP_MAX_HOSTNAME
; /* to set the '\0' below */
715 stream_get(str
, s
, len
);
720 XFREE(MTYPE_BGP_PEER_HOST
, peer
->hostname
);
721 XFREE(MTYPE_BGP_PEER_HOST
, peer
->domainname
);
723 peer
->hostname
= XSTRDUP(MTYPE_BGP_PEER_HOST
, str
);
726 if (stream_get_getp(s
) + 1 > end
) {
728 EC_BGP_CAPABILITY_INVALID_DATA
,
729 "%s: Received invalid domain name len (hostname capability) from peer %s",
730 __func__
, peer
->host
);
734 len
= stream_getc(s
);
735 if (stream_get_getp(s
) + len
> end
) {
737 EC_BGP_CAPABILITY_INVALID_DATA
,
738 "%s: Received runt domain name (hostname capability) from peer %s",
739 __func__
, peer
->host
);
743 if (len
> BGP_MAX_HOSTNAME
) {
744 stream_get(str
, s
, BGP_MAX_HOSTNAME
);
745 stream_forward_getp(s
, len
- BGP_MAX_HOSTNAME
);
746 len
= BGP_MAX_HOSTNAME
; /* to set the '\0' below */
748 stream_get(str
, s
, len
);
753 XFREE(MTYPE_BGP_PEER_HOST
, peer
->domainname
);
755 peer
->domainname
= XSTRDUP(MTYPE_BGP_PEER_HOST
, str
);
758 if (bgp_debug_neighbor_events(peer
)) {
759 zlog_debug("%s received hostname %s, domainname %s", peer
->host
,
760 peer
->hostname
, peer
->domainname
);
766 static const struct message capcode_str
[] = {
767 {CAPABILITY_CODE_MP
, "MultiProtocol Extensions"},
768 {CAPABILITY_CODE_REFRESH
, "Route Refresh"},
769 {CAPABILITY_CODE_ORF
, "Cooperative Route Filtering"},
770 {CAPABILITY_CODE_RESTART
, "Graceful Restart"},
771 {CAPABILITY_CODE_AS4
, "4-octet AS number"},
772 {CAPABILITY_CODE_ADDPATH
, "AddPath"},
773 {CAPABILITY_CODE_DYNAMIC
, "Dynamic"},
774 {CAPABILITY_CODE_ENHE
, "Extended Next Hop Encoding"},
775 {CAPABILITY_CODE_DYNAMIC_OLD
, "Dynamic (Old)"},
776 {CAPABILITY_CODE_REFRESH_OLD
, "Route Refresh (Old)"},
777 {CAPABILITY_CODE_ORF_OLD
, "ORF (Old)"},
778 {CAPABILITY_CODE_FQDN
, "FQDN"},
779 {CAPABILITY_CODE_ENHANCED_RR
, "Enhanced Route Refresh"},
780 {CAPABILITY_CODE_EXT_MESSAGE
, "BGP Extended Message"},
783 /* Minimum sizes for length field of each cap (so not inc. the header) */
784 static const size_t cap_minsizes
[] = {
785 [CAPABILITY_CODE_MP
] = CAPABILITY_CODE_MP_LEN
,
786 [CAPABILITY_CODE_REFRESH
] = CAPABILITY_CODE_REFRESH_LEN
,
787 [CAPABILITY_CODE_ORF
] = CAPABILITY_CODE_ORF_LEN
,
788 [CAPABILITY_CODE_RESTART
] = CAPABILITY_CODE_RESTART_LEN
,
789 [CAPABILITY_CODE_AS4
] = CAPABILITY_CODE_AS4_LEN
,
790 [CAPABILITY_CODE_ADDPATH
] = CAPABILITY_CODE_ADDPATH_LEN
,
791 [CAPABILITY_CODE_DYNAMIC
] = CAPABILITY_CODE_DYNAMIC_LEN
,
792 [CAPABILITY_CODE_DYNAMIC_OLD
] = CAPABILITY_CODE_DYNAMIC_LEN
,
793 [CAPABILITY_CODE_ENHE
] = CAPABILITY_CODE_ENHE_LEN
,
794 [CAPABILITY_CODE_REFRESH_OLD
] = CAPABILITY_CODE_REFRESH_LEN
,
795 [CAPABILITY_CODE_ORF_OLD
] = CAPABILITY_CODE_ORF_LEN
,
796 [CAPABILITY_CODE_FQDN
] = CAPABILITY_CODE_MIN_FQDN_LEN
,
797 [CAPABILITY_CODE_ENHANCED_RR
] = CAPABILITY_CODE_ENHANCED_LEN
,
798 [CAPABILITY_CODE_EXT_MESSAGE
] = CAPABILITY_CODE_EXT_MESSAGE_LEN
,
801 /* value the capability must be a multiple of.
802 * 0-data capabilities won't be checked against this.
803 * Other capabilities whose data doesn't fall on convenient boundaries for this
804 * table should be set to 1.
806 static const size_t cap_modsizes
[] = {
807 [CAPABILITY_CODE_MP
] = 4,
808 [CAPABILITY_CODE_REFRESH
] = 1,
809 [CAPABILITY_CODE_ORF
] = 1,
810 [CAPABILITY_CODE_RESTART
] = 1,
811 [CAPABILITY_CODE_AS4
] = 4,
812 [CAPABILITY_CODE_ADDPATH
] = 4,
813 [CAPABILITY_CODE_DYNAMIC
] = 1,
814 [CAPABILITY_CODE_DYNAMIC_OLD
] = 1,
815 [CAPABILITY_CODE_ENHE
] = 6,
816 [CAPABILITY_CODE_REFRESH_OLD
] = 1,
817 [CAPABILITY_CODE_ORF_OLD
] = 1,
818 [CAPABILITY_CODE_FQDN
] = 1,
819 [CAPABILITY_CODE_ENHANCED_RR
] = 1,
820 [CAPABILITY_CODE_EXT_MESSAGE
] = 1,
824 * Parse given capability.
825 * XXX: This is reading into a stream, but not using stream API
827 * @param[out] mp_capability Set to 1 on return iff one or more Multiprotocol
828 * capabilities were encountered.
830 static int bgp_capability_parse(struct peer
*peer
, size_t length
,
831 int *mp_capability
, uint8_t **error
)
834 struct stream
*s
= BGP_INPUT(peer
);
835 size_t end
= stream_get_getp(s
) + length
;
836 uint16_t restart_flag_time
= 0;
838 assert(STREAM_READABLE(s
) >= length
);
840 while (stream_get_getp(s
) < end
) {
842 uint8_t *sp
= stream_pnt(s
);
843 struct capability_header caphdr
;
846 /* We need at least capability code and capability length. */
847 if (stream_get_getp(s
) + 2 > end
) {
848 zlog_info("%s Capability length error (< header)",
850 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
851 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
855 caphdr
.code
= stream_getc(s
);
856 caphdr
.length
= stream_getc(s
);
857 start
= stream_get_getp(s
);
859 /* Capability length check sanity check. */
860 if (start
+ caphdr
.length
> end
) {
861 zlog_info("%s Capability length error (< length)",
863 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
864 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
868 if (bgp_debug_neighbor_events(peer
))
869 zlog_debug("%s OPEN has %s capability (%u), length %u",
871 lookup_msg(capcode_str
, caphdr
.code
, NULL
),
872 caphdr
.code
, caphdr
.length
);
874 /* Length sanity check, type-specific, for known capabilities */
875 switch (caphdr
.code
) {
876 case CAPABILITY_CODE_MP
:
877 case CAPABILITY_CODE_REFRESH
:
878 case CAPABILITY_CODE_REFRESH_OLD
:
879 case CAPABILITY_CODE_ORF
:
880 case CAPABILITY_CODE_ORF_OLD
:
881 case CAPABILITY_CODE_RESTART
:
882 case CAPABILITY_CODE_AS4
:
883 case CAPABILITY_CODE_ADDPATH
:
884 case CAPABILITY_CODE_DYNAMIC
:
885 case CAPABILITY_CODE_DYNAMIC_OLD
:
886 case CAPABILITY_CODE_ENHE
:
887 case CAPABILITY_CODE_FQDN
:
888 case CAPABILITY_CODE_ENHANCED_RR
:
889 case CAPABILITY_CODE_EXT_MESSAGE
:
891 if (caphdr
.length
< cap_minsizes
[caphdr
.code
]) {
893 "%s %s Capability length error: got %u, expected at least %u",
895 lookup_msg(capcode_str
, caphdr
.code
,
898 (unsigned)cap_minsizes
[caphdr
.code
]);
899 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
900 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
904 && caphdr
.length
% cap_modsizes
[caphdr
.code
] != 0) {
906 "%s %s Capability length error: got %u, expected a multiple of %u",
908 lookup_msg(capcode_str
, caphdr
.code
,
911 (unsigned)cap_modsizes
[caphdr
.code
]);
912 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
913 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
916 /* we deliberately ignore unknown codes, see below */
921 switch (caphdr
.code
) {
922 case CAPABILITY_CODE_MP
: {
925 /* Ignore capability when override-capability is set. */
926 if (!CHECK_FLAG(peer
->flags
,
927 PEER_FLAG_OVERRIDE_CAPABILITY
)) {
928 /* Set negotiated value. */
929 ret
= bgp_capability_mp(peer
, &caphdr
);
931 /* Unsupported Capability. */
933 /* Store return data. */
934 memcpy(*error
, sp
, caphdr
.length
+ 2);
935 *error
+= caphdr
.length
+ 2;
937 ret
= 0; /* Don't return error for this */
940 case CAPABILITY_CODE_ENHANCED_RR
:
941 case CAPABILITY_CODE_REFRESH
:
942 case CAPABILITY_CODE_REFRESH_OLD
: {
943 /* BGP refresh capability */
944 if (caphdr
.code
== CAPABILITY_CODE_ENHANCED_RR
)
945 SET_FLAG(peer
->cap
, PEER_CAP_ENHANCED_RR_RCV
);
946 else if (caphdr
.code
== CAPABILITY_CODE_REFRESH_OLD
)
947 SET_FLAG(peer
->cap
, PEER_CAP_REFRESH_OLD_RCV
);
949 SET_FLAG(peer
->cap
, PEER_CAP_REFRESH_NEW_RCV
);
951 case CAPABILITY_CODE_ORF
:
952 case CAPABILITY_CODE_ORF_OLD
:
953 ret
= bgp_capability_orf_entry(peer
, &caphdr
);
955 case CAPABILITY_CODE_RESTART
:
956 ret
= bgp_capability_restart(peer
, &caphdr
);
958 case CAPABILITY_CODE_DYNAMIC
:
959 case CAPABILITY_CODE_DYNAMIC_OLD
:
960 SET_FLAG(peer
->cap
, PEER_CAP_DYNAMIC_RCV
);
962 case CAPABILITY_CODE_AS4
:
963 /* Already handled as a special-case parsing of the
965 * at the beginning of OPEN processing. So we care not a
967 * for the value really, only error case.
969 if (!bgp_capability_as4(peer
, &caphdr
))
972 case CAPABILITY_CODE_ADDPATH
:
973 ret
= bgp_capability_addpath(peer
, &caphdr
);
975 case CAPABILITY_CODE_ENHE
:
976 ret
= bgp_capability_enhe(peer
, &caphdr
);
978 case CAPABILITY_CODE_EXT_MESSAGE
:
979 ret
= bgp_capability_ext_message(peer
, &caphdr
);
981 case CAPABILITY_CODE_FQDN
:
982 ret
= bgp_capability_hostname(peer
, &caphdr
);
985 if (caphdr
.code
> 128) {
986 /* We don't send Notification for unknown vendor
988 capabilities. It seems reasonable for now...
990 flog_warn(EC_BGP_CAPABILITY_VENDOR
,
991 "%s Vendor specific capability %d",
992 peer
->host
, caphdr
.code
);
995 EC_BGP_CAPABILITY_UNKNOWN
,
996 "%s unrecognized capability code: %d - ignored",
997 peer
->host
, caphdr
.code
);
998 memcpy(*error
, sp
, caphdr
.length
+ 2);
999 *error
+= caphdr
.length
+ 2;
1004 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
1005 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
1008 if (stream_get_getp(s
) != (start
+ caphdr
.length
)) {
1009 if (stream_get_getp(s
) > (start
+ caphdr
.length
))
1011 EC_BGP_CAPABILITY_INVALID_LENGTH
,
1012 "%s Cap-parser for %s read past cap-length, %u!",
1014 lookup_msg(capcode_str
, caphdr
.code
,
1017 stream_set_getp(s
, start
+ caphdr
.length
);
1020 if (!CHECK_FLAG(peer
->cap
, PEER_CAP_RESTART_RCV
)) {
1021 UNSET_FLAG(restart_flag_time
, 0xF000);
1022 peer
->v_gr_restart
= restart_flag_time
;
1028 static int bgp_auth_parse(struct peer
*peer
, size_t length
)
1030 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
1031 BGP_NOTIFY_OPEN_AUTH_FAILURE
);
1035 static bool strict_capability_same(struct peer
*peer
)
1039 for (i
= AFI_IP
; i
< AFI_MAX
; i
++)
1040 for (j
= SAFI_UNICAST
; j
< SAFI_MAX
; j
++)
1041 if (peer
->afc
[i
][j
] != peer
->afc_nego
[i
][j
])
1046 /* peek into option, stores ASN to *as4 if the AS4 capability was found.
1047 * Returns 0 if no as4 found, as4cap value otherwise.
1049 as_t
peek_for_as4_capability(struct peer
*peer
, uint8_t length
)
1051 struct stream
*s
= BGP_INPUT(peer
);
1052 size_t orig_getp
= stream_get_getp(s
);
1053 size_t end
= orig_getp
+ length
;
1056 if (BGP_DEBUG(as4
, AS4
))
1058 "%s [AS4] rcv OPEN w/ OPTION parameter len: %u, peeking for as4",
1059 peer
->host
, length
);
1060 /* the error cases we DONT handle, we ONLY try to read as4 out of
1061 * correctly formatted options.
1063 while (stream_get_getp(s
) < end
) {
1067 /* Check the length. */
1068 if (stream_get_getp(s
) + 2 > end
)
1071 /* Fetch option type and length. */
1072 opt_type
= stream_getc(s
);
1073 opt_length
= stream_getc(s
);
1075 /* Option length check. */
1076 if (stream_get_getp(s
) + opt_length
> end
)
1079 if (opt_type
== BGP_OPEN_OPT_CAP
) {
1080 unsigned long capd_start
= stream_get_getp(s
);
1081 unsigned long capd_end
= capd_start
+ opt_length
;
1083 assert(capd_end
<= end
);
1085 while (stream_get_getp(s
) < capd_end
) {
1086 struct capability_header hdr
;
1088 if (stream_get_getp(s
) + 2 > capd_end
)
1091 hdr
.code
= stream_getc(s
);
1092 hdr
.length
= stream_getc(s
);
1094 if ((stream_get_getp(s
) + hdr
.length
)
1098 if (hdr
.code
== CAPABILITY_CODE_AS4
) {
1099 if (BGP_DEBUG(as4
, AS4
))
1101 "[AS4] found AS4 capability, about to parse");
1102 as4
= bgp_capability_as4(peer
, &hdr
);
1106 stream_forward_getp(s
, hdr
.length
);
1112 stream_set_getp(s
, orig_getp
);
1117 * Parse open option.
1119 * @param[out] mp_capability @see bgp_capability_parse() for semantics.
1121 int bgp_open_option_parse(struct peer
*peer
, uint8_t length
, int *mp_capability
)
1125 uint8_t error_data
[BGP_STANDARD_MESSAGE_MAX_PACKET_SIZE
];
1126 struct stream
*s
= BGP_INPUT(peer
);
1127 size_t end
= stream_get_getp(s
) + length
;
1131 if (bgp_debug_neighbor_events(peer
))
1132 zlog_debug("%s rcv OPEN w/ OPTION parameter len: %u",
1133 peer
->host
, length
);
1135 /* Unset any previously received GR capability. */
1136 UNSET_FLAG(peer
->cap
, PEER_CAP_RESTART_RCV
);
1138 while (stream_get_getp(s
) < end
) {
1142 /* Must have at least an OPEN option header */
1143 if (STREAM_READABLE(s
) < 2) {
1144 zlog_info("%s Option length error", peer
->host
);
1145 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
1146 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
1150 /* Fetch option type and length. */
1151 opt_type
= stream_getc(s
);
1152 opt_length
= stream_getc(s
);
1154 /* Option length check. */
1155 if (STREAM_READABLE(s
) < opt_length
) {
1156 zlog_info("%s Option length error", peer
->host
);
1157 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
1158 BGP_NOTIFY_OPEN_MALFORMED_ATTR
);
1162 if (bgp_debug_neighbor_events(peer
))
1164 "%s rcvd OPEN w/ optional parameter type %u (%s) len %u",
1165 peer
->host
, opt_type
,
1166 opt_type
== BGP_OPEN_OPT_AUTH
1168 : opt_type
== BGP_OPEN_OPT_CAP
1174 case BGP_OPEN_OPT_AUTH
:
1175 ret
= bgp_auth_parse(peer
, opt_length
);
1177 case BGP_OPEN_OPT_CAP
:
1178 ret
= bgp_capability_parse(peer
, opt_length
,
1179 mp_capability
, &error
);
1182 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
1183 BGP_NOTIFY_OPEN_UNSUP_PARAM
);
1188 /* Parse error. To accumulate all unsupported capability codes,
1189 bgp_capability_parse does not return -1 when encounter
1190 unsupported capability code. To detect that, please check
1191 error and erro_data pointer, like below. */
1196 /* All OPEN option is parsed. Check capability when strict compare
1198 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_STRICT_CAP_MATCH
)) {
1199 /* If Unsupported Capability exists. */
1200 if (error
!= error_data
) {
1201 bgp_notify_send_with_data(peer
, BGP_NOTIFY_OPEN_ERR
,
1202 BGP_NOTIFY_OPEN_UNSUP_CAPBL
,
1204 error
- error_data
);
1208 /* Check local capability does not negotiated with remote
1210 if (!strict_capability_same(peer
)) {
1211 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
1212 BGP_NOTIFY_OPEN_UNSUP_CAPBL
);
1217 /* Extended Message Support */
1218 peer
->max_packet_size
=
1219 (CHECK_FLAG(peer
->cap
, PEER_CAP_EXTENDED_MESSAGE_RCV
)
1220 && CHECK_FLAG(peer
->cap
, PEER_CAP_EXTENDED_MESSAGE_ADV
))
1221 ? BGP_EXTENDED_MESSAGE_MAX_PACKET_SIZE
1222 : BGP_STANDARD_MESSAGE_MAX_PACKET_SIZE
;
1224 /* Check there are no common AFI/SAFIs and send Unsupported Capability
1227 && !CHECK_FLAG(peer
->flags
, PEER_FLAG_OVERRIDE_CAPABILITY
)) {
1228 if (!peer
->afc_nego
[AFI_IP
][SAFI_UNICAST
]
1229 && !peer
->afc_nego
[AFI_IP
][SAFI_MULTICAST
]
1230 && !peer
->afc_nego
[AFI_IP
][SAFI_LABELED_UNICAST
]
1231 && !peer
->afc_nego
[AFI_IP
][SAFI_MPLS_VPN
]
1232 && !peer
->afc_nego
[AFI_IP
][SAFI_ENCAP
]
1233 && !peer
->afc_nego
[AFI_IP
][SAFI_FLOWSPEC
]
1234 && !peer
->afc_nego
[AFI_IP6
][SAFI_UNICAST
]
1235 && !peer
->afc_nego
[AFI_IP6
][SAFI_MULTICAST
]
1236 && !peer
->afc_nego
[AFI_IP6
][SAFI_LABELED_UNICAST
]
1237 && !peer
->afc_nego
[AFI_IP6
][SAFI_MPLS_VPN
]
1238 && !peer
->afc_nego
[AFI_IP6
][SAFI_ENCAP
]
1239 && !peer
->afc_nego
[AFI_IP6
][SAFI_FLOWSPEC
]
1240 && !peer
->afc_nego
[AFI_L2VPN
][SAFI_EVPN
]) {
1241 flog_err(EC_BGP_PKT_OPEN
,
1242 "%s [Error] Configured AFI/SAFIs do not overlap with received MP capabilities",
1245 if (error
!= error_data
)
1246 bgp_notify_send_with_data(
1247 peer
, BGP_NOTIFY_OPEN_ERR
,
1248 BGP_NOTIFY_OPEN_UNSUP_CAPBL
, error_data
,
1249 error
- error_data
);
1251 bgp_notify_send(peer
, BGP_NOTIFY_OPEN_ERR
,
1252 BGP_NOTIFY_OPEN_UNSUP_CAPBL
);
1259 static void bgp_open_capability_orf(struct stream
*s
, struct peer
*peer
,
1260 afi_t afi
, safi_t safi
, uint8_t code
)
1266 unsigned long numberp
;
1267 int number_of_orfs
= 0;
1269 iana_safi_t pkt_safi
;
1271 /* Convert AFI, SAFI to values for packet. */
1272 bgp_map_afi_safi_int2iana(afi
, safi
, &pkt_afi
, &pkt_safi
);
1274 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1275 capp
= stream_get_endp(s
); /* Set Capability Len Pointer */
1276 stream_putc(s
, 0); /* Capability Length */
1277 stream_putc(s
, code
); /* Capability Code */
1278 orfp
= stream_get_endp(s
); /* Set ORF Len Pointer */
1279 stream_putc(s
, 0); /* ORF Length */
1280 stream_putw(s
, pkt_afi
);
1282 stream_putc(s
, pkt_safi
);
1283 numberp
= stream_get_endp(s
); /* Set Number Pointer */
1284 stream_putc(s
, 0); /* Number of ORFs */
1286 /* Address Prefix ORF */
1287 if (CHECK_FLAG(peer
->af_flags
[afi
][safi
], PEER_FLAG_ORF_PREFIX_SM
)
1288 || CHECK_FLAG(peer
->af_flags
[afi
][safi
], PEER_FLAG_ORF_PREFIX_RM
)) {
1289 stream_putc(s
, (code
== CAPABILITY_CODE_ORF
1291 : ORF_TYPE_PREFIX_OLD
));
1293 if (CHECK_FLAG(peer
->af_flags
[afi
][safi
],
1294 PEER_FLAG_ORF_PREFIX_SM
)
1295 && CHECK_FLAG(peer
->af_flags
[afi
][safi
],
1296 PEER_FLAG_ORF_PREFIX_RM
)) {
1297 SET_FLAG(peer
->af_cap
[afi
][safi
],
1298 PEER_CAP_ORF_PREFIX_SM_ADV
);
1299 SET_FLAG(peer
->af_cap
[afi
][safi
],
1300 PEER_CAP_ORF_PREFIX_RM_ADV
);
1301 stream_putc(s
, ORF_MODE_BOTH
);
1302 } else if (CHECK_FLAG(peer
->af_flags
[afi
][safi
],
1303 PEER_FLAG_ORF_PREFIX_SM
)) {
1304 SET_FLAG(peer
->af_cap
[afi
][safi
],
1305 PEER_CAP_ORF_PREFIX_SM_ADV
);
1306 stream_putc(s
, ORF_MODE_SEND
);
1308 SET_FLAG(peer
->af_cap
[afi
][safi
],
1309 PEER_CAP_ORF_PREFIX_RM_ADV
);
1310 stream_putc(s
, ORF_MODE_RECEIVE
);
1315 /* Total Number of ORFs. */
1316 stream_putc_at(s
, numberp
, number_of_orfs
);
1318 /* Total ORF Len. */
1319 orf_len
= stream_get_endp(s
) - orfp
- 1;
1320 stream_putc_at(s
, orfp
, orf_len
);
1322 /* Total Capability Len. */
1323 cap_len
= stream_get_endp(s
) - capp
- 1;
1324 stream_putc_at(s
, capp
, cap_len
);
1327 static void bgp_peer_send_gr_capability(struct stream
*s
, struct peer
*peer
,
1334 iana_safi_t pkt_safi
;
1335 uint32_t restart_time
;
1336 unsigned long capp
= 0;
1337 unsigned long rcapp
= 0;
1339 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_GRACEFUL_RESTART
)
1340 && !CHECK_FLAG(peer
->flags
, PEER_FLAG_GRACEFUL_RESTART_HELPER
))
1343 if (BGP_DEBUG(graceful_restart
, GRACEFUL_RESTART
))
1344 zlog_debug("[BGP_GR] Sending helper Capability for Peer :%s :",
1347 SET_FLAG(peer
->cap
, PEER_CAP_RESTART_ADV
);
1348 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1349 capp
= stream_get_endp(s
); /* Set Capability Len Pointer */
1350 stream_putc(s
, 0); /* Capability Length */
1351 stream_putc(s
, CAPABILITY_CODE_RESTART
);
1352 /* Set Restart Capability Len Pointer */
1353 rcapp
= stream_get_endp(s
);
1355 restart_time
= peer
->bgp
->restart_time
;
1356 if (peer
->bgp
->t_startup
) {
1357 SET_FLAG(restart_time
, RESTART_R_BIT
);
1358 SET_FLAG(peer
->cap
, PEER_CAP_RESTART_BIT_ADV
);
1360 if (BGP_DEBUG(graceful_restart
, GRACEFUL_RESTART
))
1361 zlog_debug("[BGP_GR] Sending R-Bit for Peer :%s :",
1365 stream_putw(s
, restart_time
);
1367 /* Send address-family specific graceful-restart capability
1368 * only when GR config is present
1370 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_GRACEFUL_RESTART
)) {
1371 if (CHECK_FLAG(peer
->bgp
->flags
, BGP_FLAG_GR_PRESERVE_FWD
)
1372 && BGP_DEBUG(graceful_restart
, GRACEFUL_RESTART
))
1373 zlog_debug("[BGP_GR] F bit Set");
1375 FOREACH_AFI_SAFI (afi
, safi
) {
1376 if (!peer
->afc
[afi
][safi
])
1379 if (BGP_DEBUG(graceful_restart
, GRACEFUL_RESTART
))
1381 "[BGP_GR] Sending GR Capability for AFI :%d :, SAFI :%d:",
1384 /* Convert AFI, SAFI to values for
1387 bgp_map_afi_safi_int2iana(afi
, safi
, &pkt_afi
,
1389 stream_putw(s
, pkt_afi
);
1390 stream_putc(s
, pkt_safi
);
1391 if (CHECK_FLAG(peer
->bgp
->flags
,
1392 BGP_FLAG_GR_PRESERVE_FWD
))
1393 stream_putc(s
, RESTART_F_BIT
);
1399 /* Total Graceful restart capability Len. */
1400 len
= stream_get_endp(s
) - rcapp
- 1;
1401 stream_putc_at(s
, rcapp
, len
);
1403 /* Total Capability Len. */
1404 len
= stream_get_endp(s
) - capp
- 1;
1405 stream_putc_at(s
, capp
, len
);
1408 /* Fill in capability open option to the packet. */
1409 void bgp_open_capability(struct stream
*s
, struct peer
*peer
)
1412 unsigned long cp
, capp
, rcapp
;
1416 iana_safi_t pkt_safi
;
1418 uint8_t afi_safi_count
= 0;
1419 int adv_addpath_tx
= 0;
1421 /* Remember current pointer for Opt Parm Len. */
1422 cp
= stream_get_endp(s
);
1427 /* Do not send capability. */
1428 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_CAPABILITY_OPEN
)
1429 || CHECK_FLAG(peer
->flags
, PEER_FLAG_DONT_CAPABILITY
))
1432 /* MP capability for configured AFI, SAFI */
1433 FOREACH_AFI_SAFI (afi
, safi
) {
1434 if (peer
->afc
[afi
][safi
]) {
1435 /* Convert AFI, SAFI to values for packet. */
1436 bgp_map_afi_safi_int2iana(afi
, safi
, &pkt_afi
,
1439 peer
->afc_adv
[afi
][safi
] = 1;
1440 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1441 stream_putc(s
, CAPABILITY_CODE_MP_LEN
+ 2);
1442 stream_putc(s
, CAPABILITY_CODE_MP
);
1443 stream_putc(s
, CAPABILITY_CODE_MP_LEN
);
1444 stream_putw(s
, pkt_afi
);
1446 stream_putc(s
, pkt_safi
);
1448 /* Extended nexthop capability - currently
1449 * supporting RFC-5549 for
1450 * Link-Local peering only
1452 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_CAPABILITY_ENHE
)
1453 && peer
->su
.sa
.sa_family
== AF_INET6
1455 && (safi
== SAFI_UNICAST
|| safi
== SAFI_MPLS_VPN
1456 || safi
== SAFI_LABELED_UNICAST
)) {
1457 /* RFC 5549 Extended Next Hop Encoding
1459 SET_FLAG(peer
->cap
, PEER_CAP_ENHE_ADV
);
1460 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1461 stream_putc(s
, CAPABILITY_CODE_ENHE_LEN
+ 2);
1462 stream_putc(s
, CAPABILITY_CODE_ENHE
);
1463 stream_putc(s
, CAPABILITY_CODE_ENHE_LEN
);
1465 SET_FLAG(peer
->af_cap
[AFI_IP
][safi
],
1466 PEER_CAP_ENHE_AF_ADV
);
1467 stream_putw(s
, pkt_afi
);
1468 stream_putw(s
, pkt_safi
);
1469 stream_putw(s
, afi_int2iana(AFI_IP6
));
1471 if (CHECK_FLAG(peer
->af_cap
[afi
][safi
],
1472 PEER_CAP_ENHE_AF_RCV
))
1473 SET_FLAG(peer
->af_cap
[afi
][safi
],
1474 PEER_CAP_ENHE_AF_NEGO
);
1479 /* Route refresh. */
1480 SET_FLAG(peer
->cap
, PEER_CAP_REFRESH_ADV
);
1481 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1482 stream_putc(s
, CAPABILITY_CODE_REFRESH_LEN
+ 2);
1483 stream_putc(s
, CAPABILITY_CODE_REFRESH_OLD
);
1484 stream_putc(s
, CAPABILITY_CODE_REFRESH_LEN
);
1485 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1486 stream_putc(s
, CAPABILITY_CODE_REFRESH_LEN
+ 2);
1487 stream_putc(s
, CAPABILITY_CODE_REFRESH
);
1488 stream_putc(s
, CAPABILITY_CODE_REFRESH_LEN
);
1490 /* Enhanced Route Refresh. */
1491 SET_FLAG(peer
->cap
, PEER_CAP_ENHANCED_RR_ADV
);
1492 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1493 stream_putc(s
, CAPABILITY_CODE_ENHANCED_LEN
+ 2);
1494 stream_putc(s
, CAPABILITY_CODE_ENHANCED_RR
);
1495 stream_putc(s
, CAPABILITY_CODE_ENHANCED_LEN
);
1498 SET_FLAG(peer
->cap
, PEER_CAP_AS4_ADV
);
1499 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1500 stream_putc(s
, CAPABILITY_CODE_AS4_LEN
+ 2);
1501 stream_putc(s
, CAPABILITY_CODE_AS4
);
1502 stream_putc(s
, CAPABILITY_CODE_AS4_LEN
);
1503 if (peer
->change_local_as
)
1504 local_as
= peer
->change_local_as
;
1506 local_as
= peer
->local_as
;
1507 stream_putl(s
, local_as
);
1509 /* Extended Message Support */
1510 SET_FLAG(peer
->cap
, PEER_CAP_EXTENDED_MESSAGE_ADV
);
1511 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1512 stream_putc(s
, CAPABILITY_CODE_EXT_MESSAGE_LEN
+ 2);
1513 stream_putc(s
, CAPABILITY_CODE_EXT_MESSAGE
);
1514 stream_putc(s
, CAPABILITY_CODE_EXT_MESSAGE_LEN
);
1517 FOREACH_AFI_SAFI (afi
, safi
) {
1518 if (peer
->afc
[afi
][safi
]) {
1521 /* Only advertise addpath TX if a feature that
1524 if (peer
->addpath_type
[afi
][safi
] != BGP_ADDPATH_NONE
)
1529 SET_FLAG(peer
->cap
, PEER_CAP_ADDPATH_ADV
);
1530 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1531 stream_putc(s
, (CAPABILITY_CODE_ADDPATH_LEN
* afi_safi_count
) + 2);
1532 stream_putc(s
, CAPABILITY_CODE_ADDPATH
);
1533 stream_putc(s
, CAPABILITY_CODE_ADDPATH_LEN
* afi_safi_count
);
1535 FOREACH_AFI_SAFI (afi
, safi
) {
1536 if (peer
->afc
[afi
][safi
]) {
1537 /* Convert AFI, SAFI to values for packet. */
1538 bgp_map_afi_safi_int2iana(afi
, safi
, &pkt_afi
,
1541 stream_putw(s
, pkt_afi
);
1542 stream_putc(s
, pkt_safi
);
1544 if (adv_addpath_tx
) {
1545 stream_putc(s
, BGP_ADDPATH_RX
| BGP_ADDPATH_TX
);
1546 SET_FLAG(peer
->af_cap
[afi
][safi
],
1547 PEER_CAP_ADDPATH_AF_RX_ADV
);
1548 SET_FLAG(peer
->af_cap
[afi
][safi
],
1549 PEER_CAP_ADDPATH_AF_TX_ADV
);
1551 stream_putc(s
, BGP_ADDPATH_RX
);
1552 SET_FLAG(peer
->af_cap
[afi
][safi
],
1553 PEER_CAP_ADDPATH_AF_RX_ADV
);
1554 UNSET_FLAG(peer
->af_cap
[afi
][safi
],
1555 PEER_CAP_ADDPATH_AF_TX_ADV
);
1560 /* ORF capability. */
1561 FOREACH_AFI_SAFI (afi
, safi
) {
1562 if (CHECK_FLAG(peer
->af_flags
[afi
][safi
],
1563 PEER_FLAG_ORF_PREFIX_SM
)
1564 || CHECK_FLAG(peer
->af_flags
[afi
][safi
],
1565 PEER_FLAG_ORF_PREFIX_RM
)) {
1566 bgp_open_capability_orf(s
, peer
, afi
, safi
,
1567 CAPABILITY_CODE_ORF_OLD
);
1568 bgp_open_capability_orf(s
, peer
, afi
, safi
,
1569 CAPABILITY_CODE_ORF
);
1573 /* Dynamic capability. */
1574 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_DYNAMIC_CAPABILITY
)) {
1575 SET_FLAG(peer
->cap
, PEER_CAP_DYNAMIC_ADV
);
1576 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1577 stream_putc(s
, CAPABILITY_CODE_DYNAMIC_LEN
+ 2);
1578 stream_putc(s
, CAPABILITY_CODE_DYNAMIC_OLD
);
1579 stream_putc(s
, CAPABILITY_CODE_DYNAMIC_LEN
);
1580 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1581 stream_putc(s
, CAPABILITY_CODE_DYNAMIC_LEN
+ 2);
1582 stream_putc(s
, CAPABILITY_CODE_DYNAMIC
);
1583 stream_putc(s
, CAPABILITY_CODE_DYNAMIC_LEN
);
1586 /* Hostname capability */
1587 if (cmd_hostname_get()) {
1588 SET_FLAG(peer
->cap
, PEER_CAP_HOSTNAME_ADV
);
1589 stream_putc(s
, BGP_OPEN_OPT_CAP
);
1590 rcapp
= stream_get_endp(s
); /* Ptr to length placeholder */
1591 stream_putc(s
, 0); /* dummy len for now */
1592 stream_putc(s
, CAPABILITY_CODE_FQDN
);
1593 capp
= stream_get_endp(s
);
1594 stream_putc(s
, 0); /* dummy len for now */
1595 len
= strlen(cmd_hostname_get());
1596 if (len
> BGP_MAX_HOSTNAME
)
1597 len
= BGP_MAX_HOSTNAME
;
1599 stream_putc(s
, len
);
1600 stream_put(s
, cmd_hostname_get(), len
);
1601 if (cmd_domainname_get()) {
1602 len
= strlen(cmd_domainname_get());
1603 if (len
> BGP_MAX_HOSTNAME
)
1604 len
= BGP_MAX_HOSTNAME
;
1606 stream_putc(s
, len
);
1607 stream_put(s
, cmd_domainname_get(), len
);
1609 stream_putc(s
, 0); /* 0 length */
1611 /* Set the lengths straight */
1612 len
= stream_get_endp(s
) - rcapp
- 1;
1613 stream_putc_at(s
, rcapp
, len
);
1614 len
= stream_get_endp(s
) - capp
- 1;
1615 stream_putc_at(s
, capp
, len
);
1617 if (bgp_debug_neighbor_events(peer
))
1619 "%s Sending hostname cap with hn = %s, dn = %s",
1620 peer
->host
, cmd_hostname_get(),
1621 cmd_domainname_get());
1624 bgp_peer_send_gr_capability(s
, peer
, cp
);
1626 /* Total Opt Parm Len. */
1627 len
= stream_get_endp(s
) - cp
- 1;
1628 stream_putc_at(s
, cp
, len
);