1 /* BGP-4, BGP-4+ daemon program
2 * Copyright (C) 1996, 97, 98, 99, 2000 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
29 #include "sockunion.h"
38 #include "workqueue.h"
46 #include "frr_pthread.h"
49 #include "bgpd/bgpd.h"
50 #include "bgpd/bgp_table.h"
51 #include "bgpd/bgp_aspath.h"
52 #include "bgpd/bgp_route.h"
53 #include "bgpd/bgp_dump.h"
54 #include "bgpd/bgp_debug.h"
55 #include "bgpd/bgp_errors.h"
56 #include "bgpd/bgp_community.h"
57 #include "bgpd/bgp_attr.h"
58 #include "bgpd/bgp_regex.h"
59 #include "bgpd/bgp_clist.h"
60 #include "bgpd/bgp_fsm.h"
61 #include "bgpd/bgp_packet.h"
62 #include "bgpd/bgp_zebra.h"
63 #include "bgpd/bgp_open.h"
64 #include "bgpd/bgp_filter.h"
65 #include "bgpd/bgp_nexthop.h"
66 #include "bgpd/bgp_damp.h"
67 #include "bgpd/bgp_mplsvpn.h"
69 #include "bgpd/rfapi/bgp_rfapi_cfg.h"
70 #include "bgpd/rfapi/rfapi_backend.h"
72 #include "bgpd/bgp_evpn.h"
73 #include "bgpd/bgp_advertise.h"
74 #include "bgpd/bgp_network.h"
75 #include "bgpd/bgp_vty.h"
76 #include "bgpd/bgp_mpath.h"
77 #include "bgpd/bgp_nht.h"
78 #include "bgpd/bgp_updgrp.h"
79 #include "bgpd/bgp_bfd.h"
80 #include "bgpd/bgp_memory.h"
81 #include "bgpd/bgp_evpn_vty.h"
82 #include "bgpd/bgp_keepalives.h"
83 #include "bgpd/bgp_io.h"
84 #include "bgpd/bgp_ecommunity.h"
85 #include "bgpd/bgp_flowspec.h"
86 #include "bgpd/bgp_labelpool.h"
87 #include "bgpd/bgp_pbr.h"
88 #include "bgpd/bgp_addpath.h"
90 DEFINE_MTYPE_STATIC(BGPD
, PEER_TX_SHUTDOWN_MSG
, "Peer shutdown message (TX)");
91 DEFINE_QOBJ_TYPE(bgp_master
)
93 DEFINE_QOBJ_TYPE(peer
)
95 /* BGP process wide configuration. */
96 static struct bgp_master bgp_master
;
98 /* BGP process wide configuration pointer to export. */
99 struct bgp_master
*bm
;
101 /* BGP community-list. */
102 struct community_list_handler
*bgp_clist
;
104 unsigned int multipath_num
= MULTIPATH_NUM
;
106 static void bgp_if_finish(struct bgp
*bgp
);
107 static void peer_drop_dynamic_neighbor(struct peer
*peer
);
109 extern struct zclient
*zclient
;
111 /* handle main socket creation or deletion */
112 static int bgp_check_main_socket(bool create
, struct bgp
*bgp
)
114 static int bgp_server_main_created
;
116 if (create
== true) {
117 if (bgp_server_main_created
)
119 if (bgp_socket(bgp
, bm
->port
, bm
->address
) < 0)
120 return BGP_ERR_INVALID_VALUE
;
121 bgp_server_main_created
= 1;
124 if (!bgp_server_main_created
)
127 bgp_server_main_created
= 0;
131 void bgp_session_reset(struct peer
*peer
)
133 if (peer
->doppelganger
&& (peer
->doppelganger
->status
!= Deleted
)
134 && !(CHECK_FLAG(peer
->doppelganger
->flags
, PEER_FLAG_CONFIG_NODE
)))
135 peer_delete(peer
->doppelganger
);
137 BGP_EVENT_ADD(peer
, BGP_Stop
);
141 * During session reset, we may delete the doppelganger peer, which would
142 * be the next node to the current node. If the session reset was invoked
143 * during walk of peer list, we would end up accessing the freed next
144 * node. This function moves the next node along.
146 static void bgp_session_reset_safe(struct peer
*peer
, struct listnode
**nnode
)
151 n
= (nnode
) ? *nnode
: NULL
;
152 npeer
= (n
) ? listgetdata(n
) : NULL
;
154 if (peer
->doppelganger
&& (peer
->doppelganger
->status
!= Deleted
)
155 && !(CHECK_FLAG(peer
->doppelganger
->flags
,
156 PEER_FLAG_CONFIG_NODE
))) {
157 if (peer
->doppelganger
== npeer
)
158 /* nnode and *nnode are confirmed to be non-NULL here */
159 *nnode
= (*nnode
)->next
;
160 peer_delete(peer
->doppelganger
);
163 BGP_EVENT_ADD(peer
, BGP_Stop
);
166 /* BGP global flag manipulation. */
167 int bgp_option_set(int flag
)
171 case BGP_OPT_MULTIPLE_INSTANCE
:
172 case BGP_OPT_CONFIG_CISCO
:
173 case BGP_OPT_NO_LISTEN
:
174 case BGP_OPT_NO_ZEBRA
:
175 SET_FLAG(bm
->options
, flag
);
178 return BGP_ERR_INVALID_FLAG
;
183 int bgp_option_unset(int flag
)
186 case BGP_OPT_MULTIPLE_INSTANCE
:
187 if (listcount(bm
->bgp
) > 1)
188 return BGP_ERR_MULTIPLE_INSTANCE_USED
;
190 case BGP_OPT_NO_ZEBRA
:
192 case BGP_OPT_CONFIG_CISCO
:
193 UNSET_FLAG(bm
->options
, flag
);
196 return BGP_ERR_INVALID_FLAG
;
201 int bgp_option_check(int flag
)
203 return CHECK_FLAG(bm
->options
, flag
);
206 /* BGP flag manipulation. */
207 int bgp_flag_set(struct bgp
*bgp
, int flag
)
209 SET_FLAG(bgp
->flags
, flag
);
213 int bgp_flag_unset(struct bgp
*bgp
, int flag
)
215 UNSET_FLAG(bgp
->flags
, flag
);
219 int bgp_flag_check(struct bgp
*bgp
, int flag
)
221 return CHECK_FLAG(bgp
->flags
, flag
);
224 /* Internal function to set BGP structure configureation flag. */
225 static void bgp_config_set(struct bgp
*bgp
, int config
)
227 SET_FLAG(bgp
->config
, config
);
230 static void bgp_config_unset(struct bgp
*bgp
, int config
)
232 UNSET_FLAG(bgp
->config
, config
);
235 static int bgp_config_check(struct bgp
*bgp
, int config
)
237 return CHECK_FLAG(bgp
->config
, config
);
240 /* Set BGP router identifier. */
241 static int bgp_router_id_set(struct bgp
*bgp
, const struct in_addr
*id
)
244 struct listnode
*node
, *nnode
;
246 if (IPV4_ADDR_SAME(&bgp
->router_id
, id
))
249 /* EVPN uses router id in RD, withdraw them */
250 if (is_evpn_enabled())
251 bgp_evpn_handle_router_id_update(bgp
, TRUE
);
253 IPV4_ADDR_COPY(&bgp
->router_id
, id
);
255 /* Set all peer's local identifier with this value. */
256 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
257 IPV4_ADDR_COPY(&peer
->local_id
, id
);
259 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
260 peer
->last_reset
= PEER_DOWN_RID_CHANGE
;
261 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
262 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
266 /* EVPN uses router id in RD, update them */
267 if (is_evpn_enabled())
268 bgp_evpn_handle_router_id_update(bgp
, FALSE
);
273 void bgp_router_id_zebra_bump(vrf_id_t vrf_id
, const struct prefix
*router_id
)
275 struct listnode
*node
, *nnode
;
277 struct in_addr
*addr
= NULL
;
279 if (router_id
!= NULL
)
280 addr
= (struct in_addr
*)&(router_id
->u
.prefix4
);
282 if (vrf_id
== VRF_DEFAULT
) {
283 /* Router-id change for default VRF has to also update all
285 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
)) {
286 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
)
290 bgp
->router_id_zebra
= *addr
;
292 addr
= &bgp
->router_id_zebra
;
294 if (!bgp
->router_id_static
.s_addr
) {
295 /* Router ID is updated if there are no active
298 if (bgp
->established_peers
== 0) {
299 if (BGP_DEBUG(zebra
, ZEBRA
))
300 zlog_debug("RID change : vrf %u, RTR ID %s",
301 bgp
->vrf_id
, inet_ntoa(*addr
));
302 bgp_router_id_set(bgp
, addr
);
307 bgp
= bgp_lookup_by_vrf_id(vrf_id
);
310 bgp
->router_id_zebra
= *addr
;
312 addr
= &bgp
->router_id_zebra
;
314 if (!bgp
->router_id_static
.s_addr
) {
315 /* Router ID is updated if there are no active
318 if (bgp
->established_peers
== 0) {
319 if (BGP_DEBUG(zebra
, ZEBRA
))
320 zlog_debug("RID change : vrf %u, RTR ID %s",
321 bgp
->vrf_id
, inet_ntoa(*addr
));
322 bgp_router_id_set(bgp
, addr
);
330 int bgp_router_id_static_set(struct bgp
*bgp
, struct in_addr id
)
332 bgp
->router_id_static
= id
;
333 bgp_router_id_set(bgp
, id
.s_addr
? &id
: &bgp
->router_id_zebra
);
337 /* BGP's cluster-id control. */
338 int bgp_cluster_id_set(struct bgp
*bgp
, struct in_addr
*cluster_id
)
341 struct listnode
*node
, *nnode
;
343 if (bgp_config_check(bgp
, BGP_CONFIG_CLUSTER_ID
)
344 && IPV4_ADDR_SAME(&bgp
->cluster_id
, cluster_id
))
347 IPV4_ADDR_COPY(&bgp
->cluster_id
, cluster_id
);
348 bgp_config_set(bgp
, BGP_CONFIG_CLUSTER_ID
);
350 /* Clear all IBGP peer. */
351 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
352 if (peer
->sort
!= BGP_PEER_IBGP
)
355 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
356 peer
->last_reset
= PEER_DOWN_CLID_CHANGE
;
357 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
358 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
364 int bgp_cluster_id_unset(struct bgp
*bgp
)
367 struct listnode
*node
, *nnode
;
369 if (!bgp_config_check(bgp
, BGP_CONFIG_CLUSTER_ID
))
372 bgp
->cluster_id
.s_addr
= 0;
373 bgp_config_unset(bgp
, BGP_CONFIG_CLUSTER_ID
);
375 /* Clear all IBGP peer. */
376 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
377 if (peer
->sort
!= BGP_PEER_IBGP
)
380 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
381 peer
->last_reset
= PEER_DOWN_CLID_CHANGE
;
382 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
383 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
389 /* time_t value that is monotonicly increasing
390 * and uneffected by adjustments to system clock
392 time_t bgp_clock(void)
400 /* BGP timer configuration. */
401 int bgp_timers_set(struct bgp
*bgp
, uint32_t keepalive
, uint32_t holdtime
)
403 bgp
->default_keepalive
=
404 (keepalive
< holdtime
/ 3 ? keepalive
: holdtime
/ 3);
405 bgp
->default_holdtime
= holdtime
;
410 int bgp_timers_unset(struct bgp
*bgp
)
412 bgp
->default_keepalive
= BGP_DEFAULT_KEEPALIVE
;
413 bgp
->default_holdtime
= BGP_DEFAULT_HOLDTIME
;
418 /* BGP confederation configuration. */
419 int bgp_confederation_id_set(struct bgp
*bgp
, as_t as
)
422 struct listnode
*node
, *nnode
;
426 return BGP_ERR_INVALID_AS
;
428 /* Remember - were we doing confederation before? */
429 already_confed
= bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
);
431 bgp_config_set(bgp
, BGP_CONFIG_CONFEDERATION
);
433 /* If we were doing confederation already, this is just an external
434 AS change. Just Reset EBGP sessions, not CONFED sessions. If we
435 were not doing confederation before, reset all EBGP sessions. */
436 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
437 /* We're looking for peers who's AS is not local or part of our
439 if (already_confed
) {
440 if (peer_sort(peer
) == BGP_PEER_EBGP
) {
442 if (BGP_IS_VALID_STATE_FOR_NOTIF(
445 PEER_DOWN_CONFED_ID_CHANGE
;
447 peer
, BGP_NOTIFY_CEASE
,
448 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
450 bgp_session_reset_safe(peer
, &nnode
);
453 /* Not doign confederation before, so reset every
456 if (peer_sort(peer
) != BGP_PEER_IBGP
) {
457 /* Reset the local_as to be our EBGP one */
458 if (peer_sort(peer
) == BGP_PEER_EBGP
)
460 if (BGP_IS_VALID_STATE_FOR_NOTIF(
463 PEER_DOWN_CONFED_ID_CHANGE
;
465 peer
, BGP_NOTIFY_CEASE
,
466 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
468 bgp_session_reset_safe(peer
, &nnode
);
475 int bgp_confederation_id_unset(struct bgp
*bgp
)
478 struct listnode
*node
, *nnode
;
481 bgp_config_unset(bgp
, BGP_CONFIG_CONFEDERATION
);
483 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
484 /* We're looking for peers who's AS is not local */
485 if (peer_sort(peer
) != BGP_PEER_IBGP
) {
486 peer
->local_as
= bgp
->as
;
487 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
488 peer
->last_reset
= PEER_DOWN_CONFED_ID_CHANGE
;
489 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
490 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
494 bgp_session_reset_safe(peer
, &nnode
);
500 /* Is an AS part of the confed or not? */
501 int bgp_confederation_peers_check(struct bgp
*bgp
, as_t as
)
508 for (i
= 0; i
< bgp
->confed_peers_cnt
; i
++)
509 if (bgp
->confed_peers
[i
] == as
)
515 /* Add an AS to the confederation set. */
516 int bgp_confederation_peers_add(struct bgp
*bgp
, as_t as
)
519 struct listnode
*node
, *nnode
;
522 return BGP_ERR_INVALID_BGP
;
525 return BGP_ERR_INVALID_AS
;
527 if (bgp_confederation_peers_check(bgp
, as
))
530 if (bgp
->confed_peers
)
532 XREALLOC(MTYPE_BGP_CONFED_LIST
, bgp
->confed_peers
,
533 (bgp
->confed_peers_cnt
+ 1) * sizeof(as_t
));
536 XMALLOC(MTYPE_BGP_CONFED_LIST
,
537 (bgp
->confed_peers_cnt
+ 1) * sizeof(as_t
));
539 bgp
->confed_peers
[bgp
->confed_peers_cnt
] = as
;
540 bgp
->confed_peers_cnt
++;
542 if (bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
)) {
543 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
544 if (peer
->as
== as
) {
545 peer
->local_as
= bgp
->as
;
546 if (BGP_IS_VALID_STATE_FOR_NOTIF(
549 PEER_DOWN_CONFED_PEER_CHANGE
;
551 peer
, BGP_NOTIFY_CEASE
,
552 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
554 bgp_session_reset_safe(peer
, &nnode
);
561 /* Delete an AS from the confederation set. */
562 int bgp_confederation_peers_remove(struct bgp
*bgp
, as_t as
)
567 struct listnode
*node
, *nnode
;
572 if (!bgp_confederation_peers_check(bgp
, as
))
575 for (i
= 0; i
< bgp
->confed_peers_cnt
; i
++)
576 if (bgp
->confed_peers
[i
] == as
)
577 for (j
= i
+ 1; j
< bgp
->confed_peers_cnt
; j
++)
578 bgp
->confed_peers
[j
- 1] = bgp
->confed_peers
[j
];
580 bgp
->confed_peers_cnt
--;
582 if (bgp
->confed_peers_cnt
== 0) {
583 if (bgp
->confed_peers
)
584 XFREE(MTYPE_BGP_CONFED_LIST
, bgp
->confed_peers
);
585 bgp
->confed_peers
= NULL
;
588 XREALLOC(MTYPE_BGP_CONFED_LIST
, bgp
->confed_peers
,
589 bgp
->confed_peers_cnt
* sizeof(as_t
));
591 /* Now reset any peer who's remote AS has just been removed from the
593 if (bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
)) {
594 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
595 if (peer
->as
== as
) {
596 peer
->local_as
= bgp
->confed_id
;
597 if (BGP_IS_VALID_STATE_FOR_NOTIF(
600 PEER_DOWN_CONFED_PEER_CHANGE
;
602 peer
, BGP_NOTIFY_CEASE
,
603 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
605 bgp_session_reset_safe(peer
, &nnode
);
613 /* Local preference configuration. */
614 int bgp_default_local_preference_set(struct bgp
*bgp
, uint32_t local_pref
)
619 bgp
->default_local_pref
= local_pref
;
624 int bgp_default_local_preference_unset(struct bgp
*bgp
)
629 bgp
->default_local_pref
= BGP_DEFAULT_LOCAL_PREF
;
634 /* Local preference configuration. */
635 int bgp_default_subgroup_pkt_queue_max_set(struct bgp
*bgp
, uint32_t queue_size
)
640 bgp
->default_subgroup_pkt_queue_max
= queue_size
;
645 int bgp_default_subgroup_pkt_queue_max_unset(struct bgp
*bgp
)
649 bgp
->default_subgroup_pkt_queue_max
=
650 BGP_DEFAULT_SUBGROUP_PKT_QUEUE_MAX
;
655 /* Listen limit configuration. */
656 int bgp_listen_limit_set(struct bgp
*bgp
, int listen_limit
)
661 bgp
->dynamic_neighbors_limit
= listen_limit
;
666 int bgp_listen_limit_unset(struct bgp
*bgp
)
671 bgp
->dynamic_neighbors_limit
= BGP_DYNAMIC_NEIGHBORS_LIMIT_DEFAULT
;
676 int bgp_map_afi_safi_iana2int(iana_afi_t pkt_afi
, iana_safi_t pkt_safi
,
677 afi_t
*afi
, safi_t
*safi
)
679 /* Map from IANA values to internal values, return error if
680 * values are unrecognized.
682 *afi
= afi_iana2int(pkt_afi
);
683 *safi
= safi_iana2int(pkt_safi
);
684 if (*afi
== AFI_MAX
|| *safi
== SAFI_MAX
)
690 int bgp_map_afi_safi_int2iana(afi_t afi
, safi_t safi
, iana_afi_t
*pkt_afi
,
691 iana_safi_t
*pkt_safi
)
693 /* Map from internal values to IANA values, return error if
694 * internal values are bad (unexpected).
696 if (afi
== AFI_MAX
|| safi
== SAFI_MAX
)
698 *pkt_afi
= afi_int2iana(afi
);
699 *pkt_safi
= safi_int2iana(safi
);
703 struct peer_af
*peer_af_create(struct peer
*peer
, afi_t afi
, safi_t safi
)
711 afid
= afindex(afi
, safi
);
712 if (afid
>= BGP_AF_MAX
)
715 assert(peer
->peer_af_array
[afid
] == NULL
);
717 /* Allocate new peer af */
718 af
= XCALLOC(MTYPE_BGP_PEER_AF
, sizeof(struct peer_af
));
720 peer
->peer_af_array
[afid
] = af
;
729 struct peer_af
*peer_af_find(struct peer
*peer
, afi_t afi
, safi_t safi
)
736 afid
= afindex(afi
, safi
);
737 if (afid
>= BGP_AF_MAX
)
740 return peer
->peer_af_array
[afid
];
743 int peer_af_delete(struct peer
*peer
, afi_t afi
, safi_t safi
)
751 afid
= afindex(afi
, safi
);
752 if (afid
>= BGP_AF_MAX
)
755 af
= peer
->peer_af_array
[afid
];
759 bgp_stop_announce_route_timer(af
);
761 if (PAF_SUBGRP(af
)) {
762 if (BGP_DEBUG(update_groups
, UPDATE_GROUPS
))
763 zlog_debug("u%" PRIu64
":s%" PRIu64
" remove peer %s",
764 af
->subgroup
->update_group
->id
,
765 af
->subgroup
->id
, peer
->host
);
768 update_subgroup_remove_peer(af
->subgroup
, af
);
770 peer
->peer_af_array
[afid
] = NULL
;
771 XFREE(MTYPE_BGP_PEER_AF
, af
);
775 /* Peer comparison function for sorting. */
776 int peer_cmp(struct peer
*p1
, struct peer
*p2
)
778 if (p1
->group
&& !p2
->group
)
781 if (!p1
->group
&& p2
->group
)
784 if (p1
->group
== p2
->group
) {
785 if (p1
->conf_if
&& !p2
->conf_if
)
788 if (!p1
->conf_if
&& p2
->conf_if
)
791 if (p1
->conf_if
&& p2
->conf_if
)
792 return if_cmp_name_func(p1
->conf_if
, p2
->conf_if
);
794 return strcmp(p1
->group
->name
, p2
->group
->name
);
796 return sockunion_cmp(&p1
->su
, &p2
->su
);
799 static unsigned int peer_hash_key_make(void *p
)
801 struct peer
*peer
= p
;
802 return sockunion_hash(&peer
->su
);
805 static bool peer_hash_same(const void *p1
, const void *p2
)
807 const struct peer
*peer1
= p1
;
808 const struct peer
*peer2
= p2
;
809 return (sockunion_same(&peer1
->su
, &peer2
->su
)
810 && CHECK_FLAG(peer1
->flags
, PEER_FLAG_CONFIG_NODE
)
811 == CHECK_FLAG(peer2
->flags
, PEER_FLAG_CONFIG_NODE
));
814 void peer_flag_inherit(struct peer
*peer
, uint32_t flag
)
818 /* Skip if peer is not a peer-group member. */
819 if (!peer_group_active(peer
))
822 /* Unset override flag to signal inheritance from peer-group. */
823 UNSET_FLAG(peer
->flags_override
, flag
);
826 * Inherit flag state from peer-group. If the flag of the peer-group is
827 * not being inverted, the peer must inherit the inverse of the current
828 * peer-group flag state.
830 group_val
= CHECK_FLAG(peer
->group
->conf
->flags
, flag
);
831 if (!CHECK_FLAG(peer
->group
->conf
->flags_invert
, flag
)
832 && CHECK_FLAG(peer
->flags_invert
, flag
))
833 COND_FLAG(peer
->flags
, flag
, !group_val
);
835 COND_FLAG(peer
->flags
, flag
, group_val
);
838 int peer_af_flag_check(struct peer
*peer
, afi_t afi
, safi_t safi
, uint32_t flag
)
840 return CHECK_FLAG(peer
->af_flags
[afi
][safi
], flag
);
843 void peer_af_flag_inherit(struct peer
*peer
, afi_t afi
, safi_t safi
,
848 /* Skip if peer is not a peer-group member. */
849 if (!peer_group_active(peer
))
852 /* Unset override flag to signal inheritance from peer-group. */
853 UNSET_FLAG(peer
->af_flags_override
[afi
][safi
], flag
);
856 * Inherit flag state from peer-group. If the flag of the peer-group is
857 * not being inverted, the peer must inherit the inverse of the current
858 * peer-group flag state.
860 group_val
= CHECK_FLAG(peer
->group
->conf
->af_flags
[afi
][safi
], flag
);
861 if (!CHECK_FLAG(peer
->group
->conf
->af_flags_invert
[afi
][safi
], flag
)
862 && CHECK_FLAG(peer
->af_flags_invert
[afi
][safi
], flag
))
863 COND_FLAG(peer
->af_flags
[afi
][safi
], flag
, !group_val
);
865 COND_FLAG(peer
->af_flags
[afi
][safi
], flag
, group_val
);
868 static bool peergroup_flag_check(struct peer
*peer
, uint32_t flag
)
870 if (!peer_group_active(peer
)) {
871 if (CHECK_FLAG(peer
->flags_invert
, flag
))
872 return !CHECK_FLAG(peer
->flags
, flag
);
874 return !!CHECK_FLAG(peer
->flags
, flag
);
877 return !!CHECK_FLAG(peer
->flags_override
, flag
);
880 static bool peergroup_af_flag_check(struct peer
*peer
, afi_t afi
, safi_t safi
,
883 if (!peer_group_active(peer
)) {
884 if (CHECK_FLAG(peer
->af_flags_invert
[afi
][safi
], flag
))
885 return !peer_af_flag_check(peer
, afi
, safi
, flag
);
887 return !!peer_af_flag_check(peer
, afi
, safi
, flag
);
890 return !!CHECK_FLAG(peer
->af_flags_override
[afi
][safi
], flag
);
893 static bool peergroup_filter_check(struct peer
*peer
, afi_t afi
, safi_t safi
,
894 uint8_t type
, int direct
)
896 struct bgp_filter
*filter
;
898 if (peer_group_active(peer
))
899 return !!CHECK_FLAG(peer
->filter_override
[afi
][safi
][direct
],
902 filter
= &peer
->filter
[afi
][safi
];
904 case PEER_FT_DISTRIBUTE_LIST
:
905 return !!(filter
->dlist
[direct
].name
);
906 case PEER_FT_FILTER_LIST
:
907 return !!(filter
->aslist
[direct
].name
);
908 case PEER_FT_PREFIX_LIST
:
909 return !!(filter
->plist
[direct
].name
);
910 case PEER_FT_ROUTE_MAP
:
911 return !!(filter
->map
[direct
].name
);
912 case PEER_FT_UNSUPPRESS_MAP
:
913 return !!(filter
->usmap
.name
);
919 /* Return true if the addpath type is set for peer and different from
922 static int peergroup_af_addpath_check(struct peer
*peer
, afi_t afi
, safi_t safi
)
924 enum bgp_addpath_strat type
, g_type
;
926 type
= peer
->addpath_type
[afi
][safi
];
928 if (type
!= BGP_ADDPATH_NONE
) {
929 if (peer_group_active(peer
)) {
930 g_type
= peer
->group
->conf
->addpath_type
[afi
][safi
];
944 /* Check peer's AS number and determines if this peer is IBGP or EBGP */
945 static inline bgp_peer_sort_t
peer_calc_sort(struct peer
*peer
)
952 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
953 if (peer
->as_type
== AS_INTERNAL
)
954 return BGP_PEER_IBGP
;
956 else if (peer
->as_type
== AS_EXTERNAL
)
957 return BGP_PEER_EBGP
;
959 else if (peer
->as_type
== AS_SPECIFIED
&& peer
->as
) {
961 return (bgp
->as
== peer
->as
? BGP_PEER_IBGP
969 peer1
= listnode_head(peer
->group
->peer
);
974 return BGP_PEER_INTERNAL
;
978 if (bgp
&& CHECK_FLAG(bgp
->config
, BGP_CONFIG_CONFEDERATION
)) {
979 if (peer
->local_as
== 0)
980 return BGP_PEER_INTERNAL
;
982 if (peer
->local_as
== peer
->as
) {
983 if (bgp
->as
== bgp
->confed_id
) {
984 if (peer
->local_as
== bgp
->as
)
985 return BGP_PEER_IBGP
;
987 return BGP_PEER_EBGP
;
989 if (peer
->local_as
== bgp
->confed_id
)
990 return BGP_PEER_EBGP
;
992 return BGP_PEER_IBGP
;
996 if (bgp_confederation_peers_check(bgp
, peer
->as
))
997 return BGP_PEER_CONFED
;
999 return BGP_PEER_EBGP
;
1001 if (peer
->as_type
!= AS_SPECIFIED
)
1002 return (peer
->as_type
== AS_INTERNAL
? BGP_PEER_IBGP
1005 return (peer
->local_as
== 0
1007 : peer
->local_as
== peer
->as
? BGP_PEER_IBGP
1012 /* Calculate and cache the peer "sort" */
1013 bgp_peer_sort_t
peer_sort(struct peer
*peer
)
1015 peer
->sort
= peer_calc_sort(peer
);
1019 static void peer_free(struct peer
*peer
)
1024 assert(peer
->status
== Deleted
);
1028 /* this /ought/ to have been done already through bgp_stop earlier,
1029 * but just to be sure..
1031 bgp_timer_set(peer
);
1032 bgp_reads_off(peer
);
1033 bgp_writes_off(peer
);
1034 assert(!peer
->t_write
);
1035 assert(!peer
->t_read
);
1036 BGP_EVENT_FLUSH(peer
);
1038 pthread_mutex_destroy(&peer
->io_mtx
);
1040 /* Free connected nexthop, if present */
1041 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
)
1042 && !peer_dynamic_neighbor(peer
))
1043 bgp_delete_connected_nexthop(family2afi(peer
->su
.sa
.sa_family
),
1046 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG
, peer
->tx_shutdown_message
);
1049 XFREE(MTYPE_PEER_DESC
, peer
->desc
);
1053 /* Free allocated host character. */
1055 XFREE(MTYPE_BGP_PEER_HOST
, peer
->host
);
1059 if (peer
->domainname
) {
1060 XFREE(MTYPE_BGP_PEER_HOST
, peer
->domainname
);
1061 peer
->domainname
= NULL
;
1065 XFREE(MTYPE_BGP_PEER_IFNAME
, peer
->ifname
);
1066 peer
->ifname
= NULL
;
1069 /* Update source configuration. */
1070 if (peer
->update_source
) {
1071 sockunion_free(peer
->update_source
);
1072 peer
->update_source
= NULL
;
1075 if (peer
->update_if
) {
1076 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
1077 peer
->update_if
= NULL
;
1080 if (peer
->notify
.data
)
1081 XFREE(MTYPE_TMP
, peer
->notify
.data
);
1082 memset(&peer
->notify
, 0, sizeof(struct bgp_notify
));
1084 if (peer
->clear_node_queue
)
1085 work_queue_free_and_null(&peer
->clear_node_queue
);
1087 bgp_sync_delete(peer
);
1089 if (peer
->conf_if
) {
1090 XFREE(MTYPE_PEER_CONF_IF
, peer
->conf_if
);
1091 peer
->conf_if
= NULL
;
1094 bfd_info_free(&(peer
->bfd_info
));
1096 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
1097 for (safi
= SAFI_UNICAST
; safi
< SAFI_MAX
; safi
++) {
1098 bgp_addpath_set_peer_type(peer
, afi
, safi
,
1103 bgp_unlock(peer
->bgp
);
1105 memset(peer
, 0, sizeof(struct peer
));
1107 XFREE(MTYPE_BGP_PEER
, peer
);
1110 /* increase reference count on a struct peer */
1111 struct peer
*peer_lock_with_caller(const char *name
, struct peer
*peer
)
1113 assert(peer
&& (peer
->lock
>= 0));
1116 zlog_debug("%s peer_lock %p %d", name
, peer
, peer
->lock
);
1124 /* decrease reference count on a struct peer
1125 * struct peer is freed and NULL returned if last reference
1127 struct peer
*peer_unlock_with_caller(const char *name
, struct peer
*peer
)
1129 assert(peer
&& (peer
->lock
> 0));
1132 zlog_debug("%s peer_unlock %p %d", name
, peer
, peer
->lock
);
1137 if (peer
->lock
== 0) {
1145 /* Allocate new peer object, implicitely locked. */
1146 struct peer
*peer_new(struct bgp
*bgp
)
1153 /* bgp argument is absolutely required */
1158 /* Allocate new peer. */
1159 peer
= XCALLOC(MTYPE_BGP_PEER
, sizeof(struct peer
));
1161 /* Set default value. */
1163 peer
->v_start
= BGP_INIT_START_TIMER
;
1164 peer
->v_connect
= BGP_DEFAULT_CONNECT_RETRY
;
1165 peer
->status
= Idle
;
1166 peer
->ostatus
= Idle
;
1167 peer
->cur_event
= peer
->last_event
= peer
->last_major_event
= 0;
1168 peer
->bgp
= bgp_lock(bgp
);
1169 peer
= peer_lock(peer
); /* initial reference */
1170 peer
->password
= NULL
;
1172 /* Set default flags. */
1173 FOREACH_AFI_SAFI (afi
, safi
) {
1174 if (!bgp_option_check(BGP_OPT_CONFIG_CISCO
)) {
1175 SET_FLAG(peer
->af_flags
[afi
][safi
],
1176 PEER_FLAG_SEND_COMMUNITY
);
1177 SET_FLAG(peer
->af_flags
[afi
][safi
],
1178 PEER_FLAG_SEND_EXT_COMMUNITY
);
1179 SET_FLAG(peer
->af_flags
[afi
][safi
],
1180 PEER_FLAG_SEND_LARGE_COMMUNITY
);
1182 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1183 PEER_FLAG_SEND_COMMUNITY
);
1184 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1185 PEER_FLAG_SEND_EXT_COMMUNITY
);
1186 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1187 PEER_FLAG_SEND_LARGE_COMMUNITY
);
1189 peer
->addpath_type
[afi
][safi
] = BGP_ADDPATH_NONE
;
1192 /* set nexthop-unchanged for l2vpn evpn by default */
1193 SET_FLAG(peer
->af_flags
[AFI_L2VPN
][SAFI_EVPN
],
1194 PEER_FLAG_NEXTHOP_UNCHANGED
);
1196 SET_FLAG(peer
->sflags
, PEER_STATUS_CAPABILITY_OPEN
);
1198 /* Create buffers. */
1199 peer
->ibuf
= stream_fifo_new();
1200 peer
->obuf
= stream_fifo_new();
1201 pthread_mutex_init(&peer
->io_mtx
, NULL
);
1203 /* We use a larger buffer for peer->obuf_work in the event that:
1204 * - We RX a BGP_UPDATE where the attributes alone are just
1205 * under BGP_MAX_PACKET_SIZE
1206 * - The user configures an outbound route-map that does many as-path
1207 * prepends or adds many communities. At most they can have
1208 * CMD_ARGC_MAX args in a route-map so there is a finite limit on how
1209 * large they can make the attributes.
1211 * Having a buffer with BGP_MAX_PACKET_SIZE_OVERFLOW allows us to avoid
1212 * bounds checking for every single attribute as we construct an
1216 stream_new(BGP_MAX_PACKET_SIZE
+ BGP_MAX_PACKET_SIZE_OVERFLOW
);
1218 ringbuf_new(BGP_MAX_PACKET_SIZE
* BGP_READ_PACKET_MAX
);
1220 peer
->scratch
= stream_new(BGP_MAX_PACKET_SIZE
);
1222 bgp_sync_init(peer
);
1224 /* Get service port number. */
1225 sp
= getservbyname("bgp", "tcp");
1226 peer
->port
= (sp
== NULL
) ? BGP_PORT_DEFAULT
: ntohs(sp
->s_port
);
1228 QOBJ_REG(peer
, peer
);
1233 * This function is invoked when a duplicate peer structure associated with
1234 * a neighbor is being deleted. If this about-to-be-deleted structure is
1235 * the one with all the config, then we have to copy over the info.
1237 void peer_xfer_config(struct peer
*peer_dst
, struct peer
*peer_src
)
1239 struct peer_af
*paf
;
1247 /* The following function is used by both peer group config copy to
1248 * individual peer and when we transfer config
1250 if (peer_src
->change_local_as
)
1251 peer_dst
->change_local_as
= peer_src
->change_local_as
;
1253 /* peer flags apply */
1254 peer_dst
->flags
= peer_src
->flags
;
1255 peer_dst
->cap
= peer_src
->cap
;
1257 peer_dst
->local_as
= peer_src
->local_as
;
1258 peer_dst
->port
= peer_src
->port
;
1259 (void)peer_sort(peer_dst
);
1260 peer_dst
->rmap_type
= peer_src
->rmap_type
;
1263 peer_dst
->holdtime
= peer_src
->holdtime
;
1264 peer_dst
->keepalive
= peer_src
->keepalive
;
1265 peer_dst
->connect
= peer_src
->connect
;
1266 peer_dst
->v_holdtime
= peer_src
->v_holdtime
;
1267 peer_dst
->v_keepalive
= peer_src
->v_keepalive
;
1268 peer_dst
->routeadv
= peer_src
->routeadv
;
1269 peer_dst
->v_routeadv
= peer_src
->v_routeadv
;
1271 /* password apply */
1272 if (peer_src
->password
&& !peer_dst
->password
)
1273 peer_dst
->password
=
1274 XSTRDUP(MTYPE_PEER_PASSWORD
, peer_src
->password
);
1276 FOREACH_AFI_SAFI (afi
, safi
) {
1277 peer_dst
->afc
[afi
][safi
] = peer_src
->afc
[afi
][safi
];
1278 peer_dst
->af_flags
[afi
][safi
] = peer_src
->af_flags
[afi
][safi
];
1279 peer_dst
->allowas_in
[afi
][safi
] =
1280 peer_src
->allowas_in
[afi
][safi
];
1281 peer_dst
->weight
[afi
][safi
] = peer_src
->weight
[afi
][safi
];
1282 peer_dst
->addpath_type
[afi
][safi
] =
1283 peer_src
->addpath_type
[afi
][safi
];
1286 for (afidx
= BGP_AF_START
; afidx
< BGP_AF_MAX
; afidx
++) {
1287 paf
= peer_src
->peer_af_array
[afidx
];
1289 peer_af_create(peer_dst
, paf
->afi
, paf
->safi
);
1292 /* update-source apply */
1293 if (peer_src
->update_source
) {
1294 if (peer_dst
->update_source
)
1295 sockunion_free(peer_dst
->update_source
);
1296 if (peer_dst
->update_if
) {
1297 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer_dst
->update_if
);
1298 peer_dst
->update_if
= NULL
;
1300 peer_dst
->update_source
=
1301 sockunion_dup(peer_src
->update_source
);
1302 } else if (peer_src
->update_if
) {
1303 if (peer_dst
->update_if
)
1304 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer_dst
->update_if
);
1305 if (peer_dst
->update_source
) {
1306 sockunion_free(peer_dst
->update_source
);
1307 peer_dst
->update_source
= NULL
;
1309 peer_dst
->update_if
=
1310 XSTRDUP(MTYPE_PEER_UPDATE_SOURCE
, peer_src
->update_if
);
1313 if (peer_src
->ifname
) {
1314 if (peer_dst
->ifname
)
1315 XFREE(MTYPE_BGP_PEER_IFNAME
, peer_dst
->ifname
);
1318 XSTRDUP(MTYPE_BGP_PEER_IFNAME
, peer_src
->ifname
);
1322 static int bgp_peer_conf_if_to_su_update_v4(struct peer
*peer
,
1323 struct interface
*ifp
)
1325 struct connected
*ifc
;
1328 struct listnode
*node
;
1330 /* If our IPv4 address on the interface is /30 or /31, we can derive the
1331 * IPv4 address of the other end.
1333 for (ALL_LIST_ELEMENTS_RO(ifp
->connected
, node
, ifc
)) {
1334 if (ifc
->address
&& (ifc
->address
->family
== AF_INET
)) {
1335 PREFIX_COPY_IPV4(&p
, CONNECTED_PREFIX(ifc
));
1336 if (p
.prefixlen
== 30) {
1337 peer
->su
.sa
.sa_family
= AF_INET
;
1338 addr
= ntohl(p
.u
.prefix4
.s_addr
);
1340 peer
->su
.sin
.sin_addr
.s_addr
=
1342 else if (addr
% 4 == 2)
1343 peer
->su
.sin
.sin_addr
.s_addr
=
1345 #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
1346 peer
->su
.sin
.sin_len
=
1347 sizeof(struct sockaddr_in
);
1348 #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
1350 } else if (p
.prefixlen
== 31) {
1351 peer
->su
.sa
.sa_family
= AF_INET
;
1352 addr
= ntohl(p
.u
.prefix4
.s_addr
);
1354 peer
->su
.sin
.sin_addr
.s_addr
=
1357 peer
->su
.sin
.sin_addr
.s_addr
=
1359 #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
1360 peer
->su
.sin
.sin_len
=
1361 sizeof(struct sockaddr_in
);
1362 #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
1364 } else if (bgp_debug_neighbor_events(peer
))
1366 "%s: IPv4 interface address is not /30 or /31, v4 session not started",
1374 static int bgp_peer_conf_if_to_su_update_v6(struct peer
*peer
,
1375 struct interface
*ifp
)
1377 struct nbr_connected
*ifc_nbr
;
1379 /* Have we learnt the peer's IPv6 link-local address? */
1380 if (ifp
->nbr_connected
1381 && (ifc_nbr
= listnode_head(ifp
->nbr_connected
))) {
1382 peer
->su
.sa
.sa_family
= AF_INET6
;
1383 memcpy(&peer
->su
.sin6
.sin6_addr
, &ifc_nbr
->address
->u
.prefix
,
1384 sizeof(struct in6_addr
));
1386 peer
->su
.sin6
.sin6_len
= sizeof(struct sockaddr_in6
);
1388 peer
->su
.sin6
.sin6_scope_id
= ifp
->ifindex
;
1396 * Set or reset the peer address socketunion structure based on the
1397 * learnt/derived peer address. If the address has changed, update the
1398 * password on the listen socket, if needed.
1400 void bgp_peer_conf_if_to_su_update(struct peer
*peer
)
1402 struct interface
*ifp
;
1404 int peer_addr_updated
= 0;
1410 * Our peer structure is stored in the bgp->peerhash
1411 * release it before we modify anything.
1413 hash_release(peer
->bgp
->peerhash
, peer
);
1415 prev_family
= peer
->su
.sa
.sa_family
;
1416 if ((ifp
= if_lookup_by_name(peer
->conf_if
, peer
->bgp
->vrf_id
))) {
1418 /* If BGP unnumbered is not "v6only", we first see if we can
1420 * peer's IPv4 address.
1422 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_IFPEER_V6ONLY
))
1424 bgp_peer_conf_if_to_su_update_v4(peer
, ifp
);
1426 /* If "v6only" or we can't derive peer's IPv4 address, see if
1428 * learnt the peer's IPv6 link-local address. This is from the
1430 * IPv6 address in router advertisement.
1432 if (!peer_addr_updated
)
1434 bgp_peer_conf_if_to_su_update_v6(peer
, ifp
);
1436 /* If we could derive the peer address, we may need to install the
1438 * configured for the peer, if any, on the listen socket. Otherwise,
1440 * that peer's address is not available and uninstall the password, if
1443 if (peer_addr_updated
) {
1444 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
)
1445 && prev_family
== AF_UNSPEC
)
1448 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
)
1449 && prev_family
!= AF_UNSPEC
)
1450 bgp_md5_unset(peer
);
1451 peer
->su
.sa
.sa_family
= AF_UNSPEC
;
1452 memset(&peer
->su
.sin6
.sin6_addr
, 0, sizeof(struct in6_addr
));
1456 * Since our su changed we need to del/add peer to the peerhash
1458 hash_get(peer
->bgp
->peerhash
, peer
, hash_alloc_intern
);
1461 static void bgp_recalculate_afi_safi_bestpaths(struct bgp
*bgp
, afi_t afi
,
1464 struct bgp_node
*rn
, *nrn
;
1466 for (rn
= bgp_table_top(bgp
->rib
[afi
][safi
]); rn
;
1467 rn
= bgp_route_next(rn
)) {
1468 if (rn
->info
!= NULL
) {
1469 /* Special handling for 2-level routing
1471 if (safi
== SAFI_MPLS_VPN
|| safi
== SAFI_ENCAP
1472 || safi
== SAFI_EVPN
) {
1473 for (nrn
= bgp_table_top(
1474 (struct bgp_table
*)(rn
->info
));
1475 nrn
; nrn
= bgp_route_next(nrn
))
1476 bgp_process(bgp
, nrn
, afi
, safi
);
1478 bgp_process(bgp
, rn
, afi
, safi
);
1483 /* Force a bestpath recalculation for all prefixes. This is used
1484 * when 'bgp bestpath' commands are entered.
1486 void bgp_recalculate_all_bestpaths(struct bgp
*bgp
)
1491 FOREACH_AFI_SAFI (afi
, safi
) {
1492 bgp_recalculate_afi_safi_bestpaths(bgp
, afi
, safi
);
1497 * Create new BGP peer.
1499 * conf_if and su are mutually exclusive if configuring from the cli.
1500 * If we are handing a doppelganger, then we *must* pass in both
1501 * the original peer's su and conf_if, so that we can appropriately
1502 * track the bgp->peerhash( ie we don't want to remove the current
1503 * one from the config ).
1505 struct peer
*peer_create(union sockunion
*su
, const char *conf_if
,
1506 struct bgp
*bgp
, as_t local_as
, as_t remote_as
,
1507 int as_type
, afi_t afi
, safi_t safi
,
1508 struct peer_group
*group
)
1512 char buf
[SU_ADDRSTRLEN
];
1514 peer
= peer_new(bgp
);
1516 peer
->conf_if
= XSTRDUP(MTYPE_PEER_CONF_IF
, conf_if
);
1520 bgp_peer_conf_if_to_su_update(peer
);
1522 XFREE(MTYPE_BGP_PEER_HOST
, peer
->host
);
1523 peer
->host
= XSTRDUP(MTYPE_BGP_PEER_HOST
, conf_if
);
1526 sockunion2str(su
, buf
, SU_ADDRSTRLEN
);
1528 XFREE(MTYPE_BGP_PEER_HOST
, peer
->host
);
1529 peer
->host
= XSTRDUP(MTYPE_BGP_PEER_HOST
, buf
);
1531 peer
->local_as
= local_as
;
1532 peer
->as
= remote_as
;
1533 peer
->as_type
= as_type
;
1534 peer
->local_id
= bgp
->router_id
;
1535 peer
->v_holdtime
= bgp
->default_holdtime
;
1536 peer
->v_keepalive
= bgp
->default_keepalive
;
1537 peer
->v_routeadv
= (peer_sort(peer
) == BGP_PEER_IBGP
)
1538 ? BGP_DEFAULT_IBGP_ROUTEADV
1539 : BGP_DEFAULT_EBGP_ROUTEADV
;
1541 peer
= peer_lock(peer
); /* bgp peer list reference */
1542 peer
->group
= group
;
1543 listnode_add_sort(bgp
->peer
, peer
);
1544 hash_get(bgp
->peerhash
, peer
, hash_alloc_intern
);
1546 /* Adjust update-group coalesce timer heuristics for # peers. */
1547 if (bgp
->heuristic_coalesce
) {
1548 long ct
= BGP_DEFAULT_SUBGROUP_COALESCE_TIME
1550 * BGP_PEER_ADJUST_SUBGROUP_COALESCE_TIME
);
1551 bgp
->coalesce_time
= MIN(BGP_MAX_SUBGROUP_COALESCE_TIME
, ct
);
1554 active
= peer_active(peer
);
1556 /* Last read and reset time set */
1557 peer
->readtime
= peer
->resettime
= bgp_clock();
1559 /* Default TTL set. */
1560 peer
->ttl
= (peer
->sort
== BGP_PEER_IBGP
) ? MAXTTL
: 1;
1562 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
1565 peer
->afc
[afi
][safi
] = 1;
1566 peer_af_create(peer
, afi
, safi
);
1569 /* auto shutdown if configured */
1570 if (bgp
->autoshutdown
)
1571 peer_flag_set(peer
, PEER_FLAG_SHUTDOWN
);
1572 /* Set up peer's events and timers. */
1573 else if (!active
&& peer_active(peer
))
1574 bgp_timer_set(peer
);
1579 /* Make accept BGP peer. This function is only called from the test code */
1580 struct peer
*peer_create_accept(struct bgp
*bgp
)
1584 peer
= peer_new(bgp
);
1586 peer
= peer_lock(peer
); /* bgp peer list reference */
1587 listnode_add_sort(bgp
->peer
, peer
);
1593 * Return true if we have a peer configured to use this afi/safi
1595 int bgp_afi_safi_peer_exists(struct bgp
*bgp
, afi_t afi
, safi_t safi
)
1597 struct listnode
*node
;
1600 for (ALL_LIST_ELEMENTS_RO(bgp
->peer
, node
, peer
)) {
1601 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
))
1604 if (peer
->afc
[afi
][safi
])
1611 /* Change peer's AS number. */
1612 void peer_as_change(struct peer
*peer
, as_t as
, int as_specified
)
1614 bgp_peer_sort_t type
;
1617 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
1618 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
1619 peer
->last_reset
= PEER_DOWN_REMOTE_AS_CHANGE
;
1620 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
1621 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
1623 bgp_session_reset(peer
);
1625 type
= peer_sort(peer
);
1627 peer
->as_type
= as_specified
;
1629 if (bgp_config_check(peer
->bgp
, BGP_CONFIG_CONFEDERATION
)
1630 && !bgp_confederation_peers_check(peer
->bgp
, as
)
1631 && peer
->bgp
->as
!= as
)
1632 peer
->local_as
= peer
->bgp
->confed_id
;
1634 peer
->local_as
= peer
->bgp
->as
;
1636 /* Advertisement-interval reset */
1637 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_ROUTEADV
)) {
1638 peer
->v_routeadv
= (peer_sort(peer
) == BGP_PEER_IBGP
)
1639 ? BGP_DEFAULT_IBGP_ROUTEADV
1640 : BGP_DEFAULT_EBGP_ROUTEADV
;
1644 if (peer_sort(peer
) == BGP_PEER_IBGP
)
1646 else if (type
== BGP_PEER_IBGP
)
1649 /* reflector-client reset */
1650 if (peer_sort(peer
) != BGP_PEER_IBGP
) {
1651 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_UNICAST
],
1652 PEER_FLAG_REFLECTOR_CLIENT
);
1653 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_MULTICAST
],
1654 PEER_FLAG_REFLECTOR_CLIENT
);
1655 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_LABELED_UNICAST
],
1656 PEER_FLAG_REFLECTOR_CLIENT
);
1657 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_MPLS_VPN
],
1658 PEER_FLAG_REFLECTOR_CLIENT
);
1659 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_ENCAP
],
1660 PEER_FLAG_REFLECTOR_CLIENT
);
1661 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_FLOWSPEC
],
1662 PEER_FLAG_REFLECTOR_CLIENT
);
1663 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_UNICAST
],
1664 PEER_FLAG_REFLECTOR_CLIENT
);
1665 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_MULTICAST
],
1666 PEER_FLAG_REFLECTOR_CLIENT
);
1667 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_LABELED_UNICAST
],
1668 PEER_FLAG_REFLECTOR_CLIENT
);
1669 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_MPLS_VPN
],
1670 PEER_FLAG_REFLECTOR_CLIENT
);
1671 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_ENCAP
],
1672 PEER_FLAG_REFLECTOR_CLIENT
);
1673 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_FLOWSPEC
],
1674 PEER_FLAG_REFLECTOR_CLIENT
);
1675 UNSET_FLAG(peer
->af_flags
[AFI_L2VPN
][SAFI_EVPN
],
1676 PEER_FLAG_REFLECTOR_CLIENT
);
1679 /* local-as reset */
1680 if (peer_sort(peer
) != BGP_PEER_EBGP
) {
1681 peer
->change_local_as
= 0;
1682 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS
);
1683 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
1684 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
1688 /* If peer does not exist, create new one. If peer already exists,
1689 set AS number to the peer. */
1690 int peer_remote_as(struct bgp
*bgp
, union sockunion
*su
, const char *conf_if
,
1691 as_t
*as
, int as_type
, afi_t afi
, safi_t safi
)
1697 peer
= peer_lookup_by_conf_if(bgp
, conf_if
);
1699 peer
= peer_lookup(bgp
, su
);
1702 /* Not allowed for a dynamic peer. */
1703 if (peer_dynamic_neighbor(peer
)) {
1705 return BGP_ERR_INVALID_FOR_DYNAMIC_PEER
;
1708 /* When this peer is a member of peer-group. */
1710 if (peer
->group
->conf
->as
) {
1711 /* Return peer group's AS number. */
1712 *as
= peer
->group
->conf
->as
;
1713 return BGP_ERR_PEER_GROUP_MEMBER
;
1715 if (peer_sort(peer
->group
->conf
) == BGP_PEER_IBGP
) {
1716 if ((as_type
!= AS_INTERNAL
)
1717 && (bgp
->as
!= *as
)) {
1719 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT
;
1722 if ((as_type
!= AS_EXTERNAL
)
1723 && (bgp
->as
== *as
)) {
1725 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT
;
1730 /* Existing peer's AS number change. */
1731 if (((peer
->as_type
== AS_SPECIFIED
) && peer
->as
!= *as
)
1732 || (peer
->as_type
!= as_type
))
1733 peer_as_change(peer
, *as
, as_type
);
1736 return BGP_ERR_NO_INTERFACE_CONFIG
;
1738 /* If the peer is not part of our confederation, and its not an
1739 iBGP peer then spoof the source AS */
1740 if (bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
)
1741 && !bgp_confederation_peers_check(bgp
, *as
)
1743 local_as
= bgp
->confed_id
;
1747 /* If this is IPv4 unicast configuration and "no bgp default
1748 ipv4-unicast" is specified. */
1750 if (bgp_flag_check(bgp
, BGP_FLAG_NO_DEFAULT_IPV4
)
1751 && afi
== AFI_IP
&& safi
== SAFI_UNICAST
)
1752 peer_create(su
, conf_if
, bgp
, local_as
, *as
, as_type
, 0,
1755 peer_create(su
, conf_if
, bgp
, local_as
, *as
, as_type
,
1762 static void peer_group2peer_config_copy_af(struct peer_group
*group
,
1763 struct peer
*peer
, afi_t afi
,
1767 int out
= FILTER_OUT
;
1769 uint32_t pflags_ovrd
;
1770 uint8_t *pfilter_ovrd
;
1774 pflags_ovrd
= peer
->af_flags_override
[afi
][safi
];
1775 pfilter_ovrd
= &peer
->filter_override
[afi
][safi
][in
];
1777 /* peer af_flags apply */
1778 flags_tmp
= conf
->af_flags
[afi
][safi
] & ~pflags_ovrd
;
1779 flags_tmp
^= conf
->af_flags_invert
[afi
][safi
]
1780 ^ peer
->af_flags_invert
[afi
][safi
];
1781 flags_tmp
&= ~pflags_ovrd
;
1783 UNSET_FLAG(peer
->af_flags
[afi
][safi
], ~pflags_ovrd
);
1784 SET_FLAG(peer
->af_flags
[afi
][safi
], flags_tmp
);
1785 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1786 conf
->af_flags_invert
[afi
][safi
]);
1788 /* maximum-prefix */
1789 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_MAX_PREFIX
)) {
1790 PEER_ATTR_INHERIT(peer
, group
, pmax
[afi
][safi
]);
1791 PEER_ATTR_INHERIT(peer
, group
, pmax_threshold
[afi
][safi
]);
1792 PEER_ATTR_INHERIT(peer
, group
, pmax_restart
[afi
][safi
]);
1796 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_ALLOWAS_IN
))
1797 PEER_ATTR_INHERIT(peer
, group
, allowas_in
[afi
][safi
]);
1800 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_WEIGHT
))
1801 PEER_ATTR_INHERIT(peer
, group
, weight
[afi
][safi
]);
1803 /* default-originate route-map */
1804 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_DEFAULT_ORIGINATE
)) {
1805 PEER_STR_ATTR_INHERIT(peer
, group
, default_rmap
[afi
][safi
].name
,
1806 MTYPE_ROUTE_MAP_NAME
);
1807 PEER_ATTR_INHERIT(peer
, group
, default_rmap
[afi
][safi
].map
);
1810 /* inbound filter apply */
1811 if (!CHECK_FLAG(pfilter_ovrd
[in
], PEER_FT_DISTRIBUTE_LIST
)) {
1812 PEER_STR_ATTR_INHERIT(peer
, group
,
1813 filter
[afi
][safi
].dlist
[in
].name
,
1814 MTYPE_BGP_FILTER_NAME
);
1815 PEER_ATTR_INHERIT(peer
, group
,
1816 filter
[afi
][safi
].dlist
[in
].alist
);
1819 if (!CHECK_FLAG(pfilter_ovrd
[in
], PEER_FT_PREFIX_LIST
)) {
1820 PEER_STR_ATTR_INHERIT(peer
, group
,
1821 filter
[afi
][safi
].plist
[in
].name
,
1822 MTYPE_BGP_FILTER_NAME
);
1823 PEER_ATTR_INHERIT(peer
, group
,
1824 filter
[afi
][safi
].plist
[in
].plist
);
1827 if (!CHECK_FLAG(pfilter_ovrd
[in
], PEER_FT_FILTER_LIST
)) {
1828 PEER_STR_ATTR_INHERIT(peer
, group
,
1829 filter
[afi
][safi
].aslist
[in
].name
,
1830 MTYPE_BGP_FILTER_NAME
);
1831 PEER_ATTR_INHERIT(peer
, group
,
1832 filter
[afi
][safi
].aslist
[in
].aslist
);
1835 if (!CHECK_FLAG(pfilter_ovrd
[RMAP_IN
], PEER_FT_ROUTE_MAP
)) {
1836 PEER_STR_ATTR_INHERIT(peer
, group
,
1837 filter
[afi
][safi
].map
[in
].name
,
1838 MTYPE_BGP_FILTER_NAME
);
1839 PEER_ATTR_INHERIT(peer
, group
,
1840 filter
[afi
][safi
].map
[RMAP_IN
].map
);
1843 /* outbound filter apply */
1844 if (!CHECK_FLAG(pfilter_ovrd
[out
], PEER_FT_DISTRIBUTE_LIST
)) {
1845 PEER_STR_ATTR_INHERIT(peer
, group
,
1846 filter
[afi
][safi
].dlist
[out
].name
,
1847 MTYPE_BGP_FILTER_NAME
);
1848 PEER_ATTR_INHERIT(peer
, group
,
1849 filter
[afi
][safi
].dlist
[out
].alist
);
1852 if (!CHECK_FLAG(pfilter_ovrd
[out
], PEER_FT_PREFIX_LIST
)) {
1853 PEER_STR_ATTR_INHERIT(peer
, group
,
1854 filter
[afi
][safi
].plist
[out
].name
,
1855 MTYPE_BGP_FILTER_NAME
);
1856 PEER_ATTR_INHERIT(peer
, group
,
1857 filter
[afi
][safi
].plist
[out
].plist
);
1860 if (!CHECK_FLAG(pfilter_ovrd
[out
], PEER_FT_FILTER_LIST
)) {
1861 PEER_STR_ATTR_INHERIT(peer
, group
,
1862 filter
[afi
][safi
].aslist
[out
].name
,
1863 MTYPE_BGP_FILTER_NAME
);
1864 PEER_ATTR_INHERIT(peer
, group
,
1865 filter
[afi
][safi
].aslist
[out
].aslist
);
1868 if (!CHECK_FLAG(pfilter_ovrd
[RMAP_OUT
], PEER_FT_ROUTE_MAP
)) {
1869 PEER_STR_ATTR_INHERIT(peer
, group
,
1870 filter
[afi
][safi
].map
[RMAP_OUT
].name
,
1871 MTYPE_BGP_FILTER_NAME
);
1872 PEER_ATTR_INHERIT(peer
, group
,
1873 filter
[afi
][safi
].map
[RMAP_OUT
].map
);
1876 /* nondirectional filter apply */
1877 if (!CHECK_FLAG(pfilter_ovrd
[0], PEER_FT_UNSUPPRESS_MAP
)) {
1878 PEER_STR_ATTR_INHERIT(peer
, group
, filter
[afi
][safi
].usmap
.name
,
1879 MTYPE_BGP_FILTER_NAME
);
1880 PEER_ATTR_INHERIT(peer
, group
, filter
[afi
][safi
].usmap
.map
);
1883 if (peer
->addpath_type
[afi
][safi
] == BGP_ADDPATH_NONE
) {
1884 peer
->addpath_type
[afi
][safi
] = conf
->addpath_type
[afi
][safi
];
1885 bgp_addpath_type_changed(conf
->bgp
);
1889 static int peer_activate_af(struct peer
*peer
, afi_t afi
, safi_t safi
)
1894 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
1895 flog_err(EC_BGP_PEER_GROUP
, "%s was called for peer-group %s",
1896 __func__
, peer
->host
);
1900 /* Do not activate a peer for both SAFI_UNICAST and SAFI_LABELED_UNICAST
1902 if ((safi
== SAFI_UNICAST
&& peer
->afc
[afi
][SAFI_LABELED_UNICAST
])
1903 || (safi
== SAFI_LABELED_UNICAST
&& peer
->afc
[afi
][SAFI_UNICAST
]))
1904 return BGP_ERR_PEER_SAFI_CONFLICT
;
1906 /* Nothing to do if we've already activated this peer */
1907 if (peer
->afc
[afi
][safi
])
1910 if (peer_af_create(peer
, afi
, safi
) == NULL
)
1913 active
= peer_active(peer
);
1914 peer
->afc
[afi
][safi
] = 1;
1917 peer_group2peer_config_copy_af(peer
->group
, peer
, afi
, safi
);
1919 if (!active
&& peer_active(peer
)) {
1920 bgp_timer_set(peer
);
1922 if (peer
->status
== Established
) {
1923 if (CHECK_FLAG(peer
->cap
, PEER_CAP_DYNAMIC_RCV
)) {
1924 peer
->afc_adv
[afi
][safi
] = 1;
1925 bgp_capability_send(peer
, afi
, safi
,
1927 CAPABILITY_ACTION_SET
);
1928 if (peer
->afc_recv
[afi
][safi
]) {
1929 peer
->afc_nego
[afi
][safi
] = 1;
1930 bgp_announce_route(peer
, afi
, safi
);
1933 peer
->last_reset
= PEER_DOWN_AF_ACTIVATE
;
1934 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
1935 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
1938 if (peer
->status
== OpenSent
|| peer
->status
== OpenConfirm
) {
1939 peer
->last_reset
= PEER_DOWN_AF_ACTIVATE
;
1940 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
1941 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
1944 * If we are turning on a AFI/SAFI locally and we've
1945 * started bringing a peer up, we need to tell
1946 * the other peer to restart because we might loose
1947 * configuration here because when the doppelganger
1948 * gets to a established state due to how
1949 * we resolve we could just overwrite the afi/safi
1952 other
= peer
->doppelganger
;
1954 && (other
->status
== OpenSent
1955 || other
->status
== OpenConfirm
)) {
1956 other
->last_reset
= PEER_DOWN_AF_ACTIVATE
;
1957 bgp_notify_send(other
, BGP_NOTIFY_CEASE
,
1958 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
1965 /* Activate the peer or peer group for specified AFI and SAFI. */
1966 int peer_activate(struct peer
*peer
, afi_t afi
, safi_t safi
)
1969 struct peer_group
*group
;
1970 struct listnode
*node
, *nnode
;
1971 struct peer
*tmp_peer
;
1974 /* Nothing to do if we've already activated this peer */
1975 if (peer
->afc
[afi
][safi
])
1980 /* This is a peer-group so activate all of the members of the
1981 * peer-group as well */
1982 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
1984 /* Do not activate a peer for both SAFI_UNICAST and
1985 * SAFI_LABELED_UNICAST */
1986 if ((safi
== SAFI_UNICAST
1987 && peer
->afc
[afi
][SAFI_LABELED_UNICAST
])
1988 || (safi
== SAFI_LABELED_UNICAST
1989 && peer
->afc
[afi
][SAFI_UNICAST
]))
1990 return BGP_ERR_PEER_SAFI_CONFLICT
;
1992 peer
->afc
[afi
][safi
] = 1;
1993 group
= peer
->group
;
1995 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, tmp_peer
)) {
1996 ret
|= peer_activate_af(tmp_peer
, afi
, safi
);
1999 ret
|= peer_activate_af(peer
, afi
, safi
);
2002 /* If this is the first peer to be activated for this
2003 * afi/labeled-unicast recalc bestpaths to trigger label allocation */
2004 if (safi
== SAFI_LABELED_UNICAST
2005 && !bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
]) {
2007 if (BGP_DEBUG(zebra
, ZEBRA
))
2009 "peer(s) are now active for labeled-unicast, allocate MPLS labels");
2011 bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
] = 1;
2012 bgp_recalculate_afi_safi_bestpaths(bgp
, afi
, SAFI_UNICAST
);
2015 if (safi
== SAFI_FLOWSPEC
) {
2016 /* connect to table manager */
2017 bgp_zebra_init_tm_connect(bgp
);
2022 static int non_peergroup_deactivate_af(struct peer
*peer
, afi_t afi
,
2025 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
2026 flog_err(EC_BGP_PEER_GROUP
, "%s was called for peer-group %s",
2027 __func__
, peer
->host
);
2031 /* Nothing to do if we've already deactivated this peer */
2032 if (!peer
->afc
[afi
][safi
])
2035 /* De-activate the address family configuration. */
2036 peer
->afc
[afi
][safi
] = 0;
2038 if (peer_af_delete(peer
, afi
, safi
) != 0) {
2039 flog_err(EC_BGP_PEER_DELETE
,
2040 "couldn't delete af structure for peer %s",
2045 if (peer
->status
== Established
) {
2046 if (CHECK_FLAG(peer
->cap
, PEER_CAP_DYNAMIC_RCV
)) {
2047 peer
->afc_adv
[afi
][safi
] = 0;
2048 peer
->afc_nego
[afi
][safi
] = 0;
2050 if (peer_active_nego(peer
)) {
2051 bgp_capability_send(peer
, afi
, safi
,
2053 CAPABILITY_ACTION_UNSET
);
2054 bgp_clear_route(peer
, afi
, safi
);
2055 peer
->pcount
[afi
][safi
] = 0;
2057 peer
->last_reset
= PEER_DOWN_NEIGHBOR_DELETE
;
2058 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2059 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2062 peer
->last_reset
= PEER_DOWN_NEIGHBOR_DELETE
;
2063 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2064 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2071 int peer_deactivate(struct peer
*peer
, afi_t afi
, safi_t safi
)
2074 struct peer_group
*group
;
2075 struct peer
*tmp_peer
;
2076 struct listnode
*node
, *nnode
;
2079 /* Nothing to do if we've already de-activated this peer */
2080 if (!peer
->afc
[afi
][safi
])
2083 /* This is a peer-group so de-activate all of the members of the
2084 * peer-group as well */
2085 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
2086 peer
->afc
[afi
][safi
] = 0;
2087 group
= peer
->group
;
2089 if (peer_af_delete(peer
, afi
, safi
) != 0) {
2090 flog_err(EC_BGP_PEER_DELETE
,
2091 "couldn't delete af structure for peer %s",
2095 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, tmp_peer
)) {
2096 ret
|= non_peergroup_deactivate_af(tmp_peer
, afi
, safi
);
2099 ret
|= non_peergroup_deactivate_af(peer
, afi
, safi
);
2104 /* If this is the last peer to be deactivated for this
2105 * afi/labeled-unicast recalc bestpaths to trigger label deallocation */
2106 if (safi
== SAFI_LABELED_UNICAST
2107 && bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
]
2108 && !bgp_afi_safi_peer_exists(bgp
, afi
, safi
)) {
2110 if (BGP_DEBUG(zebra
, ZEBRA
))
2112 "peer(s) are no longer active for labeled-unicast, deallocate MPLS labels");
2114 bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
] = 0;
2115 bgp_recalculate_afi_safi_bestpaths(bgp
, afi
, SAFI_UNICAST
);
2120 int peer_afc_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int enable
)
2123 return peer_activate(peer
, afi
, safi
);
2125 return peer_deactivate(peer
, afi
, safi
);
2128 static void peer_nsf_stop(struct peer
*peer
)
2133 UNSET_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
);
2134 UNSET_FLAG(peer
->sflags
, PEER_STATUS_NSF_MODE
);
2136 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++)
2137 for (safi
= SAFI_UNICAST
; safi
<= SAFI_MPLS_VPN
; safi
++)
2138 peer
->nsf
[afi
][safi
] = 0;
2140 if (peer
->t_gr_restart
) {
2141 BGP_TIMER_OFF(peer
->t_gr_restart
);
2142 if (bgp_debug_neighbor_events(peer
))
2143 zlog_debug("%s graceful restart timer stopped",
2146 if (peer
->t_gr_stale
) {
2147 BGP_TIMER_OFF(peer
->t_gr_stale
);
2148 if (bgp_debug_neighbor_events(peer
))
2150 "%s graceful restart stalepath timer stopped",
2153 bgp_clear_route_all(peer
);
2156 /* Delete peer from confguration.
2158 * The peer is moved to a dead-end "Deleted" neighbour-state, to allow
2159 * it to "cool off" and refcounts to hit 0, at which state it is freed.
2161 * This function /should/ take care to be idempotent, to guard against
2162 * it being called multiple times through stray events that come in
2163 * that happen to result in this function being called again. That
2164 * said, getting here for a "Deleted" peer is a bug in the neighbour
2167 int peer_delete(struct peer
*peer
)
2173 struct bgp_filter
*filter
;
2174 struct listnode
*pn
;
2177 assert(peer
->status
!= Deleted
);
2180 accept_peer
= CHECK_FLAG(peer
->sflags
, PEER_STATUS_ACCEPT_PEER
);
2182 bgp_reads_off(peer
);
2183 bgp_writes_off(peer
);
2184 assert(!CHECK_FLAG(peer
->thread_flags
, PEER_THREAD_WRITES_ON
));
2185 assert(!CHECK_FLAG(peer
->thread_flags
, PEER_THREAD_READS_ON
));
2187 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
))
2188 peer_nsf_stop(peer
);
2190 SET_FLAG(peer
->flags
, PEER_FLAG_DELETE
);
2192 /* If this peer belongs to peer group, clear up the
2195 if (peer_dynamic_neighbor(peer
))
2196 peer_drop_dynamic_neighbor(peer
);
2198 if ((pn
= listnode_lookup(peer
->group
->peer
, peer
))) {
2200 peer
); /* group->peer list reference */
2201 list_delete_node(peer
->group
->peer
, pn
);
2206 /* Withdraw all information from routing table. We can not use
2207 * BGP_EVENT_ADD (peer, BGP_Stop) at here. Because the event is
2208 * executed after peer structure is deleted.
2210 peer
->last_reset
= PEER_DOWN_NEIGHBOR_DELETE
;
2212 UNSET_FLAG(peer
->flags
, PEER_FLAG_DELETE
);
2214 if (peer
->doppelganger
) {
2215 peer
->doppelganger
->doppelganger
= NULL
;
2216 peer
->doppelganger
= NULL
;
2219 UNSET_FLAG(peer
->sflags
, PEER_STATUS_ACCEPT_PEER
);
2220 bgp_fsm_change_status(peer
, Deleted
);
2222 /* Remove from NHT */
2223 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
))
2224 bgp_unlink_nexthop_by_peer(peer
);
2226 /* Password configuration */
2227 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
)) {
2228 XFREE(MTYPE_PEER_PASSWORD
, peer
->password
);
2230 if (!accept_peer
&& !BGP_PEER_SU_UNSPEC(peer
)
2231 && !CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
2232 bgp_md5_unset(peer
);
2235 bgp_timer_set(peer
); /* stops all timers for Deleted */
2237 /* Delete from all peer list. */
2238 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)
2239 && (pn
= listnode_lookup(bgp
->peer
, peer
))) {
2240 peer_unlock(peer
); /* bgp peer list reference */
2241 list_delete_node(bgp
->peer
, pn
);
2242 hash_release(bgp
->peerhash
, peer
);
2247 stream_fifo_free(peer
->ibuf
);
2252 stream_fifo_free(peer
->obuf
);
2256 if (peer
->ibuf_work
) {
2257 ringbuf_del(peer
->ibuf_work
);
2258 peer
->ibuf_work
= NULL
;
2261 if (peer
->obuf_work
) {
2262 stream_free(peer
->obuf_work
);
2263 peer
->obuf_work
= NULL
;
2266 if (peer
->scratch
) {
2267 stream_free(peer
->scratch
);
2268 peer
->scratch
= NULL
;
2271 /* Local and remote addresses. */
2272 if (peer
->su_local
) {
2273 sockunion_free(peer
->su_local
);
2274 peer
->su_local
= NULL
;
2277 if (peer
->su_remote
) {
2278 sockunion_free(peer
->su_remote
);
2279 peer
->su_remote
= NULL
;
2282 /* Free filter related memory. */
2283 FOREACH_AFI_SAFI (afi
, safi
) {
2284 filter
= &peer
->filter
[afi
][safi
];
2286 for (i
= FILTER_IN
; i
< FILTER_MAX
; i
++) {
2287 if (filter
->dlist
[i
].name
) {
2288 XFREE(MTYPE_BGP_FILTER_NAME
,
2289 filter
->dlist
[i
].name
);
2290 filter
->dlist
[i
].name
= NULL
;
2293 if (filter
->plist
[i
].name
) {
2294 XFREE(MTYPE_BGP_FILTER_NAME
,
2295 filter
->plist
[i
].name
);
2296 filter
->plist
[i
].name
= NULL
;
2299 if (filter
->aslist
[i
].name
) {
2300 XFREE(MTYPE_BGP_FILTER_NAME
,
2301 filter
->aslist
[i
].name
);
2302 filter
->aslist
[i
].name
= NULL
;
2306 for (i
= RMAP_IN
; i
< RMAP_MAX
; i
++) {
2307 if (filter
->map
[i
].name
) {
2308 XFREE(MTYPE_BGP_FILTER_NAME
,
2309 filter
->map
[i
].name
);
2310 filter
->map
[i
].name
= NULL
;
2314 if (filter
->usmap
.name
) {
2315 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
2316 filter
->usmap
.name
= NULL
;
2319 if (peer
->default_rmap
[afi
][safi
].name
) {
2320 XFREE(MTYPE_ROUTE_MAP_NAME
,
2321 peer
->default_rmap
[afi
][safi
].name
);
2322 peer
->default_rmap
[afi
][safi
].name
= NULL
;
2326 FOREACH_AFI_SAFI (afi
, safi
)
2327 peer_af_delete(peer
, afi
, safi
);
2329 if (peer
->hostname
) {
2330 XFREE(MTYPE_BGP_PEER_HOST
, peer
->hostname
);
2331 peer
->hostname
= NULL
;
2334 if (peer
->domainname
) {
2335 XFREE(MTYPE_BGP_PEER_HOST
, peer
->domainname
);
2336 peer
->domainname
= NULL
;
2339 peer_unlock(peer
); /* initial reference */
2344 static int peer_group_cmp(struct peer_group
*g1
, struct peer_group
*g2
)
2346 return strcmp(g1
->name
, g2
->name
);
2349 /* Peer group cofiguration. */
2350 static struct peer_group
*peer_group_new(void)
2352 return (struct peer_group
*)XCALLOC(MTYPE_PEER_GROUP
,
2353 sizeof(struct peer_group
));
2356 static void peer_group_free(struct peer_group
*group
)
2358 XFREE(MTYPE_PEER_GROUP
, group
);
2361 struct peer_group
*peer_group_lookup(struct bgp
*bgp
, const char *name
)
2363 struct peer_group
*group
;
2364 struct listnode
*node
, *nnode
;
2366 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
2367 if (strcmp(group
->name
, name
) == 0)
2373 struct peer_group
*peer_group_get(struct bgp
*bgp
, const char *name
)
2375 struct peer_group
*group
;
2378 group
= peer_group_lookup(bgp
, name
);
2382 group
= peer_group_new();
2385 XFREE(MTYPE_PEER_GROUP_HOST
, group
->name
);
2386 group
->name
= XSTRDUP(MTYPE_PEER_GROUP_HOST
, name
);
2387 group
->peer
= list_new();
2388 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++)
2389 group
->listen_range
[afi
] = list_new();
2390 group
->conf
= peer_new(bgp
);
2391 if (!bgp_flag_check(bgp
, BGP_FLAG_NO_DEFAULT_IPV4
))
2392 group
->conf
->afc
[AFI_IP
][SAFI_UNICAST
] = 1;
2393 if (group
->conf
->host
)
2394 XFREE(MTYPE_BGP_PEER_HOST
, group
->conf
->host
);
2395 group
->conf
->host
= XSTRDUP(MTYPE_BGP_PEER_HOST
, name
);
2396 group
->conf
->group
= group
;
2397 group
->conf
->as
= 0;
2398 group
->conf
->ttl
= 1;
2399 group
->conf
->gtsm_hops
= 0;
2400 group
->conf
->v_routeadv
= BGP_DEFAULT_EBGP_ROUTEADV
;
2401 SET_FLAG(group
->conf
->sflags
, PEER_STATUS_GROUP
);
2402 listnode_add_sort(bgp
->group
, group
);
2407 static void peer_group2peer_config_copy(struct peer_group
*group
,
2417 peer
->as
= conf
->as
;
2420 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_LOCAL_AS
))
2421 peer
->change_local_as
= conf
->change_local_as
;
2424 peer
->ttl
= conf
->ttl
;
2427 peer
->gtsm_hops
= conf
->gtsm_hops
;
2429 /* peer flags apply */
2430 flags_tmp
= conf
->flags
& ~peer
->flags_override
;
2431 flags_tmp
^= conf
->flags_invert
^ peer
->flags_invert
;
2432 flags_tmp
&= ~peer
->flags_override
;
2434 UNSET_FLAG(peer
->flags
, ~peer
->flags_override
);
2435 SET_FLAG(peer
->flags
, flags_tmp
);
2436 SET_FLAG(peer
->flags_invert
, conf
->flags_invert
);
2438 /* peer timers apply */
2439 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_TIMER
)) {
2440 PEER_ATTR_INHERIT(peer
, group
, holdtime
);
2441 PEER_ATTR_INHERIT(peer
, group
, keepalive
);
2444 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_TIMER_CONNECT
)) {
2445 PEER_ATTR_INHERIT(peer
, group
, connect
);
2446 if (CHECK_FLAG(conf
->flags
, PEER_FLAG_TIMER_CONNECT
))
2447 peer
->v_connect
= conf
->connect
;
2449 peer
->v_connect
= BGP_DEFAULT_CONNECT_RETRY
;
2452 /* advertisement-interval apply */
2453 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_ROUTEADV
)) {
2454 PEER_ATTR_INHERIT(peer
, group
, routeadv
);
2455 if (CHECK_FLAG(conf
->flags
, PEER_FLAG_ROUTEADV
))
2456 peer
->v_routeadv
= conf
->routeadv
;
2458 peer
->v_routeadv
= (peer_sort(peer
) == BGP_PEER_IBGP
)
2459 ? BGP_DEFAULT_IBGP_ROUTEADV
2460 : BGP_DEFAULT_EBGP_ROUTEADV
;
2463 /* password apply */
2464 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_PASSWORD
))
2465 PEER_STR_ATTR_INHERIT(peer
, group
, password
,
2466 MTYPE_PEER_PASSWORD
);
2468 if (!BGP_PEER_SU_UNSPEC(peer
))
2471 /* update-source apply */
2472 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_UPDATE_SOURCE
)) {
2473 if (conf
->update_source
) {
2474 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
2475 PEER_SU_ATTR_INHERIT(peer
, group
, update_source
);
2476 } else if (conf
->update_if
) {
2477 sockunion_free(peer
->update_source
);
2478 PEER_STR_ATTR_INHERIT(peer
, group
, update_if
,
2479 MTYPE_PEER_UPDATE_SOURCE
);
2483 bgp_bfd_peer_group2peer_copy(conf
, peer
);
2486 /* Peer group's remote AS configuration. */
2487 int peer_group_remote_as(struct bgp
*bgp
, const char *group_name
, as_t
*as
,
2490 struct peer_group
*group
;
2492 struct listnode
*node
, *nnode
;
2494 group
= peer_group_lookup(bgp
, group_name
);
2498 if ((as_type
== group
->conf
->as_type
) && (group
->conf
->as
== *as
))
2502 /* When we setup peer-group AS number all peer group member's AS
2503 number must be updated to same number. */
2504 peer_as_change(group
->conf
, *as
, as_type
);
2506 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2507 if (((peer
->as_type
== AS_SPECIFIED
) && peer
->as
!= *as
)
2508 || (peer
->as_type
!= as_type
))
2509 peer_as_change(peer
, *as
, as_type
);
2515 int peer_group_delete(struct peer_group
*group
)
2519 struct prefix
*prefix
;
2521 struct listnode
*node
, *nnode
;
2526 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2527 other
= peer
->doppelganger
;
2529 if (other
&& other
->status
!= Deleted
) {
2530 other
->group
= NULL
;
2534 list_delete(&group
->peer
);
2536 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
2537 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
,
2539 prefix_free(prefix
);
2541 list_delete(&group
->listen_range
[afi
]);
2544 XFREE(MTYPE_PEER_GROUP_HOST
, group
->name
);
2547 bfd_info_free(&(group
->conf
->bfd_info
));
2549 group
->conf
->group
= NULL
;
2550 peer_delete(group
->conf
);
2552 /* Delete from all peer_group list. */
2553 listnode_delete(bgp
->group
, group
);
2555 peer_group_free(group
);
2560 int peer_group_remote_as_delete(struct peer_group
*group
)
2562 struct peer
*peer
, *other
;
2563 struct listnode
*node
, *nnode
;
2565 if ((group
->conf
->as_type
== AS_UNSPECIFIED
)
2566 || ((!group
->conf
->as
) && (group
->conf
->as_type
== AS_SPECIFIED
)))
2569 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2570 other
= peer
->doppelganger
;
2574 if (other
&& other
->status
!= Deleted
) {
2575 other
->group
= NULL
;
2579 list_delete_all_node(group
->peer
);
2581 group
->conf
->as
= 0;
2582 group
->conf
->as_type
= AS_UNSPECIFIED
;
2587 int peer_group_listen_range_add(struct peer_group
*group
, struct prefix
*range
)
2589 struct prefix
*prefix
;
2590 struct listnode
*node
, *nnode
;
2593 afi
= family2afi(range
->family
);
2595 /* Group needs remote AS configured. */
2596 if (group
->conf
->as_type
== AS_UNSPECIFIED
)
2597 return BGP_ERR_PEER_GROUP_NO_REMOTE_AS
;
2599 /* Ensure no duplicates. Currently we don't care about overlaps. */
2600 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
, prefix
)) {
2601 if (prefix_same(range
, prefix
))
2605 prefix
= prefix_new();
2606 prefix_copy(prefix
, range
);
2607 listnode_add(group
->listen_range
[afi
], prefix
);
2611 int peer_group_listen_range_del(struct peer_group
*group
, struct prefix
*range
)
2613 struct prefix
*prefix
, prefix2
;
2614 struct listnode
*node
, *nnode
;
2617 char buf
[PREFIX2STR_BUFFER
];
2619 afi
= family2afi(range
->family
);
2621 /* Identify the listen range. */
2622 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
, prefix
)) {
2623 if (prefix_same(range
, prefix
))
2628 return BGP_ERR_DYNAMIC_NEIGHBORS_RANGE_NOT_FOUND
;
2630 prefix2str(prefix
, buf
, sizeof(buf
));
2632 /* Dispose off any dynamic neighbors that exist due to this listen range
2634 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2635 if (!peer_dynamic_neighbor(peer
))
2638 sockunion2hostprefix(&peer
->su
, &prefix2
);
2639 if (prefix_match(prefix
, &prefix2
)) {
2640 if (bgp_debug_neighbor_events(peer
))
2642 "Deleting dynamic neighbor %s group %s upon "
2643 "delete of listen range %s",
2644 peer
->host
, group
->name
, buf
);
2649 /* Get rid of the listen range */
2650 listnode_delete(group
->listen_range
[afi
], prefix
);
2655 /* Bind specified peer to peer group. */
2656 int peer_group_bind(struct bgp
*bgp
, union sockunion
*su
, struct peer
*peer
,
2657 struct peer_group
*group
, as_t
*as
)
2659 int first_member
= 0;
2663 /* Lookup the peer. */
2665 peer
= peer_lookup(bgp
, su
);
2667 /* The peer exist, bind it to the peer-group */
2669 /* When the peer already belongs to a peer-group, check the
2671 if (peer_group_active(peer
)) {
2673 /* The peer is already bound to the peer-group,
2676 if (strcmp(peer
->group
->name
, group
->name
) == 0)
2679 return BGP_ERR_PEER_GROUP_CANT_CHANGE
;
2682 /* The peer has not specified a remote-as, inherit it from the
2684 if (peer
->as_type
== AS_UNSPECIFIED
) {
2685 peer
->as_type
= group
->conf
->as_type
;
2686 peer
->as
= group
->conf
->as
;
2689 if (!group
->conf
->as
) {
2690 if (peer_sort(group
->conf
) != BGP_PEER_INTERNAL
2691 && peer_sort(group
->conf
) != peer_sort(peer
)) {
2694 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT
;
2697 if (peer_sort(group
->conf
) == BGP_PEER_INTERNAL
)
2701 peer_group2peer_config_copy(group
, peer
);
2703 FOREACH_AFI_SAFI (afi
, safi
) {
2704 if (group
->conf
->afc
[afi
][safi
]) {
2705 peer
->afc
[afi
][safi
] = 1;
2707 if (peer_af_find(peer
, afi
, safi
)
2708 || peer_af_create(peer
, afi
, safi
)) {
2709 peer_group2peer_config_copy_af(
2710 group
, peer
, afi
, safi
);
2712 } else if (peer
->afc
[afi
][safi
])
2713 peer_deactivate(peer
, afi
, safi
);
2717 assert(group
&& peer
->group
== group
);
2719 listnode_delete(bgp
->peer
, peer
);
2721 peer
->group
= group
;
2722 listnode_add_sort(bgp
->peer
, peer
);
2724 peer
= peer_lock(peer
); /* group->peer list reference */
2725 listnode_add(group
->peer
, peer
);
2729 /* Advertisement-interval reset */
2730 if (!CHECK_FLAG(group
->conf
->flags
,
2731 PEER_FLAG_ROUTEADV
)) {
2732 group
->conf
->v_routeadv
=
2733 (peer_sort(group
->conf
)
2735 ? BGP_DEFAULT_IBGP_ROUTEADV
2736 : BGP_DEFAULT_EBGP_ROUTEADV
;
2739 /* ebgp-multihop reset */
2740 if (peer_sort(group
->conf
) == BGP_PEER_IBGP
)
2741 group
->conf
->ttl
= MAXTTL
;
2743 /* local-as reset */
2744 if (peer_sort(group
->conf
) != BGP_PEER_EBGP
) {
2745 group
->conf
->change_local_as
= 0;
2746 peer_flag_unset(group
->conf
,
2747 PEER_FLAG_LOCAL_AS
);
2748 peer_flag_unset(group
->conf
,
2749 PEER_FLAG_LOCAL_AS_NO_PREPEND
);
2750 peer_flag_unset(group
->conf
,
2751 PEER_FLAG_LOCAL_AS_REPLACE_AS
);
2755 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
2757 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
2758 peer
->last_reset
= PEER_DOWN_RMAP_BIND
;
2759 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2760 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2762 bgp_session_reset(peer
);
2766 /* Create a new peer. */
2768 if ((group
->conf
->as_type
== AS_SPECIFIED
)
2769 && (!group
->conf
->as
)) {
2770 return BGP_ERR_PEER_GROUP_NO_REMOTE_AS
;
2773 peer
= peer_create(su
, NULL
, bgp
, bgp
->as
, group
->conf
->as
,
2774 group
->conf
->as_type
, 0, 0, group
);
2776 peer
= peer_lock(peer
); /* group->peer list reference */
2777 listnode_add(group
->peer
, peer
);
2779 peer_group2peer_config_copy(group
, peer
);
2781 /* If the peer-group is active for this afi/safi then activate
2783 FOREACH_AFI_SAFI (afi
, safi
) {
2784 if (group
->conf
->afc
[afi
][safi
]) {
2785 peer
->afc
[afi
][safi
] = 1;
2786 peer_af_create(peer
, afi
, safi
);
2787 peer_group2peer_config_copy_af(group
, peer
, afi
,
2789 } else if (peer
->afc
[afi
][safi
])
2790 peer_deactivate(peer
, afi
, safi
);
2793 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
2795 /* Set up peer's events and timers. */
2796 if (peer_active(peer
))
2797 bgp_timer_set(peer
);
2803 static int bgp_startup_timer_expire(struct thread
*thread
)
2807 bgp
= THREAD_ARG(thread
);
2808 bgp
->t_startup
= NULL
;
2814 * On shutdown we call the cleanup function which
2815 * does a free of the link list nodes, free up
2816 * the data we are pointing at too.
2818 static void bgp_vrf_string_name_delete(void *data
)
2822 XFREE(MTYPE_TMP
, vname
);
2825 /* BGP instance creation by `router bgp' commands. */
2826 static struct bgp
*bgp_create(as_t
*as
, const char *name
,
2827 enum bgp_instance_type inst_type
)
2833 if ((bgp
= XCALLOC(MTYPE_BGP
, sizeof(struct bgp
))) == NULL
)
2836 if (BGP_DEBUG(zebra
, ZEBRA
)) {
2837 if (inst_type
== BGP_INSTANCE_TYPE_DEFAULT
)
2838 zlog_debug("Creating Default VRF, AS %u", *as
);
2840 zlog_debug("Creating %s %s, AS %u",
2841 (inst_type
== BGP_INSTANCE_TYPE_VRF
)
2848 bgp
->heuristic_coalesce
= true;
2849 bgp
->inst_type
= inst_type
;
2850 bgp
->vrf_id
= (inst_type
== BGP_INSTANCE_TYPE_DEFAULT
) ? VRF_DEFAULT
2852 bgp
->peer_self
= peer_new(bgp
);
2853 if (bgp
->peer_self
->host
)
2854 XFREE(MTYPE_BGP_PEER_HOST
, bgp
->peer_self
->host
);
2855 bgp
->peer_self
->host
=
2856 XSTRDUP(MTYPE_BGP_PEER_HOST
, "Static announcement");
2857 if (bgp
->peer_self
->hostname
!= NULL
) {
2858 XFREE(MTYPE_BGP_PEER_HOST
, bgp
->peer_self
->hostname
);
2859 bgp
->peer_self
->hostname
= NULL
;
2861 if (cmd_hostname_get())
2862 bgp
->peer_self
->hostname
=
2863 XSTRDUP(MTYPE_BGP_PEER_HOST
, cmd_hostname_get());
2865 if (bgp
->peer_self
->domainname
!= NULL
) {
2866 XFREE(MTYPE_BGP_PEER_HOST
, bgp
->peer_self
->domainname
);
2867 bgp
->peer_self
->domainname
= NULL
;
2869 if (cmd_domainname_get())
2870 bgp
->peer_self
->domainname
=
2871 XSTRDUP(MTYPE_BGP_PEER_HOST
, cmd_domainname_get());
2872 bgp
->peer
= list_new();
2873 bgp
->peer
->cmp
= (int (*)(void *, void *))peer_cmp
;
2874 bgp
->peerhash
= hash_create(peer_hash_key_make
, peer_hash_same
,
2876 bgp
->peerhash
->max_size
= BGP_PEER_MAX_HASH_SIZE
;
2878 bgp
->group
= list_new();
2879 bgp
->group
->cmp
= (int (*)(void *, void *))peer_group_cmp
;
2881 FOREACH_AFI_SAFI (afi
, safi
) {
2882 bgp
->route
[afi
][safi
] = bgp_table_init(bgp
, afi
, safi
);
2883 bgp
->aggregate
[afi
][safi
] = bgp_table_init(bgp
, afi
, safi
);
2884 bgp
->rib
[afi
][safi
] = bgp_table_init(bgp
, afi
, safi
);
2886 /* Enable maximum-paths */
2887 bgp_maximum_paths_set(bgp
, afi
, safi
, BGP_PEER_EBGP
,
2889 bgp_maximum_paths_set(bgp
, afi
, safi
, BGP_PEER_IBGP
,
2893 bgp
->v_update_delay
= BGP_UPDATE_DELAY_DEF
;
2894 bgp
->default_local_pref
= BGP_DEFAULT_LOCAL_PREF
;
2895 bgp
->default_subgroup_pkt_queue_max
=
2896 BGP_DEFAULT_SUBGROUP_PKT_QUEUE_MAX
;
2897 bgp
->default_holdtime
= BGP_DEFAULT_HOLDTIME
;
2898 bgp
->default_keepalive
= BGP_DEFAULT_KEEPALIVE
;
2899 bgp
->restart_time
= BGP_DEFAULT_RESTART_TIME
;
2900 bgp
->stalepath_time
= BGP_DEFAULT_STALEPATH_TIME
;
2901 bgp
->dynamic_neighbors_limit
= BGP_DYNAMIC_NEIGHBORS_LIMIT_DEFAULT
;
2902 bgp
->dynamic_neighbors_count
= 0;
2903 #if DFLT_BGP_IMPORT_CHECK
2904 bgp_flag_set(bgp
, BGP_FLAG_IMPORT_CHECK
);
2906 #if DFLT_BGP_SHOW_HOSTNAME
2907 bgp_flag_set(bgp
, BGP_FLAG_SHOW_HOSTNAME
);
2909 #if DFLT_BGP_LOG_NEIGHBOR_CHANGES
2910 bgp_flag_set(bgp
, BGP_FLAG_LOG_NEIGHBOR_CHANGES
);
2912 #if DFLT_BGP_DETERMINISTIC_MED
2913 bgp_flag_set(bgp
, BGP_FLAG_DETERMINISTIC_MED
);
2915 bgp_addpath_init_bgp_data(&bgp
->tx_addpath
);
2920 if (inst_type
!= BGP_INSTANCE_TYPE_VRF
) {
2921 bgp
->rfapi
= bgp_rfapi_new(bgp
);
2923 assert(bgp
->rfapi_cfg
);
2925 #endif /* ENABLE_BGP_VNC */
2927 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
2928 bgp
->vpn_policy
[afi
].bgp
= bgp
;
2929 bgp
->vpn_policy
[afi
].afi
= afi
;
2930 bgp
->vpn_policy
[afi
].tovpn_label
= MPLS_LABEL_NONE
;
2931 bgp
->vpn_policy
[afi
].tovpn_zebra_vrf_label_last_sent
=
2934 bgp
->vpn_policy
[afi
].import_vrf
= list_new();
2935 bgp
->vpn_policy
[afi
].import_vrf
->del
=
2936 bgp_vrf_string_name_delete
;
2937 bgp
->vpn_policy
[afi
].export_vrf
= list_new();
2938 bgp
->vpn_policy
[afi
].export_vrf
->del
=
2939 bgp_vrf_string_name_delete
;
2942 bgp
->name
= XSTRDUP(MTYPE_BGP
, name
);
2944 /* TODO - The startup timer needs to be run for the whole of BGP
2946 thread_add_timer(bm
->master
, bgp_startup_timer_expire
, bgp
,
2947 bgp
->restart_time
, &bgp
->t_startup
);
2950 /* printable name we can use in debug messages */
2951 if (inst_type
== BGP_INSTANCE_TYPE_DEFAULT
) {
2952 bgp
->name_pretty
= XSTRDUP(MTYPE_BGP
, "VRF default");
2962 len
= 4 + 1 + strlen(n
) + 1; /* "view foo\0" */
2964 bgp
->name_pretty
= XCALLOC(MTYPE_BGP
, len
);
2965 snprintf(bgp
->name_pretty
, len
, "%s %s",
2966 (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
)
2972 atomic_store_explicit(&bgp
->wpkt_quanta
, BGP_WRITE_PACKET_MAX
,
2973 memory_order_relaxed
);
2974 atomic_store_explicit(&bgp
->rpkt_quanta
, BGP_READ_PACKET_MAX
,
2975 memory_order_relaxed
);
2976 bgp
->coalesce_time
= BGP_DEFAULT_SUBGROUP_COALESCE_TIME
;
2980 update_bgp_group_init(bgp
);
2982 /* assign a unique rd id for auto derivation of vrf's RD */
2983 bf_assign_index(bm
->rd_idspace
, bgp
->vrf_rd_id
);
2990 /* Return the "default VRF" instance of BGP. */
2991 struct bgp
*bgp_get_default(void)
2994 struct listnode
*node
, *nnode
;
2996 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
))
2997 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_DEFAULT
)
3002 /* Lookup BGP entry. */
3003 struct bgp
*bgp_lookup(as_t as
, const char *name
)
3006 struct listnode
*node
, *nnode
;
3008 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
))
3010 && ((bgp
->name
== NULL
&& name
== NULL
)
3011 || (bgp
->name
&& name
&& strcmp(bgp
->name
, name
) == 0)))
3016 /* Lookup BGP structure by view name. */
3017 struct bgp
*bgp_lookup_by_name(const char *name
)
3020 struct listnode
*node
, *nnode
;
3022 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
))
3023 if ((bgp
->name
== NULL
&& name
== NULL
)
3024 || (bgp
->name
&& name
&& strcmp(bgp
->name
, name
) == 0))
3029 /* Lookup BGP instance based on VRF id. */
3030 /* Note: Only to be used for incoming messages from Zebra. */
3031 struct bgp
*bgp_lookup_by_vrf_id(vrf_id_t vrf_id
)
3035 /* Lookup VRF (in tree) and follow link. */
3036 vrf
= vrf_lookup_by_id(vrf_id
);
3039 return (vrf
->info
) ? (struct bgp
*)vrf
->info
: NULL
;
3042 /* handle socket creation or deletion, if necessary
3043 * this is called for all new BGP instances
3045 int bgp_handle_socket(struct bgp
*bgp
, struct vrf
*vrf
, vrf_id_t old_vrf_id
,
3050 /* Create BGP server socket, if listen mode not disabled */
3051 if (!bgp
|| bgp_option_check(BGP_OPT_NO_LISTEN
))
3053 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
) {
3055 * suppress vrf socket
3057 if (create
== FALSE
) {
3058 bgp_close_vrf_socket(bgp
);
3062 return BGP_ERR_INVALID_VALUE
;
3064 * if vrf_id did not change
3066 if (vrf
->vrf_id
== old_vrf_id
)
3068 if (old_vrf_id
!= VRF_UNKNOWN
) {
3069 /* look for old socket. close it. */
3070 bgp_close_vrf_socket(bgp
);
3072 /* if backend is not yet identified ( VRF_UNKNOWN) then
3073 * creation will be done later
3075 if (vrf
->vrf_id
== VRF_UNKNOWN
)
3077 ret
= bgp_socket(bgp
, bm
->port
, bm
->address
);
3079 return BGP_ERR_INVALID_VALUE
;
3082 return bgp_check_main_socket(create
, bgp
);
3085 /* Called from VTY commands. */
3086 int bgp_get(struct bgp
**bgp_val
, as_t
*as
, const char *name
,
3087 enum bgp_instance_type inst_type
)
3090 struct vrf
*vrf
= NULL
;
3092 /* Multiple instance check. */
3093 if (bgp_option_check(BGP_OPT_MULTIPLE_INSTANCE
)) {
3095 bgp
= bgp_lookup_by_name(name
);
3097 bgp
= bgp_get_default();
3099 /* Already exists. */
3101 if (bgp
->as
!= *as
) {
3103 return BGP_ERR_INSTANCE_MISMATCH
;
3105 if (bgp
->inst_type
!= inst_type
)
3106 return BGP_ERR_INSTANCE_MISMATCH
;
3111 /* BGP instance name can not be specified for single instance.
3114 return BGP_ERR_MULTIPLE_INSTANCE_NOT_SET
;
3116 /* Get default BGP structure if exists. */
3117 bgp
= bgp_get_default();
3120 if (bgp
->as
!= *as
) {
3122 return BGP_ERR_AS_MISMATCH
;
3129 bgp
= bgp_create(as
, name
, inst_type
);
3130 if (bgp_option_check(BGP_OPT_NO_ZEBRA
) && name
)
3131 bgp
->vrf_id
= vrf_generate_id();
3132 bgp_router_id_set(bgp
, &bgp
->router_id_zebra
);
3133 bgp_address_init(bgp
);
3134 bgp_tip_hash_init(bgp
);
3138 bgp
->t_rmap_def_originate_eval
= NULL
;
3140 /* If Default instance or VRF, link to the VRF structure, if present. */
3141 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_DEFAULT
3142 || bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
) {
3143 vrf
= bgp_vrf_lookup_by_instance_type(bgp
);
3145 bgp_vrf_link(bgp
, vrf
);
3147 /* BGP server socket already processed if BGP instance
3148 * already part of the list
3150 bgp_handle_socket(bgp
, vrf
, VRF_UNKNOWN
, true);
3151 listnode_add(bm
->bgp
, bgp
);
3153 if (IS_BGP_INST_KNOWN_TO_ZEBRA(bgp
)) {
3154 if (BGP_DEBUG(zebra
, ZEBRA
))
3155 zlog_debug("%s: Registering BGP instance %s to zebra",
3156 __PRETTY_FUNCTION__
, name
);
3157 bgp_zebra_instance_register(bgp
);
3164 * Make BGP instance "up". Applies only to VRFs (non-default) and
3165 * implies the VRF has been learnt from Zebra.
3167 void bgp_instance_up(struct bgp
*bgp
)
3170 struct listnode
*node
, *next
;
3172 /* Register with zebra. */
3173 bgp_zebra_instance_register(bgp
);
3175 /* Kick off any peers that may have been configured. */
3176 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
)) {
3177 if (!BGP_PEER_START_SUPPRESSED(peer
))
3178 BGP_EVENT_ADD(peer
, BGP_Start
);
3181 /* Process any networks that have been configured. */
3182 bgp_static_add(bgp
);
3186 * Make BGP instance "down". Applies only to VRFs (non-default) and
3187 * implies the VRF has been deleted by Zebra.
3189 void bgp_instance_down(struct bgp
*bgp
)
3192 struct listnode
*node
;
3193 struct listnode
*next
;
3196 if (bgp
->t_rmap_def_originate_eval
) {
3197 BGP_TIMER_OFF(bgp
->t_rmap_def_originate_eval
);
3198 bgp_unlock(bgp
); /* TODO - This timer is started with a lock -
3202 /* Bring down peers, so corresponding routes are purged. */
3203 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
)) {
3204 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
3205 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3206 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
);
3208 bgp_session_reset(peer
);
3211 /* Purge network and redistributed routes. */
3212 bgp_purge_static_redist_routes(bgp
);
3214 /* Cleanup registered nexthops (flags) */
3215 bgp_cleanup_nexthops(bgp
);
3218 /* Delete BGP instance. */
3219 int bgp_delete(struct bgp
*bgp
)
3222 struct peer_group
*group
;
3223 struct listnode
*node
, *next
;
3229 THREAD_OFF(bgp
->t_startup
);
3230 THREAD_OFF(bgp
->t_maxmed_onstartup
);
3231 THREAD_OFF(bgp
->t_update_delay
);
3232 THREAD_OFF(bgp
->t_establish_wait
);
3234 if (BGP_DEBUG(zebra
, ZEBRA
)) {
3235 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_DEFAULT
)
3236 zlog_debug("Deleting Default VRF");
3238 zlog_debug("Deleting %s %s",
3239 (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
)
3245 /* unmap from RT list */
3246 bgp_evpn_vrf_delete(bgp
);
3249 if (bgp
->t_rmap_def_originate_eval
) {
3250 BGP_TIMER_OFF(bgp
->t_rmap_def_originate_eval
);
3251 bgp_unlock(bgp
); /* TODO - This timer is started with a lock -
3255 /* Inform peers we're going down. */
3256 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
)) {
3257 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
3258 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3259 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
);
3262 /* Delete static routes (networks). */
3263 bgp_static_delete(bgp
);
3265 /* Unset redistribution. */
3266 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++)
3267 for (i
= 0; i
< ZEBRA_ROUTE_MAX
; i
++)
3268 if (i
!= ZEBRA_ROUTE_BGP
)
3269 bgp_redistribute_unset(bgp
, afi
, i
, 0);
3271 /* Free peers and peer-groups. */
3272 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, next
, group
))
3273 peer_group_delete(group
);
3275 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
))
3278 if (bgp
->peer_self
) {
3279 peer_delete(bgp
->peer_self
);
3280 bgp
->peer_self
= NULL
;
3283 update_bgp_group_free(bgp
);
3285 /* TODO - Other memory may need to be freed - e.g., NHT */
3290 bgp_cleanup_routes(bgp
);
3292 for (afi
= 0; afi
< AFI_MAX
; ++afi
) {
3293 if (!bgp
->vpn_policy
[afi
].import_redirect_rtlist
)
3296 &bgp
->vpn_policy
[afi
]
3297 .import_redirect_rtlist
);
3298 bgp
->vpn_policy
[afi
].import_redirect_rtlist
= NULL
;
3301 /* Deregister from Zebra, if needed */
3302 if (IS_BGP_INST_KNOWN_TO_ZEBRA(bgp
)) {
3303 if (BGP_DEBUG(zebra
, ZEBRA
))
3304 zlog_debug("%s: deregistering this bgp %s instance from zebra",
3305 __PRETTY_FUNCTION__
, bgp
->name
);
3306 bgp_zebra_instance_deregister(bgp
);
3309 /* Remove visibility via the master list - there may however still be
3310 * routes to be processed still referencing the struct bgp.
3312 listnode_delete(bm
->bgp
, bgp
);
3314 /* Free interfaces in this instance. */
3317 vrf
= bgp_vrf_lookup_by_instance_type(bgp
);
3318 bgp_handle_socket(bgp
, vrf
, VRF_UNKNOWN
, false);
3320 bgp_vrf_unlink(bgp
, vrf
);
3322 thread_master_free_unused(bm
->master
);
3323 bgp_unlock(bgp
); /* initial reference */
3328 void bgp_free(struct bgp
*bgp
)
3332 struct bgp_table
*table
;
3333 struct bgp_node
*rn
;
3334 struct bgp_rmap
*rmap
;
3338 list_delete(&bgp
->group
);
3339 list_delete(&bgp
->peer
);
3341 if (bgp
->peerhash
) {
3342 hash_free(bgp
->peerhash
);
3343 bgp
->peerhash
= NULL
;
3346 FOREACH_AFI_SAFI (afi
, safi
) {
3347 /* Special handling for 2-level routing tables. */
3348 if (safi
== SAFI_MPLS_VPN
|| safi
== SAFI_ENCAP
3349 || safi
== SAFI_EVPN
) {
3350 for (rn
= bgp_table_top(bgp
->rib
[afi
][safi
]); rn
;
3351 rn
= bgp_route_next(rn
)) {
3352 table
= (struct bgp_table
*)rn
->info
;
3353 bgp_table_finish(&table
);
3356 if (bgp
->route
[afi
][safi
])
3357 bgp_table_finish(&bgp
->route
[afi
][safi
]);
3358 if (bgp
->aggregate
[afi
][safi
])
3359 bgp_table_finish(&bgp
->aggregate
[afi
][safi
]);
3360 if (bgp
->rib
[afi
][safi
])
3361 bgp_table_finish(&bgp
->rib
[afi
][safi
]);
3362 rmap
= &bgp
->table_map
[afi
][safi
];
3364 XFREE(MTYPE_ROUTE_MAP_NAME
, rmap
->name
);
3367 bgp_scan_finish(bgp
);
3368 bgp_address_destroy(bgp
);
3369 bgp_tip_hash_destroy(bgp
);
3371 /* release the auto RD id */
3372 bf_release_index(bm
->rd_idspace
, bgp
->vrf_rd_id
);
3374 bgp_evpn_cleanup(bgp
);
3375 bgp_pbr_cleanup(bgp
);
3377 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
3378 vpn_policy_direction_t dir
;
3380 if (bgp
->vpn_policy
[afi
].import_vrf
)
3381 list_delete(&bgp
->vpn_policy
[afi
].import_vrf
);
3382 if (bgp
->vpn_policy
[afi
].export_vrf
)
3383 list_delete(&bgp
->vpn_policy
[afi
].export_vrf
);
3385 dir
= BGP_VPN_POLICY_DIR_FROMVPN
;
3386 if (bgp
->vpn_policy
[afi
].rtlist
[dir
])
3387 ecommunity_free(&bgp
->vpn_policy
[afi
].rtlist
[dir
]);
3388 dir
= BGP_VPN_POLICY_DIR_TOVPN
;
3389 if (bgp
->vpn_policy
[afi
].rtlist
[dir
])
3390 ecommunity_free(&bgp
->vpn_policy
[afi
].rtlist
[dir
]);
3394 XFREE(MTYPE_BGP
, bgp
->name
);
3395 if (bgp
->name_pretty
)
3396 XFREE(MTYPE_BGP
, bgp
->name_pretty
);
3398 XFREE(MTYPE_BGP
, bgp
);
3401 struct peer
*peer_lookup_by_conf_if(struct bgp
*bgp
, const char *conf_if
)
3404 struct listnode
*node
, *nnode
;
3410 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3411 if (peer
->conf_if
&& !strcmp(peer
->conf_if
, conf_if
)
3412 && !CHECK_FLAG(peer
->sflags
,
3413 PEER_STATUS_ACCEPT_PEER
))
3415 } else if (bm
->bgp
!= NULL
) {
3416 struct listnode
*bgpnode
, *nbgpnode
;
3418 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
))
3419 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3421 && !strcmp(peer
->conf_if
, conf_if
)
3422 && !CHECK_FLAG(peer
->sflags
,
3423 PEER_STATUS_ACCEPT_PEER
))
3429 struct peer
*peer_lookup_by_hostname(struct bgp
*bgp
, const char *hostname
)
3432 struct listnode
*node
, *nnode
;
3438 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3439 if (peer
->hostname
&& !strcmp(peer
->hostname
, hostname
)
3440 && !CHECK_FLAG(peer
->sflags
,
3441 PEER_STATUS_ACCEPT_PEER
))
3443 } else if (bm
->bgp
!= NULL
) {
3444 struct listnode
*bgpnode
, *nbgpnode
;
3446 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
))
3447 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3449 && !strcmp(peer
->hostname
, hostname
)
3450 && !CHECK_FLAG(peer
->sflags
,
3451 PEER_STATUS_ACCEPT_PEER
))
3457 struct peer
*peer_lookup(struct bgp
*bgp
, union sockunion
*su
)
3459 struct peer
*peer
= NULL
;
3460 struct peer tmp_peer
;
3462 memset(&tmp_peer
, 0, sizeof(struct peer
));
3465 * We do not want to find the doppelganger peer so search for the peer
3467 * the hash that has PEER_FLAG_CONFIG_NODE
3469 SET_FLAG(tmp_peer
.flags
, PEER_FLAG_CONFIG_NODE
);
3474 peer
= hash_lookup(bgp
->peerhash
, &tmp_peer
);
3475 } else if (bm
->bgp
!= NULL
) {
3476 struct listnode
*bgpnode
, *nbgpnode
;
3478 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
)) {
3479 peer
= hash_lookup(bgp
->peerhash
, &tmp_peer
);
3488 struct peer
*peer_create_bind_dynamic_neighbor(struct bgp
*bgp
,
3489 union sockunion
*su
,
3490 struct peer_group
*group
)
3496 /* Create peer first; we've already checked group config is valid. */
3497 peer
= peer_create(su
, NULL
, bgp
, bgp
->as
, group
->conf
->as
,
3498 group
->conf
->as_type
, 0, 0, group
);
3503 peer
= peer_lock(peer
);
3504 listnode_add(group
->peer
, peer
);
3506 peer_group2peer_config_copy(group
, peer
);
3509 * Bind peer for all AFs configured for the group. We don't call
3510 * peer_group_bind as that is sub-optimal and does some stuff we don't
3513 FOREACH_AFI_SAFI (afi
, safi
) {
3514 if (!group
->conf
->afc
[afi
][safi
])
3516 peer
->afc
[afi
][safi
] = 1;
3518 if (!peer_af_find(peer
, afi
, safi
))
3519 peer_af_create(peer
, afi
, safi
);
3521 peer_group2peer_config_copy_af(group
, peer
, afi
, safi
);
3524 /* Mark as dynamic, but also as a "config node" for other things to
3526 SET_FLAG(peer
->flags
, PEER_FLAG_DYNAMIC_NEIGHBOR
);
3527 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
3533 peer_group_lookup_dynamic_neighbor_range(struct peer_group
*group
,
3534 struct prefix
*prefix
)
3536 struct listnode
*node
, *nnode
;
3537 struct prefix
*range
;
3540 afi
= family2afi(prefix
->family
);
3542 if (group
->listen_range
[afi
])
3543 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
,
3545 if (prefix_match(range
, prefix
))
3552 peer_group_lookup_dynamic_neighbor(struct bgp
*bgp
, struct prefix
*prefix
,
3553 struct prefix
**listen_range
)
3555 struct prefix
*range
= NULL
;
3556 struct peer_group
*group
= NULL
;
3557 struct listnode
*node
, *nnode
;
3559 *listen_range
= NULL
;
3561 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
))
3562 if ((range
= peer_group_lookup_dynamic_neighbor_range(
3565 } else if (bm
->bgp
!= NULL
) {
3566 struct listnode
*bgpnode
, *nbgpnode
;
3568 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
))
3569 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
))
3570 if ((range
= peer_group_lookup_dynamic_neighbor_range(
3576 *listen_range
= range
;
3577 return (group
&& range
) ? group
: NULL
;
3580 struct peer
*peer_lookup_dynamic_neighbor(struct bgp
*bgp
, union sockunion
*su
)
3582 struct peer_group
*group
;
3585 struct prefix prefix
;
3586 struct prefix
*listen_range
;
3588 char buf
[PREFIX2STR_BUFFER
];
3589 char buf1
[PREFIX2STR_BUFFER
];
3591 sockunion2hostprefix(su
, &prefix
);
3593 /* See if incoming connection matches a configured listen range. */
3594 group
= peer_group_lookup_dynamic_neighbor(bgp
, &prefix
, &listen_range
);
3605 prefix2str(&prefix
, buf
, sizeof(buf
));
3606 prefix2str(listen_range
, buf1
, sizeof(buf1
));
3608 if (bgp_debug_neighbor_events(NULL
))
3610 "Dynamic Neighbor %s matches group %s listen range %s",
3611 buf
, group
->name
, buf1
);
3613 /* Are we within the listen limit? */
3614 dncount
= gbgp
->dynamic_neighbors_count
;
3616 if (dncount
>= gbgp
->dynamic_neighbors_limit
) {
3617 if (bgp_debug_neighbor_events(NULL
))
3618 zlog_debug("Dynamic Neighbor %s rejected - at limit %d",
3619 inet_sutop(su
, buf
),
3620 gbgp
->dynamic_neighbors_limit
);
3624 /* Ensure group is not disabled. */
3625 if (CHECK_FLAG(group
->conf
->flags
, PEER_FLAG_SHUTDOWN
)) {
3626 if (bgp_debug_neighbor_events(NULL
))
3628 "Dynamic Neighbor %s rejected - group %s disabled",
3633 /* Check that at least one AF is activated for the group. */
3634 if (!peer_group_af_configured(group
)) {
3635 if (bgp_debug_neighbor_events(NULL
))
3637 "Dynamic Neighbor %s rejected - no AF activated for group %s",
3642 /* Create dynamic peer and bind to associated group. */
3643 peer
= peer_create_bind_dynamic_neighbor(gbgp
, su
, group
);
3646 gbgp
->dynamic_neighbors_count
= ++dncount
;
3648 if (bgp_debug_neighbor_events(peer
))
3649 zlog_debug("%s Dynamic Neighbor added, group %s count %d",
3650 peer
->host
, group
->name
, dncount
);
3655 static void peer_drop_dynamic_neighbor(struct peer
*peer
)
3658 if (peer
->group
->bgp
) {
3659 dncount
= peer
->group
->bgp
->dynamic_neighbors_count
;
3661 peer
->group
->bgp
->dynamic_neighbors_count
= --dncount
;
3663 if (bgp_debug_neighbor_events(peer
))
3664 zlog_debug("%s dropped from group %s, count %d", peer
->host
,
3665 peer
->group
->name
, dncount
);
3668 /* If peer is configured at least one address family return 1. */
3669 int peer_active(struct peer
*peer
)
3671 if (BGP_PEER_SU_UNSPEC(peer
))
3673 if (peer
->afc
[AFI_IP
][SAFI_UNICAST
] || peer
->afc
[AFI_IP
][SAFI_MULTICAST
]
3674 || peer
->afc
[AFI_IP
][SAFI_LABELED_UNICAST
]
3675 || peer
->afc
[AFI_IP
][SAFI_MPLS_VPN
] || peer
->afc
[AFI_IP
][SAFI_ENCAP
]
3676 || peer
->afc
[AFI_IP
][SAFI_FLOWSPEC
]
3677 || peer
->afc
[AFI_IP6
][SAFI_UNICAST
]
3678 || peer
->afc
[AFI_IP6
][SAFI_MULTICAST
]
3679 || peer
->afc
[AFI_IP6
][SAFI_LABELED_UNICAST
]
3680 || peer
->afc
[AFI_IP6
][SAFI_MPLS_VPN
]
3681 || peer
->afc
[AFI_IP6
][SAFI_ENCAP
]
3682 || peer
->afc
[AFI_IP6
][SAFI_FLOWSPEC
]
3683 || peer
->afc
[AFI_L2VPN
][SAFI_EVPN
])
3688 /* If peer is negotiated at least one address family return 1. */
3689 int peer_active_nego(struct peer
*peer
)
3691 if (peer
->afc_nego
[AFI_IP
][SAFI_UNICAST
]
3692 || peer
->afc_nego
[AFI_IP
][SAFI_MULTICAST
]
3693 || peer
->afc_nego
[AFI_IP
][SAFI_LABELED_UNICAST
]
3694 || peer
->afc_nego
[AFI_IP
][SAFI_MPLS_VPN
]
3695 || peer
->afc_nego
[AFI_IP
][SAFI_ENCAP
]
3696 || peer
->afc_nego
[AFI_IP
][SAFI_FLOWSPEC
]
3697 || peer
->afc_nego
[AFI_IP6
][SAFI_UNICAST
]
3698 || peer
->afc_nego
[AFI_IP6
][SAFI_MULTICAST
]
3699 || peer
->afc_nego
[AFI_IP6
][SAFI_LABELED_UNICAST
]
3700 || peer
->afc_nego
[AFI_IP6
][SAFI_MPLS_VPN
]
3701 || peer
->afc_nego
[AFI_IP6
][SAFI_ENCAP
]
3702 || peer
->afc_nego
[AFI_IP6
][SAFI_FLOWSPEC
]
3703 || peer
->afc_nego
[AFI_L2VPN
][SAFI_EVPN
])
3708 void peer_change_action(struct peer
*peer
, afi_t afi
, safi_t safi
,
3709 enum peer_change_type type
)
3711 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
3714 if (peer
->status
!= Established
)
3717 if (type
== peer_change_reset
) {
3718 /* If we're resetting session, we've to delete both peer struct
3720 if ((peer
->doppelganger
)
3721 && (peer
->doppelganger
->status
!= Deleted
)
3722 && (!CHECK_FLAG(peer
->doppelganger
->flags
,
3723 PEER_FLAG_CONFIG_NODE
)))
3724 peer_delete(peer
->doppelganger
);
3726 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3727 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
3728 } else if (type
== peer_change_reset_in
) {
3729 if (CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_OLD_RCV
)
3730 || CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_NEW_RCV
))
3731 bgp_route_refresh_send(peer
, afi
, safi
, 0, 0, 0);
3733 if ((peer
->doppelganger
)
3734 && (peer
->doppelganger
->status
!= Deleted
)
3735 && (!CHECK_FLAG(peer
->doppelganger
->flags
,
3736 PEER_FLAG_CONFIG_NODE
)))
3737 peer_delete(peer
->doppelganger
);
3739 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3740 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
3742 } else if (type
== peer_change_reset_out
) {
3743 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
3744 bgp_announce_route(peer
, afi
, safi
);
3748 struct peer_flag_action
{
3752 /* This flag can be set for peer-group member. */
3753 uint8_t not_for_member
;
3755 /* Action when the flag is changed. */
3756 enum peer_change_type type
;
3759 static const struct peer_flag_action peer_flag_action_list
[] = {
3760 {PEER_FLAG_PASSIVE
, 0, peer_change_reset
},
3761 {PEER_FLAG_SHUTDOWN
, 0, peer_change_reset
},
3762 {PEER_FLAG_DONT_CAPABILITY
, 0, peer_change_none
},
3763 {PEER_FLAG_OVERRIDE_CAPABILITY
, 0, peer_change_none
},
3764 {PEER_FLAG_STRICT_CAP_MATCH
, 0, peer_change_none
},
3765 {PEER_FLAG_DYNAMIC_CAPABILITY
, 0, peer_change_reset
},
3766 {PEER_FLAG_DISABLE_CONNECTED_CHECK
, 0, peer_change_reset
},
3767 {PEER_FLAG_CAPABILITY_ENHE
, 0, peer_change_reset
},
3768 {PEER_FLAG_ENFORCE_FIRST_AS
, 0, peer_change_reset_in
},
3769 {PEER_FLAG_ROUTEADV
, 0, peer_change_none
},
3770 {PEER_FLAG_TIMER
, 0, peer_change_none
},
3771 {PEER_FLAG_TIMER_CONNECT
, 0, peer_change_none
},
3772 {PEER_FLAG_PASSWORD
, 0, peer_change_none
},
3773 {PEER_FLAG_LOCAL_AS
, 0, peer_change_none
},
3774 {PEER_FLAG_LOCAL_AS_NO_PREPEND
, 0, peer_change_none
},
3775 {PEER_FLAG_LOCAL_AS_REPLACE_AS
, 0, peer_change_none
},
3776 {PEER_FLAG_UPDATE_SOURCE
, 0, peer_change_none
},
3779 static const struct peer_flag_action peer_af_flag_action_list
[] = {
3780 {PEER_FLAG_SEND_COMMUNITY
, 1, peer_change_reset_out
},
3781 {PEER_FLAG_SEND_EXT_COMMUNITY
, 1, peer_change_reset_out
},
3782 {PEER_FLAG_SEND_LARGE_COMMUNITY
, 1, peer_change_reset_out
},
3783 {PEER_FLAG_NEXTHOP_SELF
, 1, peer_change_reset_out
},
3784 {PEER_FLAG_REFLECTOR_CLIENT
, 1, peer_change_reset
},
3785 {PEER_FLAG_RSERVER_CLIENT
, 1, peer_change_reset
},
3786 {PEER_FLAG_SOFT_RECONFIG
, 0, peer_change_reset_in
},
3787 {PEER_FLAG_AS_PATH_UNCHANGED
, 1, peer_change_reset_out
},
3788 {PEER_FLAG_NEXTHOP_UNCHANGED
, 1, peer_change_reset_out
},
3789 {PEER_FLAG_MED_UNCHANGED
, 1, peer_change_reset_out
},
3790 {PEER_FLAG_DEFAULT_ORIGINATE
, 0, peer_change_none
},
3791 {PEER_FLAG_REMOVE_PRIVATE_AS
, 1, peer_change_reset_out
},
3792 {PEER_FLAG_ALLOWAS_IN
, 0, peer_change_reset_in
},
3793 {PEER_FLAG_ALLOWAS_IN_ORIGIN
, 0, peer_change_reset_in
},
3794 {PEER_FLAG_ORF_PREFIX_SM
, 1, peer_change_reset
},
3795 {PEER_FLAG_ORF_PREFIX_RM
, 1, peer_change_reset
},
3796 {PEER_FLAG_MAX_PREFIX
, 0, peer_change_none
},
3797 {PEER_FLAG_MAX_PREFIX_WARNING
, 0, peer_change_none
},
3798 {PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED
, 0, peer_change_reset_out
},
3799 {PEER_FLAG_FORCE_NEXTHOP_SELF
, 1, peer_change_reset_out
},
3800 {PEER_FLAG_REMOVE_PRIVATE_AS_ALL
, 1, peer_change_reset_out
},
3801 {PEER_FLAG_REMOVE_PRIVATE_AS_REPLACE
, 1, peer_change_reset_out
},
3802 {PEER_FLAG_AS_OVERRIDE
, 1, peer_change_reset_out
},
3803 {PEER_FLAG_REMOVE_PRIVATE_AS_ALL_REPLACE
, 1, peer_change_reset_out
},
3804 {PEER_FLAG_WEIGHT
, 0, peer_change_reset_in
},
3807 /* Proper action set. */
3808 static int peer_flag_action_set(const struct peer_flag_action
*action_list
,
3809 int size
, struct peer_flag_action
*action
,
3816 const struct peer_flag_action
*match
= NULL
;
3818 /* Check peer's frag action. */
3819 for (i
= 0; i
< size
; i
++) {
3820 match
= &action_list
[i
];
3822 if (match
->flag
== 0)
3825 if (match
->flag
& flag
) {
3828 if (match
->type
== peer_change_reset_in
)
3830 if (match
->type
== peer_change_reset_out
)
3832 if (match
->type
== peer_change_reset
) {
3836 if (match
->not_for_member
)
3837 action
->not_for_member
= 1;
3841 /* Set peer clear type. */
3842 if (reset_in
&& reset_out
)
3843 action
->type
= peer_change_reset
;
3845 action
->type
= peer_change_reset_in
;
3847 action
->type
= peer_change_reset_out
;
3849 action
->type
= peer_change_none
;
3854 static void peer_flag_modify_action(struct peer
*peer
, uint32_t flag
)
3856 if (flag
== PEER_FLAG_SHUTDOWN
) {
3857 if (CHECK_FLAG(peer
->flags
, flag
)) {
3858 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
))
3859 peer_nsf_stop(peer
);
3861 UNSET_FLAG(peer
->sflags
, PEER_STATUS_PREFIX_OVERFLOW
);
3862 if (peer
->t_pmax_restart
) {
3863 BGP_TIMER_OFF(peer
->t_pmax_restart
);
3864 if (bgp_debug_neighbor_events(peer
))
3866 "%s Maximum-prefix restart timer canceled",
3870 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
))
3871 peer_nsf_stop(peer
);
3873 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
3874 char *msg
= peer
->tx_shutdown_message
;
3877 if (!msg
&& peer_group_active(peer
))
3878 msg
= peer
->group
->conf
3879 ->tx_shutdown_message
;
3880 msglen
= msg
? strlen(msg
) : 0;
3885 uint8_t msgbuf
[129];
3888 memcpy(msgbuf
+ 1, msg
, msglen
);
3890 bgp_notify_send_with_data(
3891 peer
, BGP_NOTIFY_CEASE
,
3892 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
,
3893 msgbuf
, msglen
+ 1);
3896 peer
, BGP_NOTIFY_CEASE
,
3897 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
);
3899 bgp_session_reset(peer
);
3901 peer
->v_start
= BGP_INIT_START_TIMER
;
3902 BGP_EVENT_ADD(peer
, BGP_Stop
);
3904 } else if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
3905 if (flag
== PEER_FLAG_DYNAMIC_CAPABILITY
)
3906 peer
->last_reset
= PEER_DOWN_CAPABILITY_CHANGE
;
3907 else if (flag
== PEER_FLAG_PASSIVE
)
3908 peer
->last_reset
= PEER_DOWN_PASSIVE_CHANGE
;
3909 else if (flag
== PEER_FLAG_DISABLE_CONNECTED_CHECK
)
3910 peer
->last_reset
= PEER_DOWN_MULTIHOP_CHANGE
;
3912 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3913 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
3915 bgp_session_reset(peer
);
3918 /* Change specified peer flag. */
3919 static int peer_flag_modify(struct peer
*peer
, uint32_t flag
, int set
)
3923 bool invert
, member_invert
;
3924 struct peer
*member
;
3925 struct listnode
*node
, *nnode
;
3926 struct peer_flag_action action
;
3928 memset(&action
, 0, sizeof(struct peer_flag_action
));
3929 size
= sizeof peer_flag_action_list
/ sizeof(struct peer_flag_action
);
3931 invert
= CHECK_FLAG(peer
->flags_invert
, flag
);
3932 found
= peer_flag_action_set(peer_flag_action_list
, size
, &action
,
3935 /* Abort if no flag action exists. */
3937 return BGP_ERR_INVALID_FLAG
;
3939 /* Check for flag conflict: STRICT_CAP_MATCH && OVERRIDE_CAPABILITY */
3940 if (set
&& CHECK_FLAG(peer
->flags
| flag
, PEER_FLAG_STRICT_CAP_MATCH
)
3941 && CHECK_FLAG(peer
->flags
| flag
, PEER_FLAG_OVERRIDE_CAPABILITY
))
3942 return BGP_ERR_PEER_FLAG_CONFLICT
;
3944 /* Handle flag updates where desired state matches current state. */
3945 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
3946 if (set
&& CHECK_FLAG(peer
->flags
, flag
)) {
3947 COND_FLAG(peer
->flags_override
, flag
, !invert
);
3951 if (!set
&& !CHECK_FLAG(peer
->flags
, flag
)) {
3952 COND_FLAG(peer
->flags_override
, flag
, invert
);
3957 /* Inherit from peer-group or set/unset flags accordingly. */
3958 if (peer_group_active(peer
) && set
== invert
)
3959 peer_flag_inherit(peer
, flag
);
3961 COND_FLAG(peer
->flags
, flag
, set
);
3963 /* Check if handling a regular peer. */
3964 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
3965 /* Update flag override state accordingly. */
3966 COND_FLAG(peer
->flags_override
, flag
, set
!= invert
);
3968 /* Execute flag action on peer. */
3969 if (action
.type
== peer_change_reset
)
3970 peer_flag_modify_action(peer
, flag
);
3972 /* Skip peer-group mechanics for regular peers. */
3976 if (set
&& flag
== PEER_FLAG_CAPABILITY_ENHE
)
3977 bgp_nht_register_enhe_capability_interfaces(peer
);
3980 * Update peer-group members, unless they are explicitely overriding
3981 * peer-group configuration.
3983 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
3984 /* Skip peers with overridden configuration. */
3985 if (CHECK_FLAG(member
->flags_override
, flag
))
3988 /* Check if only member without group is inverted. */
3990 CHECK_FLAG(member
->flags_invert
, flag
) && !invert
;
3992 /* Skip peers with equivalent configuration. */
3993 if (set
!= member_invert
&& CHECK_FLAG(member
->flags
, flag
))
3996 if (set
== member_invert
&& !CHECK_FLAG(member
->flags
, flag
))
3999 /* Update flag on peer-group member. */
4000 COND_FLAG(member
->flags
, flag
, set
!= member_invert
);
4002 if (set
&& flag
== PEER_FLAG_CAPABILITY_ENHE
)
4003 bgp_nht_register_enhe_capability_interfaces(member
);
4005 /* Execute flag action on peer-group member. */
4006 if (action
.type
== peer_change_reset
)
4007 peer_flag_modify_action(member
, flag
);
4013 int peer_flag_set(struct peer
*peer
, uint32_t flag
)
4015 return peer_flag_modify(peer
, flag
, 1);
4018 int peer_flag_unset(struct peer
*peer
, uint32_t flag
)
4020 return peer_flag_modify(peer
, flag
, 0);
4023 static int peer_af_flag_modify(struct peer
*peer
, afi_t afi
, safi_t safi
,
4024 uint32_t flag
, bool set
)
4028 bool invert
, member_invert
;
4029 struct peer
*member
;
4030 struct listnode
*node
, *nnode
;
4031 struct peer_flag_action action
;
4033 memset(&action
, 0, sizeof(struct peer_flag_action
));
4034 size
= sizeof peer_af_flag_action_list
4035 / sizeof(struct peer_flag_action
);
4037 invert
= CHECK_FLAG(peer
->af_flags_invert
[afi
][safi
], flag
);
4038 found
= peer_flag_action_set(peer_af_flag_action_list
, size
, &action
,
4041 /* Abort if flag action exists. */
4043 return BGP_ERR_INVALID_FLAG
;
4045 /* Special check for reflector client. */
4046 if (flag
& PEER_FLAG_REFLECTOR_CLIENT
4047 && peer_sort(peer
) != BGP_PEER_IBGP
)
4048 return BGP_ERR_NOT_INTERNAL_PEER
;
4050 /* Special check for remove-private-AS. */
4051 if (flag
& PEER_FLAG_REMOVE_PRIVATE_AS
4052 && peer_sort(peer
) == BGP_PEER_IBGP
)
4053 return BGP_ERR_REMOVE_PRIVATE_AS
;
4055 /* as-override is not allowed for IBGP peers */
4056 if (flag
& PEER_FLAG_AS_OVERRIDE
&& peer_sort(peer
) == BGP_PEER_IBGP
)
4057 return BGP_ERR_AS_OVERRIDE
;
4059 /* Handle flag updates where desired state matches current state. */
4060 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4061 if (set
&& CHECK_FLAG(peer
->af_flags
[afi
][safi
], flag
)) {
4062 COND_FLAG(peer
->af_flags_override
[afi
][safi
], flag
,
4067 if (!set
&& !CHECK_FLAG(peer
->af_flags
[afi
][safi
], flag
)) {
4068 COND_FLAG(peer
->af_flags_override
[afi
][safi
], flag
,
4075 * For EVPN we implicitly set the NEXTHOP_UNCHANGED flag,
4076 * if we are setting/unsetting flags which conflict with this flag
4077 * handle accordingly
4079 if (afi
== AFI_L2VPN
&& safi
== SAFI_EVPN
) {
4083 * if we are setting NEXTHOP_SELF, we need to unset the
4084 * NEXTHOP_UNCHANGED flag
4086 if (CHECK_FLAG(flag
, PEER_FLAG_NEXTHOP_SELF
) ||
4087 CHECK_FLAG(flag
, PEER_FLAG_FORCE_NEXTHOP_SELF
))
4088 UNSET_FLAG(peer
->af_flags
[afi
][safi
],
4089 PEER_FLAG_NEXTHOP_UNCHANGED
);
4093 * if we are unsetting NEXTHOP_SELF, we need to set the
4094 * NEXTHOP_UNCHANGED flag to reset the defaults for EVPN
4096 if (CHECK_FLAG(flag
, PEER_FLAG_NEXTHOP_SELF
) ||
4097 CHECK_FLAG(flag
, PEER_FLAG_FORCE_NEXTHOP_SELF
))
4098 SET_FLAG(peer
->af_flags
[afi
][safi
],
4099 PEER_FLAG_NEXTHOP_UNCHANGED
);
4103 /* Inherit from peer-group or set/unset flags accordingly. */
4104 if (peer_group_active(peer
) && set
== invert
)
4105 peer_af_flag_inherit(peer
, afi
, safi
, flag
);
4107 COND_FLAG(peer
->af_flags
[afi
][safi
], flag
, set
);
4109 /* Execute action when peer is established. */
4110 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)
4111 && peer
->status
== Established
) {
4112 if (!set
&& flag
== PEER_FLAG_SOFT_RECONFIG
)
4113 bgp_clear_adj_in(peer
, afi
, safi
);
4115 if (flag
== PEER_FLAG_REFLECTOR_CLIENT
)
4116 peer
->last_reset
= PEER_DOWN_RR_CLIENT_CHANGE
;
4117 else if (flag
== PEER_FLAG_RSERVER_CLIENT
)
4118 peer
->last_reset
= PEER_DOWN_RS_CLIENT_CHANGE
;
4119 else if (flag
== PEER_FLAG_ORF_PREFIX_SM
)
4120 peer
->last_reset
= PEER_DOWN_CAPABILITY_CHANGE
;
4121 else if (flag
== PEER_FLAG_ORF_PREFIX_RM
)
4122 peer
->last_reset
= PEER_DOWN_CAPABILITY_CHANGE
;
4124 peer_change_action(peer
, afi
, safi
, action
.type
);
4128 /* Check if handling a regular peer. */
4129 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4130 COND_FLAG(peer
->af_flags_override
[afi
][safi
], flag
,
4134 * Update peer-group members, unless they are explicitely
4135 * overriding peer-group configuration.
4137 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
,
4139 /* Skip peers with overridden configuration. */
4140 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4144 /* Check if only member without group is inverted. */
4146 CHECK_FLAG(member
->af_flags_invert
[afi
][safi
],
4150 /* Skip peers with equivalent configuration. */
4151 if (set
!= member_invert
4152 && CHECK_FLAG(member
->af_flags
[afi
][safi
], flag
))
4155 if (set
== member_invert
4156 && !CHECK_FLAG(member
->af_flags
[afi
][safi
], flag
))
4159 /* Update flag on peer-group member. */
4160 COND_FLAG(member
->af_flags
[afi
][safi
], flag
,
4161 set
!= member_invert
);
4163 /* Execute flag action on peer-group member. */
4164 if (member
->status
== Established
) {
4165 if (!set
&& flag
== PEER_FLAG_SOFT_RECONFIG
)
4166 bgp_clear_adj_in(member
, afi
, safi
);
4168 if (flag
== PEER_FLAG_REFLECTOR_CLIENT
)
4169 member
->last_reset
=
4170 PEER_DOWN_RR_CLIENT_CHANGE
;
4172 == PEER_FLAG_RSERVER_CLIENT
)
4173 member
->last_reset
=
4174 PEER_DOWN_RS_CLIENT_CHANGE
;
4176 == PEER_FLAG_ORF_PREFIX_SM
)
4177 member
->last_reset
=
4178 PEER_DOWN_CAPABILITY_CHANGE
;
4180 == PEER_FLAG_ORF_PREFIX_RM
)
4181 member
->last_reset
=
4182 PEER_DOWN_CAPABILITY_CHANGE
;
4184 peer_change_action(member
, afi
, safi
,
4194 int peer_af_flag_set(struct peer
*peer
, afi_t afi
, safi_t safi
, uint32_t flag
)
4196 return peer_af_flag_modify(peer
, afi
, safi
, flag
, 1);
4199 int peer_af_flag_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, uint32_t flag
)
4201 return peer_af_flag_modify(peer
, afi
, safi
, flag
, 0);
4205 int peer_tx_shutdown_message_set(struct peer
*peer
, const char *msg
)
4207 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG
, peer
->tx_shutdown_message
);
4208 peer
->tx_shutdown_message
=
4209 msg
? XSTRDUP(MTYPE_PEER_TX_SHUTDOWN_MSG
, msg
) : NULL
;
4213 int peer_tx_shutdown_message_unset(struct peer
*peer
)
4215 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG
, peer
->tx_shutdown_message
);
4220 /* EBGP multihop configuration. */
4221 int peer_ebgp_multihop_set(struct peer
*peer
, int ttl
)
4223 struct peer_group
*group
;
4224 struct listnode
*node
, *nnode
;
4227 if (peer
->sort
== BGP_PEER_IBGP
|| peer
->conf_if
)
4230 /* see comment in peer_ttl_security_hops_set() */
4231 if (ttl
!= MAXTTL
) {
4232 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4233 group
= peer
->group
;
4234 if (group
->conf
->gtsm_hops
!= 0)
4235 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4237 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
,
4239 if (peer1
->sort
== BGP_PEER_IBGP
)
4242 if (peer1
->gtsm_hops
!= 0)
4243 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4246 if (peer
->gtsm_hops
!= 0)
4247 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4253 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4254 if (peer
->fd
>= 0 && peer
->sort
!= BGP_PEER_IBGP
) {
4255 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4256 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4257 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4259 bgp_session_reset(peer
);
4262 group
= peer
->group
;
4263 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
4264 if (peer
->sort
== BGP_PEER_IBGP
)
4267 peer
->ttl
= group
->conf
->ttl
;
4269 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4270 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4271 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4273 bgp_session_reset(peer
);
4279 int peer_ebgp_multihop_unset(struct peer
*peer
)
4281 struct peer_group
*group
;
4282 struct listnode
*node
, *nnode
;
4284 if (peer
->sort
== BGP_PEER_IBGP
)
4287 if (peer
->gtsm_hops
!= 0 && peer
->ttl
!= MAXTTL
)
4288 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4290 if (peer_group_active(peer
))
4291 peer
->ttl
= peer
->group
->conf
->ttl
;
4295 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4296 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4297 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4298 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4300 bgp_session_reset(peer
);
4302 group
= peer
->group
;
4303 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
4304 if (peer
->sort
== BGP_PEER_IBGP
)
4309 if (peer
->fd
>= 0) {
4310 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4312 peer
, BGP_NOTIFY_CEASE
,
4313 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4315 bgp_session_reset(peer
);
4322 /* Neighbor description. */
4323 int peer_description_set(struct peer
*peer
, const char *desc
)
4326 XFREE(MTYPE_PEER_DESC
, peer
->desc
);
4328 peer
->desc
= XSTRDUP(MTYPE_PEER_DESC
, desc
);
4333 int peer_description_unset(struct peer
*peer
)
4336 XFREE(MTYPE_PEER_DESC
, peer
->desc
);
4343 /* Neighbor update-source. */
4344 int peer_update_source_if_set(struct peer
*peer
, const char *ifname
)
4346 struct peer
*member
;
4347 struct listnode
*node
, *nnode
;
4349 /* Set flag and configuration on peer. */
4350 peer_flag_set(peer
, PEER_FLAG_UPDATE_SOURCE
);
4351 if (peer
->update_if
) {
4352 if (strcmp(peer
->update_if
, ifname
) == 0)
4354 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
4356 peer
->update_if
= XSTRDUP(MTYPE_PEER_UPDATE_SOURCE
, ifname
);
4357 sockunion_free(peer
->update_source
);
4358 peer
->update_source
= NULL
;
4360 /* Check if handling a regular peer. */
4361 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4362 /* Send notification or reset peer depending on state. */
4363 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
4364 peer
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4365 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4366 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4368 bgp_session_reset(peer
);
4370 /* Skip peer-group mechanics for regular peers. */
4375 * Set flag and configuration on all peer-group members, unless they are
4376 * explicitely overriding peer-group configuration.
4378 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4379 /* Skip peers with overridden configuration. */
4380 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_UPDATE_SOURCE
))
4383 /* Skip peers with the same configuration. */
4384 if (member
->update_if
) {
4385 if (strcmp(member
->update_if
, ifname
) == 0)
4387 XFREE(MTYPE_PEER_UPDATE_SOURCE
, member
->update_if
);
4390 /* Set flag and configuration on peer-group member. */
4391 SET_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
);
4392 member
->update_if
= XSTRDUP(MTYPE_PEER_UPDATE_SOURCE
, ifname
);
4393 sockunion_free(member
->update_source
);
4394 member
->update_source
= NULL
;
4396 /* Send notification or reset peer depending on state. */
4397 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
4398 member
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4399 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
4400 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4402 bgp_session_reset(member
);
4408 int peer_update_source_addr_set(struct peer
*peer
, const union sockunion
*su
)
4410 struct peer
*member
;
4411 struct listnode
*node
, *nnode
;
4413 /* Set flag and configuration on peer. */
4414 peer_flag_set(peer
, PEER_FLAG_UPDATE_SOURCE
);
4415 if (peer
->update_source
) {
4416 if (sockunion_cmp(peer
->update_source
, su
) == 0)
4418 sockunion_free(peer
->update_source
);
4420 peer
->update_source
= sockunion_dup(su
);
4421 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
4423 /* Check if handling a regular peer. */
4424 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4425 /* Send notification or reset peer depending on state. */
4426 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
4427 peer
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4428 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4429 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4431 bgp_session_reset(peer
);
4433 /* Skip peer-group mechanics for regular peers. */
4438 * Set flag and configuration on all peer-group members, unless they are
4439 * explicitely overriding peer-group configuration.
4441 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4442 /* Skip peers with overridden configuration. */
4443 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_UPDATE_SOURCE
))
4446 /* Skip peers with the same configuration. */
4447 if (member
->update_source
) {
4448 if (sockunion_cmp(member
->update_source
, su
) == 0)
4450 sockunion_free(member
->update_source
);
4453 /* Set flag and configuration on peer-group member. */
4454 SET_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
);
4455 member
->update_source
= sockunion_dup(su
);
4456 XFREE(MTYPE_PEER_UPDATE_SOURCE
, member
->update_if
);
4458 /* Send notification or reset peer depending on state. */
4459 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
4460 member
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4461 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
4462 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4464 bgp_session_reset(member
);
4470 int peer_update_source_unset(struct peer
*peer
)
4472 struct peer
*member
;
4473 struct listnode
*node
, *nnode
;
4475 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_UPDATE_SOURCE
))
4478 /* Inherit configuration from peer-group if peer is member. */
4479 if (peer_group_active(peer
)) {
4480 peer_flag_inherit(peer
, PEER_FLAG_UPDATE_SOURCE
);
4481 PEER_SU_ATTR_INHERIT(peer
, peer
->group
, update_source
);
4482 PEER_STR_ATTR_INHERIT(peer
, peer
->group
, update_if
,
4483 MTYPE_PEER_UPDATE_SOURCE
);
4485 /* Otherwise remove flag and configuration from peer. */
4486 peer_flag_unset(peer
, PEER_FLAG_UPDATE_SOURCE
);
4487 sockunion_free(peer
->update_source
);
4488 peer
->update_source
= NULL
;
4489 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
4492 /* Check if handling a regular peer. */
4493 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4494 /* Send notification or reset peer depending on state. */
4495 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
4496 peer
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4497 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4498 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4500 bgp_session_reset(peer
);
4502 /* Skip peer-group mechanics for regular peers. */
4507 * Set flag and configuration on all peer-group members, unless they are
4508 * explicitely overriding peer-group configuration.
4510 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4511 /* Skip peers with overridden configuration. */
4512 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_UPDATE_SOURCE
))
4515 /* Skip peers with the same configuration. */
4516 if (!CHECK_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
)
4517 && !member
->update_source
&& !member
->update_if
)
4520 /* Remove flag and configuration on peer-group member. */
4521 UNSET_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
);
4522 sockunion_free(member
->update_source
);
4523 member
->update_source
= NULL
;
4524 XFREE(MTYPE_PEER_UPDATE_SOURCE
, member
->update_if
);
4526 /* Send notification or reset peer depending on state. */
4527 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
4528 member
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4529 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
4530 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4532 bgp_session_reset(member
);
4538 int peer_default_originate_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
4539 const char *rmap
, struct route_map
*route_map
)
4541 struct peer
*member
;
4542 struct listnode
*node
, *nnode
;
4544 /* Set flag and configuration on peer. */
4545 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_DEFAULT_ORIGINATE
);
4547 if (!peer
->default_rmap
[afi
][safi
].name
4548 || strcmp(rmap
, peer
->default_rmap
[afi
][safi
].name
) != 0) {
4549 if (peer
->default_rmap
[afi
][safi
].name
)
4550 XFREE(MTYPE_ROUTE_MAP_NAME
,
4551 peer
->default_rmap
[afi
][safi
].name
);
4553 peer
->default_rmap
[afi
][safi
].name
=
4554 XSTRDUP(MTYPE_ROUTE_MAP_NAME
, rmap
);
4555 peer
->default_rmap
[afi
][safi
].map
= route_map
;
4558 if (peer
->default_rmap
[afi
][safi
].name
)
4559 XFREE(MTYPE_ROUTE_MAP_NAME
,
4560 peer
->default_rmap
[afi
][safi
].name
);
4562 peer
->default_rmap
[afi
][safi
].name
= NULL
;
4563 peer
->default_rmap
[afi
][safi
].map
= NULL
;
4566 /* Check if handling a regular peer. */
4567 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4568 /* Update peer route announcements. */
4569 if (peer
->status
== Established
&& peer
->afc_nego
[afi
][safi
]) {
4570 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4571 bgp_default_originate(peer
, afi
, safi
, 0);
4572 bgp_announce_route(peer
, afi
, safi
);
4575 /* Skip peer-group mechanics for regular peers. */
4580 * Set flag and configuration on all peer-group members, unless they are
4581 * explicitely overriding peer-group configuration.
4583 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4584 /* Skip peers with overridden configuration. */
4585 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4586 PEER_FLAG_DEFAULT_ORIGINATE
))
4589 /* Set flag and configuration on peer-group member. */
4590 SET_FLAG(member
->af_flags
[afi
][safi
],
4591 PEER_FLAG_DEFAULT_ORIGINATE
);
4593 if (member
->default_rmap
[afi
][safi
].name
)
4594 XFREE(MTYPE_ROUTE_MAP_NAME
,
4595 member
->default_rmap
[afi
][safi
].name
);
4597 member
->default_rmap
[afi
][safi
].name
=
4598 XSTRDUP(MTYPE_ROUTE_MAP_NAME
, rmap
);
4599 member
->default_rmap
[afi
][safi
].map
= route_map
;
4602 /* Update peer route announcements. */
4603 if (member
->status
== Established
4604 && member
->afc_nego
[afi
][safi
]) {
4605 update_group_adjust_peer(
4606 peer_af_find(member
, afi
, safi
));
4607 bgp_default_originate(member
, afi
, safi
, 0);
4608 bgp_announce_route(member
, afi
, safi
);
4615 int peer_default_originate_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
4617 struct peer
*member
;
4618 struct listnode
*node
, *nnode
;
4620 /* Inherit configuration from peer-group if peer is member. */
4621 if (peer_group_active(peer
)) {
4622 peer_af_flag_inherit(peer
, afi
, safi
,
4623 PEER_FLAG_DEFAULT_ORIGINATE
);
4624 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
4625 default_rmap
[afi
][safi
].name
,
4626 MTYPE_ROUTE_MAP_NAME
);
4627 PEER_ATTR_INHERIT(peer
, peer
->group
,
4628 default_rmap
[afi
][safi
].map
);
4630 /* Otherwise remove flag and configuration from peer. */
4631 peer_af_flag_unset(peer
, afi
, safi
,
4632 PEER_FLAG_DEFAULT_ORIGINATE
);
4633 if (peer
->default_rmap
[afi
][safi
].name
)
4634 XFREE(MTYPE_ROUTE_MAP_NAME
,
4635 peer
->default_rmap
[afi
][safi
].name
);
4636 peer
->default_rmap
[afi
][safi
].name
= NULL
;
4637 peer
->default_rmap
[afi
][safi
].map
= NULL
;
4640 /* Check if handling a regular peer. */
4641 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4642 /* Update peer route announcements. */
4643 if (peer
->status
== Established
&& peer
->afc_nego
[afi
][safi
]) {
4644 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4645 bgp_default_originate(peer
, afi
, safi
, 1);
4646 bgp_announce_route(peer
, afi
, safi
);
4649 /* Skip peer-group mechanics for regular peers. */
4654 * Remove flag and configuration from all peer-group members, unless
4655 * they are explicitely overriding peer-group configuration.
4657 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4658 /* Skip peers with overridden configuration. */
4659 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4660 PEER_FLAG_DEFAULT_ORIGINATE
))
4663 /* Remove flag and configuration on peer-group member. */
4664 UNSET_FLAG(peer
->af_flags
[afi
][safi
],
4665 PEER_FLAG_DEFAULT_ORIGINATE
);
4666 if (peer
->default_rmap
[afi
][safi
].name
)
4667 XFREE(MTYPE_ROUTE_MAP_NAME
,
4668 peer
->default_rmap
[afi
][safi
].name
);
4669 peer
->default_rmap
[afi
][safi
].name
= NULL
;
4670 peer
->default_rmap
[afi
][safi
].map
= NULL
;
4672 /* Update peer route announcements. */
4673 if (peer
->status
== Established
&& peer
->afc_nego
[afi
][safi
]) {
4674 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4675 bgp_default_originate(peer
, afi
, safi
, 1);
4676 bgp_announce_route(peer
, afi
, safi
);
4683 int peer_port_set(struct peer
*peer
, uint16_t port
)
4689 int peer_port_unset(struct peer
*peer
)
4691 peer
->port
= BGP_PORT_DEFAULT
;
4696 * Helper function that is called after the name of the policy
4697 * being used by a peer has changed (AF specific). Automatically
4698 * initiates inbound or outbound processing as needed.
4700 static void peer_on_policy_change(struct peer
*peer
, afi_t afi
, safi_t safi
,
4704 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4705 if (peer
->status
== Established
)
4706 bgp_announce_route(peer
, afi
, safi
);
4708 if (peer
->status
!= Established
)
4711 if (CHECK_FLAG(peer
->af_flags
[afi
][safi
],
4712 PEER_FLAG_SOFT_RECONFIG
))
4713 bgp_soft_reconfig_in(peer
, afi
, safi
);
4714 else if (CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_OLD_RCV
)
4715 || CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_NEW_RCV
))
4716 bgp_route_refresh_send(peer
, afi
, safi
, 0, 0, 0);
4721 /* neighbor weight. */
4722 int peer_weight_set(struct peer
*peer
, afi_t afi
, safi_t safi
, uint16_t weight
)
4724 struct peer
*member
;
4725 struct listnode
*node
, *nnode
;
4727 /* Set flag and configuration on peer. */
4728 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_WEIGHT
);
4729 if (peer
->weight
[afi
][safi
] != weight
) {
4730 peer
->weight
[afi
][safi
] = weight
;
4731 peer_on_policy_change(peer
, afi
, safi
, 0);
4734 /* Skip peer-group mechanics for regular peers. */
4735 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4739 * Set flag and configuration on all peer-group members, unless they are
4740 * explicitely overriding peer-group configuration.
4742 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4743 /* Skip peers with overridden configuration. */
4744 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4748 /* Set flag and configuration on peer-group member. */
4749 SET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
);
4750 if (member
->weight
[afi
][safi
] != weight
) {
4751 member
->weight
[afi
][safi
] = weight
;
4752 peer_on_policy_change(member
, afi
, safi
, 0);
4759 int peer_weight_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
4761 struct peer
*member
;
4762 struct listnode
*node
, *nnode
;
4764 if (!CHECK_FLAG(peer
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
))
4767 /* Inherit configuration from peer-group if peer is member. */
4768 if (peer_group_active(peer
)) {
4769 peer_af_flag_inherit(peer
, afi
, safi
, PEER_FLAG_WEIGHT
);
4770 PEER_ATTR_INHERIT(peer
, peer
->group
, weight
[afi
][safi
]);
4772 peer_on_policy_change(peer
, afi
, safi
, 0);
4776 /* Remove flag and configuration from peer. */
4777 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_WEIGHT
);
4778 peer
->weight
[afi
][safi
] = 0;
4779 peer_on_policy_change(peer
, afi
, safi
, 0);
4781 /* Skip peer-group mechanics for regular peers. */
4782 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4786 * Remove flag and configuration from all peer-group members, unless
4787 * they are explicitely overriding peer-group configuration.
4789 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4790 /* Skip peers with overridden configuration. */
4791 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4795 /* Skip peers where flag is already disabled. */
4796 if (!CHECK_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
))
4799 /* Remove flag and configuration on peer-group member. */
4800 UNSET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
);
4801 member
->weight
[afi
][safi
] = 0;
4802 peer_on_policy_change(member
, afi
, safi
, 0);
4808 int peer_timers_set(struct peer
*peer
, uint32_t keepalive
, uint32_t holdtime
)
4810 struct peer
*member
;
4811 struct listnode
*node
, *nnode
;
4813 if (keepalive
> 65535)
4814 return BGP_ERR_INVALID_VALUE
;
4816 if (holdtime
> 65535)
4817 return BGP_ERR_INVALID_VALUE
;
4819 if (holdtime
< 3 && holdtime
!= 0)
4820 return BGP_ERR_INVALID_VALUE
;
4822 /* Set flag and configuration on peer. */
4823 peer_flag_set(peer
, PEER_FLAG_TIMER
);
4824 peer
->holdtime
= holdtime
;
4825 peer
->keepalive
= (keepalive
< holdtime
/ 3 ? keepalive
: holdtime
/ 3);
4827 /* Skip peer-group mechanics for regular peers. */
4828 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4832 * Set flag and configuration on all peer-group members, unless they are
4833 * explicitely overriding peer-group configuration.
4835 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4836 /* Skip peers with overridden configuration. */
4837 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER
))
4840 /* Set flag and configuration on peer-group member. */
4841 SET_FLAG(member
->flags
, PEER_FLAG_TIMER
);
4842 PEER_ATTR_INHERIT(peer
, peer
->group
, holdtime
);
4843 PEER_ATTR_INHERIT(peer
, peer
->group
, keepalive
);
4849 int peer_timers_unset(struct peer
*peer
)
4851 struct peer
*member
;
4852 struct listnode
*node
, *nnode
;
4854 /* Inherit configuration from peer-group if peer is member. */
4855 if (peer_group_active(peer
)) {
4856 peer_flag_inherit(peer
, PEER_FLAG_TIMER
);
4857 PEER_ATTR_INHERIT(peer
, peer
->group
, holdtime
);
4858 PEER_ATTR_INHERIT(peer
, peer
->group
, keepalive
);
4860 /* Otherwise remove flag and configuration from peer. */
4861 peer_flag_unset(peer
, PEER_FLAG_TIMER
);
4863 peer
->keepalive
= 0;
4866 /* Skip peer-group mechanics for regular peers. */
4867 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4871 * Remove flag and configuration from all peer-group members, unless
4872 * they are explicitely overriding peer-group configuration.
4874 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4875 /* Skip peers with overridden configuration. */
4876 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER
))
4879 /* Remove flag and configuration on peer-group member. */
4880 UNSET_FLAG(member
->flags
, PEER_FLAG_TIMER
);
4881 member
->holdtime
= 0;
4882 member
->keepalive
= 0;
4888 int peer_timers_connect_set(struct peer
*peer
, uint32_t connect
)
4890 struct peer
*member
;
4891 struct listnode
*node
, *nnode
;
4893 if (connect
> 65535)
4894 return BGP_ERR_INVALID_VALUE
;
4896 /* Set flag and configuration on peer. */
4897 peer_flag_set(peer
, PEER_FLAG_TIMER_CONNECT
);
4898 peer
->connect
= connect
;
4899 peer
->v_connect
= connect
;
4901 /* Skip peer-group mechanics for regular peers. */
4902 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4906 * Set flag and configuration on all peer-group members, unless they are
4907 * explicitely overriding peer-group configuration.
4909 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4910 /* Skip peers with overridden configuration. */
4911 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER_CONNECT
))
4914 /* Set flag and configuration on peer-group member. */
4915 SET_FLAG(member
->flags
, PEER_FLAG_TIMER_CONNECT
);
4916 member
->connect
= connect
;
4917 member
->v_connect
= connect
;
4923 int peer_timers_connect_unset(struct peer
*peer
)
4925 struct peer
*member
;
4926 struct listnode
*node
, *nnode
;
4928 /* Inherit configuration from peer-group if peer is member. */
4929 if (peer_group_active(peer
)) {
4930 peer_flag_inherit(peer
, PEER_FLAG_TIMER_CONNECT
);
4931 PEER_ATTR_INHERIT(peer
, peer
->group
, connect
);
4933 /* Otherwise remove flag and configuration from peer. */
4934 peer_flag_unset(peer
, PEER_FLAG_TIMER_CONNECT
);
4938 /* Set timer with fallback to default value. */
4940 peer
->v_connect
= peer
->connect
;
4942 peer
->v_connect
= BGP_DEFAULT_CONNECT_RETRY
;
4944 /* Skip peer-group mechanics for regular peers. */
4945 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4949 * Remove flag and configuration from all peer-group members, unless
4950 * they are explicitely overriding peer-group configuration.
4952 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4953 /* Skip peers with overridden configuration. */
4954 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER_CONNECT
))
4957 /* Remove flag and configuration on peer-group member. */
4958 UNSET_FLAG(member
->flags
, PEER_FLAG_TIMER_CONNECT
);
4959 member
->connect
= 0;
4960 member
->v_connect
= BGP_DEFAULT_CONNECT_RETRY
;
4966 int peer_advertise_interval_set(struct peer
*peer
, uint32_t routeadv
)
4968 struct peer
*member
;
4969 struct listnode
*node
, *nnode
;
4972 return BGP_ERR_INVALID_VALUE
;
4974 /* Set flag and configuration on peer. */
4975 peer_flag_set(peer
, PEER_FLAG_ROUTEADV
);
4976 peer
->routeadv
= routeadv
;
4977 peer
->v_routeadv
= routeadv
;
4979 /* Check if handling a regular peer. */
4980 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4981 /* Update peer route announcements. */
4982 update_group_adjust_peer_afs(peer
);
4983 if (peer
->status
== Established
)
4984 bgp_announce_route_all(peer
);
4986 /* Skip peer-group mechanics for regular peers. */
4991 * Set flag and configuration on all peer-group members, unless they are
4992 * explicitely overriding peer-group configuration.
4994 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4995 /* Skip peers with overridden configuration. */
4996 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_ROUTEADV
))
4999 /* Set flag and configuration on peer-group member. */
5000 SET_FLAG(member
->flags
, PEER_FLAG_ROUTEADV
);
5001 member
->routeadv
= routeadv
;
5002 member
->v_routeadv
= routeadv
;
5004 /* Update peer route announcements. */
5005 update_group_adjust_peer_afs(member
);
5006 if (member
->status
== Established
)
5007 bgp_announce_route_all(member
);
5013 int peer_advertise_interval_unset(struct peer
*peer
)
5015 struct peer
*member
;
5016 struct listnode
*node
, *nnode
;
5018 /* Inherit configuration from peer-group if peer is member. */
5019 if (peer_group_active(peer
)) {
5020 peer_flag_inherit(peer
, PEER_FLAG_ROUTEADV
);
5021 PEER_ATTR_INHERIT(peer
, peer
->group
, routeadv
);
5023 /* Otherwise remove flag and configuration from peer. */
5024 peer_flag_unset(peer
, PEER_FLAG_ROUTEADV
);
5028 /* Set timer with fallback to default value. */
5030 peer
->v_routeadv
= peer
->routeadv
;
5032 peer
->v_routeadv
= (peer
->sort
== BGP_PEER_IBGP
)
5033 ? BGP_DEFAULT_IBGP_ROUTEADV
5034 : BGP_DEFAULT_EBGP_ROUTEADV
;
5036 /* Check if handling a regular peer. */
5037 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5038 /* Update peer route announcements. */
5039 update_group_adjust_peer_afs(peer
);
5040 if (peer
->status
== Established
)
5041 bgp_announce_route_all(peer
);
5043 /* Skip peer-group mechanics for regular peers. */
5048 * Remove flag and configuration from all peer-group members, unless
5049 * they are explicitely overriding peer-group configuration.
5051 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5052 /* Skip peers with overridden configuration. */
5053 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_ROUTEADV
))
5056 /* Remove flag and configuration on peer-group member. */
5057 UNSET_FLAG(member
->flags
, PEER_FLAG_ROUTEADV
);
5058 member
->routeadv
= 0;
5059 member
->v_routeadv
= (member
->sort
== BGP_PEER_IBGP
)
5060 ? BGP_DEFAULT_IBGP_ROUTEADV
5061 : BGP_DEFAULT_EBGP_ROUTEADV
;
5063 /* Update peer route announcements. */
5064 update_group_adjust_peer_afs(member
);
5065 if (member
->status
== Established
)
5066 bgp_announce_route_all(member
);
5072 /* neighbor interface */
5073 void peer_interface_set(struct peer
*peer
, const char *str
)
5076 XFREE(MTYPE_BGP_PEER_IFNAME
, peer
->ifname
);
5077 peer
->ifname
= XSTRDUP(MTYPE_BGP_PEER_IFNAME
, str
);
5080 void peer_interface_unset(struct peer
*peer
)
5083 XFREE(MTYPE_BGP_PEER_IFNAME
, peer
->ifname
);
5084 peer
->ifname
= NULL
;
5088 int peer_allowas_in_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
5089 int allow_num
, int origin
)
5091 struct peer
*member
;
5092 struct listnode
*node
, *nnode
;
5094 if (!origin
&& (allow_num
< 1 || allow_num
> 10))
5095 return BGP_ERR_INVALID_VALUE
;
5097 /* Set flag and configuration on peer. */
5098 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN
);
5100 if (peer
->allowas_in
[afi
][safi
] != 0
5101 || !CHECK_FLAG(peer
->af_flags
[afi
][safi
],
5102 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5103 peer_af_flag_set(peer
, afi
, safi
,
5104 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5105 peer
->allowas_in
[afi
][safi
] = 0;
5106 peer_on_policy_change(peer
, afi
, safi
, 0);
5109 if (peer
->allowas_in
[afi
][safi
] != allow_num
5110 || CHECK_FLAG(peer
->af_flags
[afi
][safi
],
5111 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5113 peer_af_flag_unset(peer
, afi
, safi
,
5114 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5115 peer
->allowas_in
[afi
][safi
] = allow_num
;
5116 peer_on_policy_change(peer
, afi
, safi
, 0);
5120 /* Skip peer-group mechanics for regular peers. */
5121 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
5125 * Set flag and configuration on all peer-group members, unless
5126 * they are explicitely overriding peer-group configuration.
5128 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5129 /* Skip peers with overridden configuration. */
5130 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
5131 PEER_FLAG_ALLOWAS_IN
))
5134 /* Set flag and configuration on peer-group member. */
5135 SET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_ALLOWAS_IN
);
5137 if (member
->allowas_in
[afi
][safi
] != 0
5138 || !CHECK_FLAG(member
->af_flags
[afi
][safi
],
5139 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5140 SET_FLAG(member
->af_flags
[afi
][safi
],
5141 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5142 member
->allowas_in
[afi
][safi
] = 0;
5143 peer_on_policy_change(peer
, afi
, safi
, 0);
5146 if (member
->allowas_in
[afi
][safi
] != allow_num
5147 || CHECK_FLAG(member
->af_flags
[afi
][safi
],
5148 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5149 UNSET_FLAG(member
->af_flags
[afi
][safi
],
5150 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5151 member
->allowas_in
[afi
][safi
] = allow_num
;
5152 peer_on_policy_change(peer
, afi
, safi
, 0);
5160 int peer_allowas_in_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
5162 struct peer
*member
;
5163 struct listnode
*node
, *nnode
;
5165 /* Skip peer if flag is already disabled. */
5166 if (!CHECK_FLAG(peer
->af_flags
[afi
][safi
], PEER_FLAG_ALLOWAS_IN
))
5169 /* Inherit configuration from peer-group if peer is member. */
5170 if (peer_group_active(peer
)) {
5171 peer_af_flag_inherit(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN
);
5172 peer_af_flag_inherit(peer
, afi
, safi
,
5173 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5174 PEER_ATTR_INHERIT(peer
, peer
->group
, allowas_in
[afi
][safi
]);
5175 peer_on_policy_change(peer
, afi
, safi
, 0);
5180 /* Remove flag and configuration from peer. */
5181 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN
);
5182 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5183 peer
->allowas_in
[afi
][safi
] = 0;
5184 peer_on_policy_change(peer
, afi
, safi
, 0);
5186 /* Skip peer-group mechanics if handling a regular peer. */
5187 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
5191 * Remove flags and configuration from all peer-group members, unless
5192 * they are explicitely overriding peer-group configuration.
5194 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5195 /* Skip peers with overridden configuration. */
5196 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
5197 PEER_FLAG_ALLOWAS_IN
))
5200 /* Skip peers where flag is already disabled. */
5201 if (!CHECK_FLAG(member
->af_flags
[afi
][safi
],
5202 PEER_FLAG_ALLOWAS_IN
))
5205 /* Remove flags and configuration on peer-group member. */
5206 UNSET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_ALLOWAS_IN
);
5207 UNSET_FLAG(member
->af_flags
[afi
][safi
],
5208 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5209 member
->allowas_in
[afi
][safi
] = 0;
5210 peer_on_policy_change(member
, afi
, safi
, 0);
5216 int peer_local_as_set(struct peer
*peer
, as_t as
, int no_prepend
,
5219 bool old_no_prepend
, old_replace_as
;
5220 struct bgp
*bgp
= peer
->bgp
;
5221 struct peer
*member
;
5222 struct listnode
*node
, *nnode
;
5224 if (peer_sort(peer
) != BGP_PEER_EBGP
5225 && peer_sort(peer
) != BGP_PEER_INTERNAL
)
5226 return BGP_ERR_LOCAL_AS_ALLOWED_ONLY_FOR_EBGP
;
5229 return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS
;
5232 return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS_REMOTE_AS
;
5234 /* Save previous flag states. */
5236 !!CHECK_FLAG(peer
->flags
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5238 !!CHECK_FLAG(peer
->flags
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5240 /* Set flag and configuration on peer. */
5241 peer_flag_set(peer
, PEER_FLAG_LOCAL_AS
);
5242 peer_flag_modify(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
, no_prepend
);
5243 peer_flag_modify(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
, replace_as
);
5245 if (peer
->change_local_as
== as
&& old_no_prepend
== no_prepend
5246 && old_replace_as
== replace_as
)
5248 peer
->change_local_as
= as
;
5250 /* Check if handling a regular peer. */
5251 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5252 /* Send notification or reset peer depending on state. */
5253 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
5254 peer
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5255 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5256 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5258 bgp_session_reset(peer
);
5260 /* Skip peer-group mechanics for regular peers. */
5265 * Set flag and configuration on all peer-group members, unless they are
5266 * explicitely overriding peer-group configuration.
5268 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5269 /* Skip peers with overridden configuration. */
5270 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_LOCAL_AS
))
5273 /* Skip peers with the same configuration. */
5274 old_no_prepend
= CHECK_FLAG(member
->flags
,
5275 PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5276 old_replace_as
= CHECK_FLAG(member
->flags
,
5277 PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5278 if (member
->change_local_as
== as
5279 && CHECK_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS
)
5280 && old_no_prepend
== no_prepend
5281 && old_replace_as
== replace_as
)
5284 /* Set flag and configuration on peer-group member. */
5285 SET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS
);
5286 COND_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_NO_PREPEND
,
5288 COND_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_REPLACE_AS
,
5290 member
->change_local_as
= as
;
5292 /* Send notification or stop peer depending on state. */
5293 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
5294 member
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5295 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5296 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5298 BGP_EVENT_ADD(member
, BGP_Stop
);
5304 int peer_local_as_unset(struct peer
*peer
)
5306 struct peer
*member
;
5307 struct listnode
*node
, *nnode
;
5309 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_LOCAL_AS
))
5312 /* Inherit configuration from peer-group if peer is member. */
5313 if (peer_group_active(peer
)) {
5314 peer_flag_inherit(peer
, PEER_FLAG_LOCAL_AS
);
5315 peer_flag_inherit(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5316 peer_flag_inherit(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5317 PEER_ATTR_INHERIT(peer
, peer
->group
, change_local_as
);
5319 /* Otherwise remove flag and configuration from peer. */
5320 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS
);
5321 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5322 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5323 peer
->change_local_as
= 0;
5326 /* Check if handling a regular peer. */
5327 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5328 /* Send notification or stop peer depending on state. */
5329 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
5330 peer
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5331 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5332 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5334 BGP_EVENT_ADD(peer
, BGP_Stop
);
5336 /* Skip peer-group mechanics for regular peers. */
5341 * Remove flag and configuration from all peer-group members, unless
5342 * they are explicitely overriding peer-group configuration.
5344 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5345 /* Skip peers with overridden configuration. */
5346 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_LOCAL_AS
))
5349 /* Remove flag and configuration on peer-group member. */
5350 UNSET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS
);
5351 UNSET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5352 UNSET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5353 member
->change_local_as
= 0;
5355 /* Send notification or stop peer depending on state. */
5356 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
5357 member
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5358 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5359 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5361 bgp_session_reset(member
);
5367 /* Set password for authenticating with the peer. */
5368 int peer_password_set(struct peer
*peer
, const char *password
)
5370 struct peer
*member
;
5371 struct listnode
*node
, *nnode
;
5372 int len
= password
? strlen(password
) : 0;
5373 int ret
= BGP_SUCCESS
;
5375 if ((len
< PEER_PASSWORD_MINLEN
) || (len
> PEER_PASSWORD_MAXLEN
))
5376 return BGP_ERR_INVALID_VALUE
;
5378 /* Set flag and configuration on peer. */
5379 peer_flag_set(peer
, PEER_FLAG_PASSWORD
);
5380 if (peer
->password
&& strcmp(peer
->password
, password
) == 0)
5382 XFREE(MTYPE_PEER_PASSWORD
, peer
->password
);
5383 peer
->password
= XSTRDUP(MTYPE_PEER_PASSWORD
, password
);
5385 /* Check if handling a regular peer. */
5386 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5387 /* Send notification or reset peer depending on state. */
5388 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
5389 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5390 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5392 bgp_session_reset(peer
);
5395 * Attempt to install password on socket and skip peer-group
5398 if (BGP_PEER_SU_UNSPEC(peer
))
5400 return (bgp_md5_set(peer
) >= 0) ? BGP_SUCCESS
5401 : BGP_ERR_TCPSIG_FAILED
;
5405 * Set flag and configuration on all peer-group members, unless they are
5406 * explicitely overriding peer-group configuration.
5408 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5409 /* Skip peers with overridden configuration. */
5410 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_PASSWORD
))
5413 /* Skip peers with the same password. */
5414 if (member
->password
&& strcmp(member
->password
, password
) == 0)
5417 /* Set flag and configuration on peer-group member. */
5418 SET_FLAG(member
->flags
, PEER_FLAG_PASSWORD
);
5419 if (member
->password
)
5420 XFREE(MTYPE_PEER_PASSWORD
, member
->password
);
5421 member
->password
= XSTRDUP(MTYPE_PEER_PASSWORD
, password
);
5423 /* Send notification or reset peer depending on state. */
5424 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
))
5425 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5426 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5428 bgp_session_reset(member
);
5430 /* Attempt to install password on socket. */
5431 if (!BGP_PEER_SU_UNSPEC(member
) && bgp_md5_set(member
) < 0)
5432 ret
= BGP_ERR_TCPSIG_FAILED
;
5438 int peer_password_unset(struct peer
*peer
)
5440 struct peer
*member
;
5441 struct listnode
*node
, *nnode
;
5443 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
))
5446 /* Inherit configuration from peer-group if peer is member. */
5447 if (peer_group_active(peer
)) {
5448 peer_flag_inherit(peer
, PEER_FLAG_PASSWORD
);
5449 PEER_STR_ATTR_INHERIT(peer
, peer
->group
, password
,
5450 MTYPE_PEER_PASSWORD
);
5452 /* Otherwise remove flag and configuration from peer. */
5453 peer_flag_unset(peer
, PEER_FLAG_PASSWORD
);
5454 XFREE(MTYPE_PEER_PASSWORD
, peer
->password
);
5457 /* Check if handling a regular peer. */
5458 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5459 /* Send notification or reset peer depending on state. */
5460 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
5461 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5462 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5464 bgp_session_reset(peer
);
5466 /* Attempt to uninstall password on socket. */
5467 if (!BGP_PEER_SU_UNSPEC(peer
))
5468 bgp_md5_unset(peer
);
5470 /* Skip peer-group mechanics for regular peers. */
5475 * Remove flag and configuration from all peer-group members, unless
5476 * they are explicitely overriding peer-group configuration.
5478 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5479 /* Skip peers with overridden configuration. */
5480 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_PASSWORD
))
5483 /* Remove flag and configuration on peer-group member. */
5484 UNSET_FLAG(member
->flags
, PEER_FLAG_PASSWORD
);
5485 XFREE(MTYPE_PEER_PASSWORD
, member
->password
);
5487 /* Send notification or reset peer depending on state. */
5488 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
))
5489 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5490 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5492 bgp_session_reset(member
);
5494 /* Attempt to uninstall password on socket. */
5495 if (!BGP_PEER_SU_UNSPEC(member
))
5496 bgp_md5_unset(member
);
5503 /* Set distribute list to the peer. */
5504 int peer_distribute_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
5507 struct peer
*member
;
5508 struct bgp_filter
*filter
;
5509 struct listnode
*node
, *nnode
;
5511 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5512 return BGP_ERR_INVALID_VALUE
;
5514 /* Set configuration on peer. */
5515 filter
= &peer
->filter
[afi
][safi
];
5516 if (filter
->plist
[direct
].name
)
5517 return BGP_ERR_PEER_FILTER_CONFLICT
;
5518 if (filter
->dlist
[direct
].name
)
5519 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->dlist
[direct
].name
);
5520 filter
->dlist
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5521 filter
->dlist
[direct
].alist
= access_list_lookup(afi
, name
);
5523 /* Check if handling a regular peer. */
5524 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5525 /* Set override-flag and process peer route updates. */
5526 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5527 PEER_FT_DISTRIBUTE_LIST
);
5528 peer_on_policy_change(peer
, afi
, safi
,
5529 (direct
== FILTER_OUT
) ? 1 : 0);
5531 /* Skip peer-group mechanics for regular peers. */
5536 * Set configuration on all peer-group members, un less they are
5537 * explicitely overriding peer-group configuration.
5539 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5540 /* Skip peers with overridden configuration. */
5541 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5542 PEER_FT_DISTRIBUTE_LIST
))
5545 /* Set configuration on peer-group member. */
5546 filter
= &member
->filter
[afi
][safi
];
5547 if (filter
->dlist
[direct
].name
)
5548 XFREE(MTYPE_BGP_FILTER_NAME
,
5549 filter
->dlist
[direct
].name
);
5550 filter
->dlist
[direct
].name
=
5551 XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5552 filter
->dlist
[direct
].alist
= access_list_lookup(afi
, name
);
5554 /* Process peer route updates. */
5555 peer_on_policy_change(member
, afi
, safi
,
5556 (direct
== FILTER_OUT
) ? 1 : 0);
5562 int peer_distribute_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
)
5564 struct peer
*member
;
5565 struct bgp_filter
*filter
;
5566 struct listnode
*node
, *nnode
;
5568 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5569 return BGP_ERR_INVALID_VALUE
;
5571 /* Unset override-flag unconditionally. */
5572 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5573 PEER_FT_DISTRIBUTE_LIST
);
5575 /* Inherit configuration from peer-group if peer is member. */
5576 if (peer_group_active(peer
)) {
5577 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
5578 filter
[afi
][safi
].dlist
[direct
].name
,
5579 MTYPE_BGP_FILTER_NAME
);
5580 PEER_ATTR_INHERIT(peer
, peer
->group
,
5581 filter
[afi
][safi
].dlist
[direct
].alist
);
5583 /* Otherwise remove configuration from peer. */
5584 filter
= &peer
->filter
[afi
][safi
];
5585 if (filter
->dlist
[direct
].name
)
5586 XFREE(MTYPE_BGP_FILTER_NAME
,
5587 filter
->dlist
[direct
].name
);
5588 filter
->dlist
[direct
].name
= NULL
;
5589 filter
->dlist
[direct
].alist
= NULL
;
5592 /* Check if handling a regular peer. */
5593 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5594 /* Process peer route updates. */
5595 peer_on_policy_change(peer
, afi
, safi
,
5596 (direct
== FILTER_OUT
) ? 1 : 0);
5598 /* Skip peer-group mechanics for regular peers. */
5603 * Remove configuration on all peer-group members, unless they are
5604 * explicitely overriding peer-group configuration.
5606 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5607 /* Skip peers with overridden configuration. */
5608 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5609 PEER_FT_DISTRIBUTE_LIST
))
5612 /* Remove configuration on peer-group member. */
5613 filter
= &member
->filter
[afi
][safi
];
5614 if (filter
->dlist
[direct
].name
)
5615 XFREE(MTYPE_BGP_FILTER_NAME
,
5616 filter
->dlist
[direct
].name
);
5617 filter
->dlist
[direct
].name
= NULL
;
5618 filter
->dlist
[direct
].alist
= NULL
;
5620 /* Process peer route updates. */
5621 peer_on_policy_change(member
, afi
, safi
,
5622 (direct
== FILTER_OUT
) ? 1 : 0);
5628 /* Update distribute list. */
5629 static void peer_distribute_update(struct access_list
*access
)
5634 struct listnode
*mnode
, *mnnode
;
5635 struct listnode
*node
, *nnode
;
5638 struct peer_group
*group
;
5639 struct bgp_filter
*filter
;
5641 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
)) {
5643 update_group_policy_update(bgp
, BGP_POLICY_FILTER_LIST
,
5644 access
->name
, 0, 0);
5645 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
5646 FOREACH_AFI_SAFI (afi
, safi
) {
5647 filter
= &peer
->filter
[afi
][safi
];
5649 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5651 if (filter
->dlist
[direct
].name
)
5652 filter
->dlist
[direct
]
5653 .alist
= access_list_lookup(
5655 filter
->dlist
[direct
]
5658 filter
->dlist
[direct
].alist
=
5663 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
5664 FOREACH_AFI_SAFI (afi
, safi
) {
5665 filter
= &group
->conf
->filter
[afi
][safi
];
5667 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5669 if (filter
->dlist
[direct
].name
)
5670 filter
->dlist
[direct
]
5671 .alist
= access_list_lookup(
5673 filter
->dlist
[direct
]
5676 filter
->dlist
[direct
].alist
=
5682 vnc_prefix_list_update(bgp
);
5687 /* Set prefix list to the peer. */
5688 int peer_prefix_list_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
5691 struct peer
*member
;
5692 struct bgp_filter
*filter
;
5693 struct listnode
*node
, *nnode
;
5695 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5696 return BGP_ERR_INVALID_VALUE
;
5698 /* Set configuration on peer. */
5699 filter
= &peer
->filter
[afi
][safi
];
5700 if (filter
->dlist
[direct
].name
)
5701 return BGP_ERR_PEER_FILTER_CONFLICT
;
5702 if (filter
->plist
[direct
].name
)
5703 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->plist
[direct
].name
);
5704 filter
->plist
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5705 filter
->plist
[direct
].plist
= prefix_list_lookup(afi
, name
);
5707 /* Check if handling a regular peer. */
5708 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5709 /* Set override-flag and process peer route updates. */
5710 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5711 PEER_FT_PREFIX_LIST
);
5712 peer_on_policy_change(peer
, afi
, safi
,
5713 (direct
== FILTER_OUT
) ? 1 : 0);
5715 /* Skip peer-group mechanics for regular peers. */
5720 * Set configuration on all peer-group members, unless they are
5721 * explicitely overriding peer-group configuration.
5723 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5724 /* Skip peers with overridden configuration. */
5725 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5726 PEER_FT_PREFIX_LIST
))
5729 /* Set configuration on peer-group member. */
5730 filter
= &member
->filter
[afi
][safi
];
5731 if (filter
->plist
[direct
].name
)
5732 XFREE(MTYPE_BGP_FILTER_NAME
,
5733 filter
->plist
[direct
].name
);
5734 filter
->plist
[direct
].name
=
5735 XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5736 filter
->plist
[direct
].plist
= prefix_list_lookup(afi
, name
);
5738 /* Process peer route updates. */
5739 peer_on_policy_change(member
, afi
, safi
,
5740 (direct
== FILTER_OUT
) ? 1 : 0);
5746 int peer_prefix_list_unset(struct peer
*peer
, afi_t afi
, safi_t safi
,
5749 struct peer
*member
;
5750 struct bgp_filter
*filter
;
5751 struct listnode
*node
, *nnode
;
5753 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5754 return BGP_ERR_INVALID_VALUE
;
5756 /* Unset override-flag unconditionally. */
5757 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5758 PEER_FT_PREFIX_LIST
);
5760 /* Inherit configuration from peer-group if peer is member. */
5761 if (peer_group_active(peer
)) {
5762 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
5763 filter
[afi
][safi
].plist
[direct
].name
,
5764 MTYPE_BGP_FILTER_NAME
);
5765 PEER_ATTR_INHERIT(peer
, peer
->group
,
5766 filter
[afi
][safi
].plist
[direct
].plist
);
5768 /* Otherwise remove configuration from peer. */
5769 filter
= &peer
->filter
[afi
][safi
];
5770 if (filter
->plist
[direct
].name
)
5771 XFREE(MTYPE_BGP_FILTER_NAME
,
5772 filter
->plist
[direct
].name
);
5773 filter
->plist
[direct
].name
= NULL
;
5774 filter
->plist
[direct
].plist
= NULL
;
5777 /* Check if handling a regular peer. */
5778 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5779 /* Process peer route updates. */
5780 peer_on_policy_change(peer
, afi
, safi
,
5781 (direct
== FILTER_OUT
) ? 1 : 0);
5783 /* Skip peer-group mechanics for regular peers. */
5788 * Remove configuration on all peer-group members, unless they are
5789 * explicitely overriding peer-group configuration.
5791 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5792 /* Skip peers with overridden configuration. */
5793 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5794 PEER_FT_PREFIX_LIST
))
5797 /* Remove configuration on peer-group member. */
5798 filter
= &member
->filter
[afi
][safi
];
5799 if (filter
->plist
[direct
].name
)
5800 XFREE(MTYPE_BGP_FILTER_NAME
,
5801 filter
->plist
[direct
].name
);
5802 filter
->plist
[direct
].name
= NULL
;
5803 filter
->plist
[direct
].plist
= NULL
;
5805 /* Process peer route updates. */
5806 peer_on_policy_change(member
, afi
, safi
,
5807 (direct
== FILTER_OUT
) ? 1 : 0);
5813 /* Update prefix-list list. */
5814 static void peer_prefix_list_update(struct prefix_list
*plist
)
5816 struct listnode
*mnode
, *mnnode
;
5817 struct listnode
*node
, *nnode
;
5820 struct peer_group
*group
;
5821 struct bgp_filter
*filter
;
5826 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
)) {
5829 * Update the prefix-list on update groups.
5831 update_group_policy_update(
5832 bgp
, BGP_POLICY_PREFIX_LIST
,
5833 plist
? prefix_list_name(plist
) : NULL
, 0, 0);
5835 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
5836 FOREACH_AFI_SAFI (afi
, safi
) {
5837 filter
= &peer
->filter
[afi
][safi
];
5839 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5841 if (filter
->plist
[direct
].name
)
5842 filter
->plist
[direct
]
5843 .plist
= prefix_list_lookup(
5845 filter
->plist
[direct
]
5848 filter
->plist
[direct
].plist
=
5853 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
5854 FOREACH_AFI_SAFI (afi
, safi
) {
5855 filter
= &group
->conf
->filter
[afi
][safi
];
5857 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5859 if (filter
->plist
[direct
].name
)
5860 filter
->plist
[direct
]
5861 .plist
= prefix_list_lookup(
5863 filter
->plist
[direct
]
5866 filter
->plist
[direct
].plist
=
5874 int peer_aslist_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
5877 struct peer
*member
;
5878 struct bgp_filter
*filter
;
5879 struct listnode
*node
, *nnode
;
5881 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5882 return BGP_ERR_INVALID_VALUE
;
5884 /* Set configuration on peer. */
5885 filter
= &peer
->filter
[afi
][safi
];
5886 if (filter
->aslist
[direct
].name
)
5887 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->aslist
[direct
].name
);
5888 filter
->aslist
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5889 filter
->aslist
[direct
].aslist
= as_list_lookup(name
);
5891 /* Check if handling a regular peer. */
5892 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5893 /* Set override-flag and process peer route updates. */
5894 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5895 PEER_FT_FILTER_LIST
);
5896 peer_on_policy_change(peer
, afi
, safi
,
5897 (direct
== FILTER_OUT
) ? 1 : 0);
5899 /* Skip peer-group mechanics for regular peers. */
5904 * Set configuration on all peer-group members, unless they are
5905 * explicitely overriding peer-group configuration.
5907 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5908 /* Skip peers with overridden configuration. */
5909 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5910 PEER_FT_FILTER_LIST
))
5913 /* Set configuration on peer-group member. */
5914 filter
= &member
->filter
[afi
][safi
];
5915 if (filter
->aslist
[direct
].name
)
5916 XFREE(MTYPE_BGP_FILTER_NAME
,
5917 filter
->aslist
[direct
].name
);
5918 filter
->aslist
[direct
].name
=
5919 XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5920 filter
->aslist
[direct
].aslist
= as_list_lookup(name
);
5922 /* Process peer route updates. */
5923 peer_on_policy_change(member
, afi
, safi
,
5924 (direct
== FILTER_OUT
) ? 1 : 0);
5930 int peer_aslist_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
)
5932 struct peer
*member
;
5933 struct bgp_filter
*filter
;
5934 struct listnode
*node
, *nnode
;
5936 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5937 return BGP_ERR_INVALID_VALUE
;
5939 /* Unset override-flag unconditionally. */
5940 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5941 PEER_FT_FILTER_LIST
);
5943 /* Inherit configuration from peer-group if peer is member. */
5944 if (peer_group_active(peer
)) {
5945 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
5946 filter
[afi
][safi
].aslist
[direct
].name
,
5947 MTYPE_BGP_FILTER_NAME
);
5948 PEER_ATTR_INHERIT(peer
, peer
->group
,
5949 filter
[afi
][safi
].aslist
[direct
].aslist
);
5951 /* Otherwise remove configuration from peer. */
5952 filter
= &peer
->filter
[afi
][safi
];
5953 if (filter
->aslist
[direct
].name
)
5954 XFREE(MTYPE_BGP_FILTER_NAME
,
5955 filter
->aslist
[direct
].name
);
5956 filter
->aslist
[direct
].name
= NULL
;
5957 filter
->aslist
[direct
].aslist
= NULL
;
5960 /* Check if handling a regular peer. */
5961 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5962 /* Process peer route updates. */
5963 peer_on_policy_change(peer
, afi
, safi
,
5964 (direct
== FILTER_OUT
) ? 1 : 0);
5966 /* Skip peer-group mechanics for regular peers. */
5971 * Remove configuration on all peer-group members, unless they are
5972 * explicitely overriding peer-group configuration.
5974 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5975 /* Skip peers with overridden configuration. */
5976 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5977 PEER_FT_FILTER_LIST
))
5980 /* Remove configuration on peer-group member. */
5981 filter
= &member
->filter
[afi
][safi
];
5982 if (filter
->aslist
[direct
].name
)
5983 XFREE(MTYPE_BGP_FILTER_NAME
,
5984 filter
->aslist
[direct
].name
);
5985 filter
->aslist
[direct
].name
= NULL
;
5986 filter
->aslist
[direct
].aslist
= NULL
;
5988 /* Process peer route updates. */
5989 peer_on_policy_change(member
, afi
, safi
,
5990 (direct
== FILTER_OUT
) ? 1 : 0);
5996 static void peer_aslist_update(const char *aslist_name
)
6001 struct listnode
*mnode
, *mnnode
;
6002 struct listnode
*node
, *nnode
;
6005 struct peer_group
*group
;
6006 struct bgp_filter
*filter
;
6008 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
)) {
6009 update_group_policy_update(bgp
, BGP_POLICY_FILTER_LIST
,
6012 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
6013 FOREACH_AFI_SAFI (afi
, safi
) {
6014 filter
= &peer
->filter
[afi
][safi
];
6016 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
6018 if (filter
->aslist
[direct
].name
)
6019 filter
->aslist
[direct
]
6020 .aslist
= as_list_lookup(
6021 filter
->aslist
[direct
]
6024 filter
->aslist
[direct
].aslist
=
6029 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
6030 FOREACH_AFI_SAFI (afi
, safi
) {
6031 filter
= &group
->conf
->filter
[afi
][safi
];
6033 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
6035 if (filter
->aslist
[direct
].name
)
6036 filter
->aslist
[direct
]
6037 .aslist
= as_list_lookup(
6038 filter
->aslist
[direct
]
6041 filter
->aslist
[direct
].aslist
=
6049 static void peer_aslist_add(char *aslist_name
)
6051 peer_aslist_update(aslist_name
);
6052 route_map_notify_dependencies((char *)aslist_name
,
6053 RMAP_EVENT_ASLIST_ADDED
);
6056 static void peer_aslist_del(const char *aslist_name
)
6058 peer_aslist_update(aslist_name
);
6059 route_map_notify_dependencies(aslist_name
, RMAP_EVENT_ASLIST_DELETED
);
6063 int peer_route_map_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
6064 const char *name
, struct route_map
*route_map
)
6066 struct peer
*member
;
6067 struct bgp_filter
*filter
;
6068 struct listnode
*node
, *nnode
;
6070 if (direct
!= RMAP_IN
&& direct
!= RMAP_OUT
)
6071 return BGP_ERR_INVALID_VALUE
;
6073 /* Set configuration on peer. */
6074 filter
= &peer
->filter
[afi
][safi
];
6075 if (filter
->map
[direct
].name
)
6076 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6077 filter
->map
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6078 filter
->map
[direct
].map
= route_map
;
6080 /* Check if handling a regular peer. */
6081 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6082 /* Set override-flag and process peer route updates. */
6083 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
6085 peer_on_policy_change(peer
, afi
, safi
,
6086 (direct
== RMAP_OUT
) ? 1 : 0);
6088 /* Skip peer-group mechanics for regular peers. */
6093 * Set configuration on all peer-group members, unless they are
6094 * explicitely overriding peer-group configuration.
6096 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6097 /* Skip peers with overridden configuration. */
6098 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
6102 /* Set configuration on peer-group member. */
6103 filter
= &member
->filter
[afi
][safi
];
6104 if (filter
->map
[direct
].name
)
6105 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6106 filter
->map
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6107 filter
->map
[direct
].map
= route_map
;
6109 /* Process peer route updates. */
6110 peer_on_policy_change(member
, afi
, safi
,
6111 (direct
== RMAP_OUT
) ? 1 : 0);
6116 /* Unset route-map from the peer. */
6117 int peer_route_map_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
)
6119 struct peer
*member
;
6120 struct bgp_filter
*filter
;
6121 struct listnode
*node
, *nnode
;
6123 if (direct
!= RMAP_IN
&& direct
!= RMAP_OUT
)
6124 return BGP_ERR_INVALID_VALUE
;
6126 /* Unset override-flag unconditionally. */
6127 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
], PEER_FT_ROUTE_MAP
);
6129 /* Inherit configuration from peer-group if peer is member. */
6130 if (peer_group_active(peer
)) {
6131 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
6132 filter
[afi
][safi
].map
[direct
].name
,
6133 MTYPE_BGP_FILTER_NAME
);
6134 PEER_ATTR_INHERIT(peer
, peer
->group
,
6135 filter
[afi
][safi
].map
[direct
].map
);
6137 /* Otherwise remove configuration from peer. */
6138 filter
= &peer
->filter
[afi
][safi
];
6139 if (filter
->map
[direct
].name
)
6140 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6141 filter
->map
[direct
].name
= NULL
;
6142 filter
->map
[direct
].map
= NULL
;
6145 /* Check if handling a regular peer. */
6146 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6147 /* Process peer route updates. */
6148 peer_on_policy_change(peer
, afi
, safi
,
6149 (direct
== RMAP_OUT
) ? 1 : 0);
6151 /* Skip peer-group mechanics for regular peers. */
6156 * Remove configuration on all peer-group members, unless they are
6157 * explicitely overriding peer-group configuration.
6159 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6160 /* Skip peers with overridden configuration. */
6161 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
6165 /* Remove configuration on peer-group member. */
6166 filter
= &member
->filter
[afi
][safi
];
6167 if (filter
->map
[direct
].name
)
6168 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6169 filter
->map
[direct
].name
= NULL
;
6170 filter
->map
[direct
].map
= NULL
;
6172 /* Process peer route updates. */
6173 peer_on_policy_change(member
, afi
, safi
,
6174 (direct
== RMAP_OUT
) ? 1 : 0);
6180 /* Set unsuppress-map to the peer. */
6181 int peer_unsuppress_map_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
6182 const char *name
, struct route_map
*route_map
)
6184 struct peer
*member
;
6185 struct bgp_filter
*filter
;
6186 struct listnode
*node
, *nnode
;
6188 /* Set configuration on peer. */
6189 filter
= &peer
->filter
[afi
][safi
];
6190 if (filter
->usmap
.name
)
6191 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6192 filter
->usmap
.name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6193 filter
->usmap
.map
= route_map
;
6195 /* Check if handling a regular peer. */
6196 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6197 /* Set override-flag and process peer route updates. */
6198 SET_FLAG(peer
->filter_override
[afi
][safi
][0],
6199 PEER_FT_UNSUPPRESS_MAP
);
6200 peer_on_policy_change(peer
, afi
, safi
, 1);
6202 /* Skip peer-group mechanics for regular peers. */
6207 * Set configuration on all peer-group members, unless they are
6208 * explicitely overriding peer-group configuration.
6210 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6211 /* Skip peers with overridden configuration. */
6212 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][0],
6213 PEER_FT_UNSUPPRESS_MAP
))
6216 /* Set configuration on peer-group member. */
6217 filter
= &member
->filter
[afi
][safi
];
6218 if (filter
->usmap
.name
)
6219 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6220 filter
->usmap
.name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6221 filter
->usmap
.map
= route_map
;
6223 /* Process peer route updates. */
6224 peer_on_policy_change(member
, afi
, safi
, 1);
6230 /* Unset route-map from the peer. */
6231 int peer_unsuppress_map_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
6233 struct peer
*member
;
6234 struct bgp_filter
*filter
;
6235 struct listnode
*node
, *nnode
;
6237 /* Unset override-flag unconditionally. */
6238 UNSET_FLAG(peer
->filter_override
[afi
][safi
][0], PEER_FT_UNSUPPRESS_MAP
);
6240 /* Inherit configuration from peer-group if peer is member. */
6241 if (peer_group_active(peer
)) {
6242 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
6243 filter
[afi
][safi
].usmap
.name
,
6244 MTYPE_BGP_FILTER_NAME
);
6245 PEER_ATTR_INHERIT(peer
, peer
->group
,
6246 filter
[afi
][safi
].usmap
.map
);
6248 /* Otherwise remove configuration from peer. */
6249 filter
= &peer
->filter
[afi
][safi
];
6250 if (filter
->usmap
.name
)
6251 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6252 filter
->usmap
.name
= NULL
;
6253 filter
->usmap
.map
= NULL
;
6256 /* Check if handling a regular peer. */
6257 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6258 /* Process peer route updates. */
6259 peer_on_policy_change(peer
, afi
, safi
, 1);
6261 /* Skip peer-group mechanics for regular peers. */
6266 * Remove configuration on all peer-group members, unless they are
6267 * explicitely overriding peer-group configuration.
6269 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6270 /* Skip peers with overridden configuration. */
6271 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][0],
6272 PEER_FT_UNSUPPRESS_MAP
))
6275 /* Remove configuration on peer-group member. */
6276 filter
= &member
->filter
[afi
][safi
];
6277 if (filter
->usmap
.name
)
6278 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6279 filter
->usmap
.name
= NULL
;
6280 filter
->usmap
.map
= NULL
;
6282 /* Process peer route updates. */
6283 peer_on_policy_change(member
, afi
, safi
, 1);
6289 int peer_maximum_prefix_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
6290 uint32_t max
, uint8_t threshold
, int warning
,
6293 struct peer
*member
;
6294 struct listnode
*node
, *nnode
;
6296 /* Set flags and configuration on peer. */
6297 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX
);
6299 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX_WARNING
);
6301 peer_af_flag_unset(peer
, afi
, safi
,
6302 PEER_FLAG_MAX_PREFIX_WARNING
);
6304 peer
->pmax
[afi
][safi
] = max
;
6305 peer
->pmax_threshold
[afi
][safi
] = threshold
;
6306 peer
->pmax_restart
[afi
][safi
] = restart
;
6308 /* Check if handling a regular peer. */
6309 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6310 /* Re-check if peer violates maximum-prefix. */
6311 if ((peer
->status
== Established
) && (peer
->afc
[afi
][safi
]))
6312 bgp_maximum_prefix_overflow(peer
, afi
, safi
, 1);
6314 /* Skip peer-group mechanics for regular peers. */
6319 * Set flags and configuration on all peer-group members, unless they
6320 * are explicitely overriding peer-group configuration.
6322 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6323 /* Skip peers with overridden configuration. */
6324 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
6325 PEER_FLAG_MAX_PREFIX
))
6328 /* Set flag and configuration on peer-group member. */
6329 member
->pmax
[afi
][safi
] = max
;
6330 member
->pmax_threshold
[afi
][safi
] = threshold
;
6331 member
->pmax_restart
[afi
][safi
] = restart
;
6333 SET_FLAG(member
->af_flags
[afi
][safi
],
6334 PEER_FLAG_MAX_PREFIX_WARNING
);
6336 UNSET_FLAG(member
->af_flags
[afi
][safi
],
6337 PEER_FLAG_MAX_PREFIX_WARNING
);
6339 /* Re-check if peer violates maximum-prefix. */
6340 if ((member
->status
== Established
) && (member
->afc
[afi
][safi
]))
6341 bgp_maximum_prefix_overflow(member
, afi
, safi
, 1);
6347 int peer_maximum_prefix_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
6349 /* Inherit configuration from peer-group if peer is member. */
6350 if (peer_group_active(peer
)) {
6351 peer_af_flag_inherit(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX
);
6352 peer_af_flag_inherit(peer
, afi
, safi
,
6353 PEER_FLAG_MAX_PREFIX_WARNING
);
6354 PEER_ATTR_INHERIT(peer
, peer
->group
, pmax
[afi
][safi
]);
6355 PEER_ATTR_INHERIT(peer
, peer
->group
, pmax_threshold
[afi
][safi
]);
6356 PEER_ATTR_INHERIT(peer
, peer
->group
, pmax_restart
[afi
][safi
]);
6361 /* Remove flags and configuration from peer. */
6362 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX
);
6363 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX_WARNING
);
6364 peer
->pmax
[afi
][safi
] = 0;
6365 peer
->pmax_threshold
[afi
][safi
] = 0;
6366 peer
->pmax_restart
[afi
][safi
] = 0;
6369 * Remove flags and configuration from all peer-group members, unless
6370 * they are explicitely overriding peer-group configuration.
6372 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6373 struct peer
*member
;
6374 struct listnode
*node
;
6376 for (ALL_LIST_ELEMENTS_RO(peer
->group
->peer
, node
, member
)) {
6377 /* Skip peers with overridden configuration. */
6378 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
6379 PEER_FLAG_MAX_PREFIX
))
6382 /* Remove flag and configuration on peer-group member.
6384 UNSET_FLAG(member
->af_flags
[afi
][safi
],
6385 PEER_FLAG_MAX_PREFIX
);
6386 UNSET_FLAG(member
->af_flags
[afi
][safi
],
6387 PEER_FLAG_MAX_PREFIX_WARNING
);
6388 member
->pmax
[afi
][safi
] = 0;
6389 member
->pmax_threshold
[afi
][safi
] = 0;
6390 member
->pmax_restart
[afi
][safi
] = 0;
6397 int is_ebgp_multihop_configured(struct peer
*peer
)
6399 struct peer_group
*group
;
6400 struct listnode
*node
, *nnode
;
6403 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6404 group
= peer
->group
;
6405 if ((peer_sort(peer
) != BGP_PEER_IBGP
)
6406 && (group
->conf
->ttl
!= 1))
6409 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer1
)) {
6410 if ((peer_sort(peer1
) != BGP_PEER_IBGP
)
6411 && (peer1
->ttl
!= 1))
6415 if ((peer_sort(peer
) != BGP_PEER_IBGP
) && (peer
->ttl
!= 1))
6421 /* Set # of hops between us and BGP peer. */
6422 int peer_ttl_security_hops_set(struct peer
*peer
, int gtsm_hops
)
6424 struct peer_group
*group
;
6425 struct listnode
*node
, *nnode
;
6428 zlog_debug("peer_ttl_security_hops_set: set gtsm_hops to %d for %s",
6429 gtsm_hops
, peer
->host
);
6431 /* We cannot configure ttl-security hops when ebgp-multihop is already
6432 set. For non peer-groups, the check is simple. For peer-groups,
6434 slightly messy, because we need to check both the peer-group
6436 and all peer-group members for any trace of ebgp-multihop
6438 before actually applying the ttl-security rules. Cisco really made a
6439 mess of this configuration parameter, and OpenBGPD got it right.
6442 if ((peer
->gtsm_hops
== 0) && (peer
->sort
!= BGP_PEER_IBGP
)) {
6443 if (is_ebgp_multihop_configured(peer
))
6444 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
6446 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6447 peer
->gtsm_hops
= gtsm_hops
;
6449 /* Calling ebgp multihop also resets the session.
6450 * On restart, NHT will get setup correctly as will the
6451 * min & max ttls on the socket. The return value is
6454 ret
= peer_ebgp_multihop_set(peer
, MAXTTL
);
6459 group
= peer
->group
;
6460 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
,
6462 peer
->gtsm_hops
= group
->conf
->gtsm_hops
;
6464 /* Calling ebgp multihop also resets the
6466 * On restart, NHT will get setup correctly as
6468 * min & max ttls on the socket. The return
6472 peer_ebgp_multihop_set(peer
, MAXTTL
);
6476 /* Post the first gtsm setup or if its ibgp, maxttl setting
6478 * necessary, just set the minttl.
6480 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6481 peer
->gtsm_hops
= gtsm_hops
;
6484 sockopt_minttl(peer
->su
.sa
.sa_family
, peer
->fd
,
6485 MAXTTL
+ 1 - gtsm_hops
);
6486 if ((peer
->status
< Established
) && peer
->doppelganger
6487 && (peer
->doppelganger
->fd
>= 0))
6488 sockopt_minttl(peer
->su
.sa
.sa_family
,
6489 peer
->doppelganger
->fd
,
6490 MAXTTL
+ 1 - gtsm_hops
);
6492 group
= peer
->group
;
6493 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
,
6495 peer
->gtsm_hops
= group
->conf
->gtsm_hops
;
6497 /* Change setting of existing peer
6498 * established then change value (may break
6500 * not established yet (teardown session and
6502 * no session then do nothing (will get
6503 * handled by next connection)
6505 if (peer
->fd
>= 0 && peer
->gtsm_hops
!= 0)
6507 peer
->su
.sa
.sa_family
, peer
->fd
,
6508 MAXTTL
+ 1 - peer
->gtsm_hops
);
6509 if ((peer
->status
< Established
)
6510 && peer
->doppelganger
6511 && (peer
->doppelganger
->fd
>= 0))
6512 sockopt_minttl(peer
->su
.sa
.sa_family
,
6513 peer
->doppelganger
->fd
,
6514 MAXTTL
+ 1 - gtsm_hops
);
6522 int peer_ttl_security_hops_unset(struct peer
*peer
)
6524 struct peer_group
*group
;
6525 struct listnode
*node
, *nnode
;
6528 zlog_debug("peer_ttl_security_hops_unset: set gtsm_hops to zero for %s",
6531 /* if a peer-group member, then reset to peer-group default rather than
6533 if (peer_group_active(peer
))
6534 peer
->gtsm_hops
= peer
->group
->conf
->gtsm_hops
;
6536 peer
->gtsm_hops
= 0;
6538 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6539 /* Invoking ebgp_multihop_set will set the TTL back to the
6541 * value as well as restting the NHT and such. The session is
6544 if (peer
->sort
== BGP_PEER_EBGP
)
6545 ret
= peer_ebgp_multihop_unset(peer
);
6548 sockopt_minttl(peer
->su
.sa
.sa_family
, peer
->fd
,
6551 if ((peer
->status
< Established
) && peer
->doppelganger
6552 && (peer
->doppelganger
->fd
>= 0))
6553 sockopt_minttl(peer
->su
.sa
.sa_family
,
6554 peer
->doppelganger
->fd
, 0);
6557 group
= peer
->group
;
6558 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
6559 peer
->gtsm_hops
= 0;
6560 if (peer
->sort
== BGP_PEER_EBGP
)
6561 ret
= peer_ebgp_multihop_unset(peer
);
6564 sockopt_minttl(peer
->su
.sa
.sa_family
,
6567 if ((peer
->status
< Established
)
6568 && peer
->doppelganger
6569 && (peer
->doppelganger
->fd
>= 0))
6570 sockopt_minttl(peer
->su
.sa
.sa_family
,
6571 peer
->doppelganger
->fd
,
6581 * If peer clear is invoked in a loop for all peers on the BGP instance,
6582 * it may end up freeing the doppelganger, and if this was the next node
6583 * to the current node, we would end up accessing the freed next node.
6584 * Pass along additional parameter which can be updated if next node
6585 * is freed; only required when walking the peer list on BGP instance.
6587 int peer_clear(struct peer
*peer
, struct listnode
**nnode
)
6589 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_SHUTDOWN
)) {
6590 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_PREFIX_OVERFLOW
)) {
6591 UNSET_FLAG(peer
->sflags
, PEER_STATUS_PREFIX_OVERFLOW
);
6592 if (peer
->t_pmax_restart
) {
6593 BGP_TIMER_OFF(peer
->t_pmax_restart
);
6594 if (bgp_debug_neighbor_events(peer
))
6596 "%s Maximum-prefix restart timer canceled",
6599 BGP_EVENT_ADD(peer
, BGP_Start
);
6603 peer
->v_start
= BGP_INIT_START_TIMER
;
6604 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
6605 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
6606 BGP_NOTIFY_CEASE_ADMIN_RESET
);
6608 bgp_session_reset_safe(peer
, nnode
);
6613 int peer_clear_soft(struct peer
*peer
, afi_t afi
, safi_t safi
,
6614 enum bgp_clear_type stype
)
6616 struct peer_af
*paf
;
6618 if (peer
->status
!= Established
)
6621 if (!peer
->afc
[afi
][safi
])
6622 return BGP_ERR_AF_UNCONFIGURED
;
6624 peer
->rtt
= sockopt_tcp_rtt(peer
->fd
);
6626 if (stype
== BGP_CLEAR_SOFT_OUT
|| stype
== BGP_CLEAR_SOFT_BOTH
) {
6627 /* Clear the "neighbor x.x.x.x default-originate" flag */
6628 paf
= peer_af_find(peer
, afi
, safi
);
6629 if (paf
&& paf
->subgroup
6630 && CHECK_FLAG(paf
->subgroup
->sflags
,
6631 SUBGRP_STATUS_DEFAULT_ORIGINATE
))
6632 UNSET_FLAG(paf
->subgroup
->sflags
,
6633 SUBGRP_STATUS_DEFAULT_ORIGINATE
);
6635 bgp_announce_route(peer
, afi
, safi
);
6638 if (stype
== BGP_CLEAR_SOFT_IN_ORF_PREFIX
) {
6639 if (CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6640 PEER_CAP_ORF_PREFIX_SM_ADV
)
6641 && (CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6642 PEER_CAP_ORF_PREFIX_RM_RCV
)
6643 || CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6644 PEER_CAP_ORF_PREFIX_RM_OLD_RCV
))) {
6645 struct bgp_filter
*filter
= &peer
->filter
[afi
][safi
];
6646 uint8_t prefix_type
;
6648 if (CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6649 PEER_CAP_ORF_PREFIX_RM_RCV
))
6650 prefix_type
= ORF_TYPE_PREFIX
;
6652 prefix_type
= ORF_TYPE_PREFIX_OLD
;
6654 if (filter
->plist
[FILTER_IN
].plist
) {
6655 if (CHECK_FLAG(peer
->af_sflags
[afi
][safi
],
6656 PEER_STATUS_ORF_PREFIX_SEND
))
6657 bgp_route_refresh_send(
6658 peer
, afi
, safi
, prefix_type
,
6660 bgp_route_refresh_send(peer
, afi
, safi
,
6662 REFRESH_IMMEDIATE
, 0);
6664 if (CHECK_FLAG(peer
->af_sflags
[afi
][safi
],
6665 PEER_STATUS_ORF_PREFIX_SEND
))
6666 bgp_route_refresh_send(
6667 peer
, afi
, safi
, prefix_type
,
6668 REFRESH_IMMEDIATE
, 1);
6670 bgp_route_refresh_send(peer
, afi
, safi
,
6677 if (stype
== BGP_CLEAR_SOFT_IN
|| stype
== BGP_CLEAR_SOFT_BOTH
6678 || stype
== BGP_CLEAR_SOFT_IN_ORF_PREFIX
) {
6679 /* If neighbor has soft reconfiguration inbound flag.
6680 Use Adj-RIB-In database. */
6681 if (CHECK_FLAG(peer
->af_flags
[afi
][safi
],
6682 PEER_FLAG_SOFT_RECONFIG
))
6683 bgp_soft_reconfig_in(peer
, afi
, safi
);
6685 /* If neighbor has route refresh capability, send route
6687 message to the peer. */
6688 if (CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_OLD_RCV
)
6689 || CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_NEW_RCV
))
6690 bgp_route_refresh_send(peer
, afi
, safi
, 0, 0,
6693 return BGP_ERR_SOFT_RECONFIG_UNCONFIGURED
;
6699 /* Display peer uptime.*/
6700 char *peer_uptime(time_t uptime2
, char *buf
, size_t len
, bool use_json
,
6703 time_t uptime1
, epoch_tbuf
;
6706 /* If there is no connection has been done before print `never'. */
6709 json_object_string_add(json
, "peerUptime", "never");
6710 json_object_int_add(json
, "peerUptimeMsec", 0);
6712 snprintf(buf
, len
, "never");
6716 /* Get current time. */
6717 uptime1
= bgp_clock();
6719 tm
= gmtime(&uptime1
);
6721 if (uptime1
< ONE_DAY_SECOND
)
6722 snprintf(buf
, len
, "%02d:%02d:%02d", tm
->tm_hour
, tm
->tm_min
,
6724 else if (uptime1
< ONE_WEEK_SECOND
)
6725 snprintf(buf
, len
, "%dd%02dh%02dm", tm
->tm_yday
, tm
->tm_hour
,
6727 else if (uptime1
< ONE_YEAR_SECOND
)
6728 snprintf(buf
, len
, "%02dw%dd%02dh", tm
->tm_yday
/ 7,
6729 tm
->tm_yday
- ((tm
->tm_yday
/ 7) * 7), tm
->tm_hour
);
6731 snprintf(buf
, len
, "%02dy%02dw%dd", tm
->tm_year
- 70,
6733 tm
->tm_yday
- ((tm
->tm_yday
/ 7) * 7));
6736 epoch_tbuf
= time(NULL
) - uptime1
;
6737 json_object_string_add(json
, "peerUptime", buf
);
6738 json_object_int_add(json
, "peerUptimeMsec", uptime1
* 1000);
6739 json_object_int_add(json
, "peerUptimeEstablishedEpoch",
6746 static void bgp_config_write_filter(struct vty
*vty
, struct peer
*peer
,
6747 afi_t afi
, safi_t safi
)
6749 struct bgp_filter
*filter
;
6753 filter
= &peer
->filter
[afi
][safi
];
6755 /* distribute-list. */
6756 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_DISTRIBUTE_LIST
,
6758 vty_out(vty
, " neighbor %s distribute-list %s in\n", addr
,
6759 filter
->dlist
[FILTER_IN
].name
);
6761 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_DISTRIBUTE_LIST
,
6763 vty_out(vty
, " neighbor %s distribute-list %s out\n", addr
,
6764 filter
->dlist
[FILTER_OUT
].name
);
6767 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_PREFIX_LIST
,
6769 vty_out(vty
, " neighbor %s prefix-list %s in\n", addr
,
6770 filter
->plist
[FILTER_IN
].name
);
6772 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_PREFIX_LIST
,
6774 vty_out(vty
, " neighbor %s prefix-list %s out\n", addr
,
6775 filter
->plist
[FILTER_OUT
].name
);
6778 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_ROUTE_MAP
, RMAP_IN
))
6779 vty_out(vty
, " neighbor %s route-map %s in\n", addr
,
6780 filter
->map
[RMAP_IN
].name
);
6782 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_ROUTE_MAP
,
6784 vty_out(vty
, " neighbor %s route-map %s out\n", addr
,
6785 filter
->map
[RMAP_OUT
].name
);
6787 /* unsuppress-map */
6788 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_UNSUPPRESS_MAP
, 0))
6789 vty_out(vty
, " neighbor %s unsuppress-map %s\n", addr
,
6790 filter
->usmap
.name
);
6793 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_FILTER_LIST
,
6795 vty_out(vty
, " neighbor %s filter-list %s in\n", addr
,
6796 filter
->aslist
[FILTER_IN
].name
);
6798 if (peergroup_filter_check(peer
, afi
, safi
, PEER_FT_FILTER_LIST
,
6800 vty_out(vty
, " neighbor %s filter-list %s out\n", addr
,
6801 filter
->aslist
[FILTER_OUT
].name
);
6804 /* BGP peer configuration display function. */
6805 static void bgp_config_write_peer_global(struct vty
*vty
, struct bgp
*bgp
,
6808 struct peer
*g_peer
= NULL
;
6809 char buf
[SU_ADDRSTRLEN
];
6811 int if_pg_printed
= FALSE
;
6812 int if_ras_printed
= FALSE
;
6814 /* Skip dynamic neighbors. */
6815 if (peer_dynamic_neighbor(peer
))
6819 addr
= peer
->conf_if
;
6823 /************************************
6824 ****** Global to the neighbor ******
6825 ************************************/
6826 if (peer
->conf_if
) {
6827 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_IFPEER_V6ONLY
))
6828 vty_out(vty
, " neighbor %s interface v6only", addr
);
6830 vty_out(vty
, " neighbor %s interface", addr
);
6832 if (peer_group_active(peer
)) {
6833 vty_out(vty
, " peer-group %s", peer
->group
->name
);
6834 if_pg_printed
= TRUE
;
6835 } else if (peer
->as_type
== AS_SPECIFIED
) {
6836 vty_out(vty
, " remote-as %u", peer
->as
);
6837 if_ras_printed
= TRUE
;
6838 } else if (peer
->as_type
== AS_INTERNAL
) {
6839 vty_out(vty
, " remote-as internal");
6840 if_ras_printed
= TRUE
;
6841 } else if (peer
->as_type
== AS_EXTERNAL
) {
6842 vty_out(vty
, " remote-as external");
6843 if_ras_printed
= TRUE
;
6849 /* remote-as and peer-group */
6850 /* peer is a member of a peer-group */
6851 if (peer_group_active(peer
)) {
6852 g_peer
= peer
->group
->conf
;
6854 if (g_peer
->as_type
== AS_UNSPECIFIED
&& !if_ras_printed
) {
6855 if (peer
->as_type
== AS_SPECIFIED
) {
6856 vty_out(vty
, " neighbor %s remote-as %u\n",
6858 } else if (peer
->as_type
== AS_INTERNAL
) {
6860 " neighbor %s remote-as internal\n",
6862 } else if (peer
->as_type
== AS_EXTERNAL
) {
6864 " neighbor %s remote-as external\n",
6869 /* For swpX peers we displayed the peer-group
6870 * via 'neighbor swpX interface peer-group WORD' */
6872 vty_out(vty
, " neighbor %s peer-group %s\n", addr
,
6876 /* peer is NOT a member of a peer-group */
6878 /* peer is a peer-group, declare the peer-group */
6879 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6880 vty_out(vty
, " neighbor %s peer-group\n", addr
);
6883 if (!if_ras_printed
) {
6884 if (peer
->as_type
== AS_SPECIFIED
) {
6885 vty_out(vty
, " neighbor %s remote-as %u\n",
6887 } else if (peer
->as_type
== AS_INTERNAL
) {
6889 " neighbor %s remote-as internal\n",
6891 } else if (peer
->as_type
== AS_EXTERNAL
) {
6893 " neighbor %s remote-as external\n",
6900 if (peergroup_flag_check(peer
, PEER_FLAG_LOCAL_AS
)) {
6901 vty_out(vty
, " neighbor %s local-as %u", addr
,
6902 peer
->change_local_as
);
6903 if (peergroup_flag_check(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
))
6904 vty_out(vty
, " no-prepend");
6905 if (peergroup_flag_check(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
))
6906 vty_out(vty
, " replace-as");
6912 vty_out(vty
, " neighbor %s description %s\n", addr
, peer
->desc
);
6916 if (peergroup_flag_check(peer
, PEER_FLAG_SHUTDOWN
)) {
6917 if (peer
->tx_shutdown_message
)
6918 vty_out(vty
, " neighbor %s shutdown message %s\n", addr
,
6919 peer
->tx_shutdown_message
);
6921 vty_out(vty
, " neighbor %s shutdown\n", addr
);
6925 if (peer
->bfd_info
) {
6926 if (!peer_group_active(peer
) || !g_peer
->bfd_info
) {
6927 bgp_bfd_peer_config_write(vty
, peer
, addr
);
6932 if (peergroup_flag_check(peer
, PEER_FLAG_PASSWORD
))
6933 vty_out(vty
, " neighbor %s password %s\n", addr
,
6937 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_LONESOUL
)) {
6938 if (!peer_group_active(peer
)) {
6939 vty_out(vty
, " neighbor %s solo\n", addr
);
6944 if (peer
->port
!= BGP_PORT_DEFAULT
) {
6945 vty_out(vty
, " neighbor %s port %d\n", addr
, peer
->port
);
6948 /* Local interface name */
6950 vty_out(vty
, " neighbor %s interface %s\n", addr
, peer
->ifname
);
6954 if (peergroup_flag_check(peer
, PEER_FLAG_PASSIVE
))
6955 vty_out(vty
, " neighbor %s passive\n", addr
);
6958 if (peer
->sort
!= BGP_PEER_IBGP
&& peer
->ttl
!= 1
6959 && !(peer
->gtsm_hops
!= 0 && peer
->ttl
== MAXTTL
)) {
6960 if (!peer_group_active(peer
) || g_peer
->ttl
!= peer
->ttl
) {
6961 vty_out(vty
, " neighbor %s ebgp-multihop %d\n", addr
,
6966 /* ttl-security hops */
6967 if (peer
->gtsm_hops
!= 0) {
6968 if (!peer_group_active(peer
)
6969 || g_peer
->gtsm_hops
!= peer
->gtsm_hops
) {
6970 vty_out(vty
, " neighbor %s ttl-security hops %d\n",
6971 addr
, peer
->gtsm_hops
);
6975 /* disable-connected-check */
6976 if (peergroup_flag_check(peer
, PEER_FLAG_DISABLE_CONNECTED_CHECK
))
6977 vty_out(vty
, " neighbor %s disable-connected-check\n", addr
);
6979 /* enforce-first-as */
6980 if (peergroup_flag_check(peer
, PEER_FLAG_ENFORCE_FIRST_AS
))
6981 vty_out(vty
, " neighbor %s enforce-first-as\n", addr
);
6984 if (peergroup_flag_check(peer
, PEER_FLAG_UPDATE_SOURCE
)) {
6985 if (peer
->update_source
)
6986 vty_out(vty
, " neighbor %s update-source %s\n", addr
,
6987 sockunion2str(peer
->update_source
, buf
,
6989 else if (peer
->update_if
)
6990 vty_out(vty
, " neighbor %s update-source %s\n", addr
,
6994 /* advertisement-interval */
6995 if (peergroup_flag_check(peer
, PEER_FLAG_ROUTEADV
))
6996 vty_out(vty
, " neighbor %s advertisement-interval %u\n", addr
,
7000 if (peergroup_flag_check(peer
, PEER_FLAG_TIMER
))
7001 vty_out(vty
, " neighbor %s timers %u %u\n", addr
,
7002 peer
->keepalive
, peer
->holdtime
);
7004 /* timers connect */
7005 if (peergroup_flag_check(peer
, PEER_FLAG_TIMER_CONNECT
))
7006 vty_out(vty
, " neighbor %s timers connect %u\n", addr
,
7009 /* capability dynamic */
7010 if (peergroup_flag_check(peer
, PEER_FLAG_DYNAMIC_CAPABILITY
))
7011 vty_out(vty
, " neighbor %s capability dynamic\n", addr
);
7013 /* capability extended-nexthop */
7014 if (peergroup_flag_check(peer
, PEER_FLAG_CAPABILITY_ENHE
)) {
7015 if (CHECK_FLAG(peer
->flags_invert
, PEER_FLAG_CAPABILITY_ENHE
))
7017 " no neighbor %s capability extended-nexthop\n",
7021 " neighbor %s capability extended-nexthop\n",
7025 /* dont-capability-negotiation */
7026 if (peergroup_flag_check(peer
, PEER_FLAG_DONT_CAPABILITY
))
7027 vty_out(vty
, " neighbor %s dont-capability-negotiate\n", addr
);
7029 /* override-capability */
7030 if (peergroup_flag_check(peer
, PEER_FLAG_OVERRIDE_CAPABILITY
))
7031 vty_out(vty
, " neighbor %s override-capability\n", addr
);
7033 /* strict-capability-match */
7034 if (peergroup_flag_check(peer
, PEER_FLAG_STRICT_CAP_MATCH
))
7035 vty_out(vty
, " neighbor %s strict-capability-match\n", addr
);
7038 /* BGP peer configuration display function. */
7039 static void bgp_config_write_peer_af(struct vty
*vty
, struct bgp
*bgp
,
7040 struct peer
*peer
, afi_t afi
, safi_t safi
)
7042 struct peer
*g_peer
= NULL
;
7044 bool flag_scomm
, flag_secomm
, flag_slcomm
;
7046 /* Skip dynamic neighbors. */
7047 if (peer_dynamic_neighbor(peer
))
7051 addr
= peer
->conf_if
;
7055 /************************************
7056 ****** Per AF to the neighbor ******
7057 ************************************/
7058 if (peer_group_active(peer
)) {
7059 g_peer
= peer
->group
->conf
;
7061 /* If the peer-group is active but peer is not, print a 'no
7063 if (g_peer
->afc
[afi
][safi
] && !peer
->afc
[afi
][safi
]) {
7064 vty_out(vty
, " no neighbor %s activate\n", addr
);
7067 /* If the peer-group is not active but peer is, print an
7069 else if (!g_peer
->afc
[afi
][safi
] && peer
->afc
[afi
][safi
]) {
7070 vty_out(vty
, " neighbor %s activate\n", addr
);
7073 if (peer
->afc
[afi
][safi
]) {
7074 if ((afi
== AFI_IP
) && (safi
== SAFI_UNICAST
)) {
7075 if (bgp_flag_check(bgp
,
7076 BGP_FLAG_NO_DEFAULT_IPV4
)) {
7077 vty_out(vty
, " neighbor %s activate\n",
7081 vty_out(vty
, " neighbor %s activate\n", addr
);
7083 if ((afi
== AFI_IP
) && (safi
== SAFI_UNICAST
)) {
7084 if (!bgp_flag_check(bgp
,
7085 BGP_FLAG_NO_DEFAULT_IPV4
)) {
7087 " no neighbor %s activate\n",
7094 /* addpath TX knobs */
7095 if (peergroup_af_addpath_check(peer
, afi
, safi
)) {
7096 switch (peer
->addpath_type
[afi
][safi
]) {
7097 case BGP_ADDPATH_ALL
:
7098 vty_out(vty
, " neighbor %s addpath-tx-all-paths\n",
7101 case BGP_ADDPATH_BEST_PER_AS
:
7103 " neighbor %s addpath-tx-bestpath-per-AS\n",
7106 case BGP_ADDPATH_MAX
:
7107 case BGP_ADDPATH_NONE
:
7112 /* ORF capability. */
7113 if (peergroup_af_flag_check(peer
, afi
, safi
, PEER_FLAG_ORF_PREFIX_SM
)
7114 || peergroup_af_flag_check(peer
, afi
, safi
,
7115 PEER_FLAG_ORF_PREFIX_RM
)) {
7116 vty_out(vty
, " neighbor %s capability orf prefix-list", addr
);
7118 if (peergroup_af_flag_check(peer
, afi
, safi
,
7119 PEER_FLAG_ORF_PREFIX_SM
)
7120 && peergroup_af_flag_check(peer
, afi
, safi
,
7121 PEER_FLAG_ORF_PREFIX_RM
))
7122 vty_out(vty
, " both");
7123 else if (peergroup_af_flag_check(peer
, afi
, safi
,
7124 PEER_FLAG_ORF_PREFIX_SM
))
7125 vty_out(vty
, " send");
7127 vty_out(vty
, " receive");
7131 /* Route reflector client. */
7132 if (peergroup_af_flag_check(peer
, afi
, safi
,
7133 PEER_FLAG_REFLECTOR_CLIENT
)) {
7134 vty_out(vty
, " neighbor %s route-reflector-client\n", addr
);
7137 /* next-hop-self force */
7138 if (peergroup_af_flag_check(peer
, afi
, safi
,
7139 PEER_FLAG_FORCE_NEXTHOP_SELF
)) {
7140 vty_out(vty
, " neighbor %s next-hop-self force\n", addr
);
7144 if (peergroup_af_flag_check(peer
, afi
, safi
, PEER_FLAG_NEXTHOP_SELF
)) {
7145 vty_out(vty
, " neighbor %s next-hop-self\n", addr
);
7148 /* remove-private-AS */
7149 if (peergroup_af_flag_check(peer
, afi
, safi
,
7150 PEER_FLAG_REMOVE_PRIVATE_AS_ALL_REPLACE
)) {
7151 vty_out(vty
, " neighbor %s remove-private-AS all replace-AS\n",
7155 else if (peergroup_af_flag_check(peer
, afi
, safi
,
7156 PEER_FLAG_REMOVE_PRIVATE_AS_REPLACE
)) {
7157 vty_out(vty
, " neighbor %s remove-private-AS replace-AS\n",
7161 else if (peergroup_af_flag_check(peer
, afi
, safi
,
7162 PEER_FLAG_REMOVE_PRIVATE_AS_ALL
)) {
7163 vty_out(vty
, " neighbor %s remove-private-AS all\n", addr
);
7166 else if (peergroup_af_flag_check(peer
, afi
, safi
,
7167 PEER_FLAG_REMOVE_PRIVATE_AS
)) {
7168 vty_out(vty
, " neighbor %s remove-private-AS\n", addr
);
7172 if (peergroup_af_flag_check(peer
, afi
, safi
, PEER_FLAG_AS_OVERRIDE
)) {
7173 vty_out(vty
, " neighbor %s as-override\n", addr
);
7176 /* send-community print. */
7177 flag_scomm
= peergroup_af_flag_check(peer
, afi
, safi
,
7178 PEER_FLAG_SEND_COMMUNITY
);
7179 flag_secomm
= peergroup_af_flag_check(peer
, afi
, safi
,
7180 PEER_FLAG_SEND_EXT_COMMUNITY
);
7181 flag_slcomm
= peergroup_af_flag_check(peer
, afi
, safi
,
7182 PEER_FLAG_SEND_LARGE_COMMUNITY
);
7184 if (!bgp_option_check(BGP_OPT_CONFIG_CISCO
)) {
7185 if (flag_scomm
&& flag_secomm
&& flag_slcomm
) {
7186 vty_out(vty
, " no neighbor %s send-community all\n",
7191 " no neighbor %s send-community\n",
7195 " no neighbor %s send-community extended\n",
7200 " no neighbor %s send-community large\n",
7204 if (flag_scomm
&& flag_secomm
&& flag_slcomm
) {
7205 vty_out(vty
, " neighbor %s send-community all\n",
7207 } else if (flag_scomm
&& flag_secomm
) {
7208 vty_out(vty
, " neighbor %s send-community both\n",
7212 vty_out(vty
, " neighbor %s send-community\n",
7216 " neighbor %s send-community extended\n",
7220 " neighbor %s send-community large\n",
7225 /* Default information */
7226 if (peergroup_af_flag_check(peer
, afi
, safi
,
7227 PEER_FLAG_DEFAULT_ORIGINATE
)) {
7228 vty_out(vty
, " neighbor %s default-originate", addr
);
7230 if (peer
->default_rmap
[afi
][safi
].name
)
7231 vty_out(vty
, " route-map %s",
7232 peer
->default_rmap
[afi
][safi
].name
);
7237 /* Soft reconfiguration inbound. */
7238 if (peergroup_af_flag_check(peer
, afi
, safi
, PEER_FLAG_SOFT_RECONFIG
)) {
7239 vty_out(vty
, " neighbor %s soft-reconfiguration inbound\n",
7243 /* maximum-prefix. */
7244 if (peergroup_af_flag_check(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX
)) {
7245 vty_out(vty
, " neighbor %s maximum-prefix %lu", addr
,
7246 peer
->pmax
[afi
][safi
]);
7248 if (peer
->pmax_threshold
[afi
][safi
]
7249 != MAXIMUM_PREFIX_THRESHOLD_DEFAULT
)
7250 vty_out(vty
, " %u", peer
->pmax_threshold
[afi
][safi
]);
7251 if (peer_af_flag_check(peer
, afi
, safi
,
7252 PEER_FLAG_MAX_PREFIX_WARNING
))
7253 vty_out(vty
, " warning-only");
7254 if (peer
->pmax_restart
[afi
][safi
])
7255 vty_out(vty
, " restart %u",
7256 peer
->pmax_restart
[afi
][safi
]);
7261 /* Route server client. */
7262 if (peergroup_af_flag_check(peer
, afi
, safi
,
7263 PEER_FLAG_RSERVER_CLIENT
)) {
7264 vty_out(vty
, " neighbor %s route-server-client\n", addr
);
7267 /* Nexthop-local unchanged. */
7268 if (peergroup_af_flag_check(peer
, afi
, safi
,
7269 PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED
)) {
7270 vty_out(vty
, " neighbor %s nexthop-local unchanged\n", addr
);
7273 /* allowas-in <1-10> */
7274 if (peergroup_af_flag_check(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN
)) {
7275 if (peer_af_flag_check(peer
, afi
, safi
,
7276 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
7277 vty_out(vty
, " neighbor %s allowas-in origin\n", addr
);
7278 } else if (peer
->allowas_in
[afi
][safi
] == 3) {
7279 vty_out(vty
, " neighbor %s allowas-in\n", addr
);
7281 vty_out(vty
, " neighbor %s allowas-in %d\n", addr
,
7282 peer
->allowas_in
[afi
][safi
]);
7287 if (peergroup_af_flag_check(peer
, afi
, safi
, PEER_FLAG_WEIGHT
))
7288 vty_out(vty
, " neighbor %s weight %lu\n", addr
,
7289 peer
->weight
[afi
][safi
]);
7292 bgp_config_write_filter(vty
, peer
, afi
, safi
);
7294 /* atribute-unchanged. */
7295 if (peer_af_flag_check(peer
, afi
, safi
, PEER_FLAG_AS_PATH_UNCHANGED
)
7296 || (safi
!= SAFI_EVPN
7297 && peer_af_flag_check(peer
, afi
, safi
,
7298 PEER_FLAG_NEXTHOP_UNCHANGED
))
7299 || peer_af_flag_check(peer
, afi
, safi
, PEER_FLAG_MED_UNCHANGED
)) {
7301 if (!peer_group_active(peer
)
7302 || peergroup_af_flag_check(peer
, afi
, safi
,
7303 PEER_FLAG_AS_PATH_UNCHANGED
)
7304 || peergroup_af_flag_check(peer
, afi
, safi
,
7305 PEER_FLAG_NEXTHOP_UNCHANGED
)
7306 || peergroup_af_flag_check(peer
, afi
, safi
,
7307 PEER_FLAG_MED_UNCHANGED
)) {
7310 " neighbor %s attribute-unchanged%s%s%s\n",
7312 peer_af_flag_check(peer
, afi
, safi
,
7313 PEER_FLAG_AS_PATH_UNCHANGED
)
7316 peer_af_flag_check(peer
, afi
, safi
,
7317 PEER_FLAG_NEXTHOP_UNCHANGED
)
7320 peer_af_flag_check(peer
, afi
, safi
,
7321 PEER_FLAG_MED_UNCHANGED
)
7328 /* Address family based peer configuration display. */
7329 static void bgp_config_write_family(struct vty
*vty
, struct bgp
*bgp
, afi_t afi
,
7333 struct peer_group
*group
;
7334 struct listnode
*node
, *nnode
;
7337 vty_frame(vty
, " !\n address-family ");
7338 if (afi
== AFI_IP
) {
7339 if (safi
== SAFI_UNICAST
)
7340 vty_frame(vty
, "ipv4 unicast");
7341 else if (safi
== SAFI_LABELED_UNICAST
)
7342 vty_frame(vty
, "ipv4 labeled-unicast");
7343 else if (safi
== SAFI_MULTICAST
)
7344 vty_frame(vty
, "ipv4 multicast");
7345 else if (safi
== SAFI_MPLS_VPN
)
7346 vty_frame(vty
, "ipv4 vpn");
7347 else if (safi
== SAFI_ENCAP
)
7348 vty_frame(vty
, "ipv4 encap");
7349 else if (safi
== SAFI_FLOWSPEC
)
7350 vty_frame(vty
, "ipv4 flowspec");
7351 } else if (afi
== AFI_IP6
) {
7352 if (safi
== SAFI_UNICAST
)
7353 vty_frame(vty
, "ipv6 unicast");
7354 else if (safi
== SAFI_LABELED_UNICAST
)
7355 vty_frame(vty
, "ipv6 labeled-unicast");
7356 else if (safi
== SAFI_MULTICAST
)
7357 vty_frame(vty
, "ipv6 multicast");
7358 else if (safi
== SAFI_MPLS_VPN
)
7359 vty_frame(vty
, "ipv6 vpn");
7360 else if (safi
== SAFI_ENCAP
)
7361 vty_frame(vty
, "ipv6 encap");
7362 else if (safi
== SAFI_FLOWSPEC
)
7363 vty_frame(vty
, "ipv6 flowspec");
7364 } else if (afi
== AFI_L2VPN
) {
7365 if (safi
== SAFI_EVPN
)
7366 vty_frame(vty
, "l2vpn evpn");
7368 vty_frame(vty
, "\n");
7370 bgp_config_write_distance(vty
, bgp
, afi
, safi
);
7372 bgp_config_write_network(vty
, bgp
, afi
, safi
);
7374 bgp_config_write_redistribute(vty
, bgp
, afi
, safi
);
7376 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
))
7377 bgp_config_write_peer_af(vty
, bgp
, group
->conf
, afi
, safi
);
7379 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
7380 /* Skip dynamic neighbors. */
7381 if (peer_dynamic_neighbor(peer
))
7384 /* Do not display doppelganger peers */
7385 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
))
7386 bgp_config_write_peer_af(vty
, bgp
, peer
, afi
, safi
);
7389 bgp_config_write_maxpaths(vty
, bgp
, afi
, safi
);
7390 bgp_config_write_table_map(vty
, bgp
, afi
, safi
);
7392 if (safi
== SAFI_EVPN
)
7393 bgp_config_write_evpn_info(vty
, bgp
, afi
, safi
);
7395 if (safi
== SAFI_FLOWSPEC
)
7396 bgp_fs_config_write_pbr(vty
, bgp
, afi
, safi
);
7398 if (safi
== SAFI_UNICAST
) {
7399 bgp_vpn_policy_config_write_afi(vty
, bgp
, afi
);
7400 if (CHECK_FLAG(bgp
->af_flags
[afi
][safi
],
7401 BGP_CONFIG_VRF_TO_MPLSVPN_EXPORT
)) {
7403 vty_out(vty
, " export vpn\n");
7405 if (CHECK_FLAG(bgp
->af_flags
[afi
][safi
],
7406 BGP_CONFIG_MPLSVPN_TO_VRF_IMPORT
)) {
7408 vty_out(vty
, " import vpn\n");
7410 if (CHECK_FLAG(bgp
->af_flags
[afi
][safi
],
7411 BGP_CONFIG_VRF_TO_VRF_IMPORT
)) {
7414 for (ALL_LIST_ELEMENTS_RO(
7415 bgp
->vpn_policy
[afi
].import_vrf
, node
,
7417 vty_out(vty
, " import vrf %s\n", name
);
7421 vty_endframe(vty
, " exit-address-family\n");
7424 /* clang-format off */
7425 #if CONFDATE > 20190517
7426 CPP_NOTICE("bgpd: remove 'bgp enforce-first-as' config migration from bgp_config_write")
7428 /* clang-format on */
7430 int bgp_config_write(struct vty
*vty
)
7434 struct peer_group
*group
;
7436 struct listnode
*node
, *nnode
;
7437 struct listnode
*mnode
, *mnnode
;
7439 /* BGP Multiple instance. */
7440 if (!bgp_option_check(BGP_OPT_MULTIPLE_INSTANCE
)) {
7441 vty_out(vty
, "no bgp multiple-instance\n");
7445 /* BGP Config type. */
7446 if (bgp_option_check(BGP_OPT_CONFIG_CISCO
)) {
7447 vty_out(vty
, "bgp config-type cisco\n");
7451 if (bm
->rmap_update_timer
!= RMAP_DEFAULT_UPDATE_TIMER
)
7452 vty_out(vty
, "bgp route-map delay-timer %u\n",
7453 bm
->rmap_update_timer
);
7456 vty_out(vty
, "!\n");
7458 /* BGP configuration. */
7459 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
)) {
7461 /* skip all auto created vrf as they dont have user config */
7462 if (CHECK_FLAG(bgp
->vrf_flags
, BGP_VRF_AUTO
))
7465 /* Migrate deprecated 'bgp enforce-first-as'
7466 * config to 'neighbor * enforce-first-as' configs
7468 if (bgp_flag_check(bgp
, BGP_FLAG_ENFORCE_FIRST_AS
)) {
7469 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
7470 peer_flag_set(peer
, PEER_FLAG_ENFORCE_FIRST_AS
);
7471 bgp_flag_unset(bgp
, BGP_FLAG_ENFORCE_FIRST_AS
);
7474 /* Router bgp ASN */
7475 vty_out(vty
, "router bgp %u", bgp
->as
);
7477 if (bgp_option_check(BGP_OPT_MULTIPLE_INSTANCE
)) {
7479 vty_out(vty
, " %s %s",
7481 == BGP_INSTANCE_TYPE_VIEW
)
7488 /* No Synchronization */
7489 if (bgp_option_check(BGP_OPT_CONFIG_CISCO
))
7490 vty_out(vty
, " no synchronization\n");
7492 /* BGP fast-external-failover. */
7493 if (CHECK_FLAG(bgp
->flags
, BGP_FLAG_NO_FAST_EXT_FAILOVER
))
7494 vty_out(vty
, " no bgp fast-external-failover\n");
7496 /* BGP router ID. */
7497 if (bgp
->router_id_static
.s_addr
!= 0)
7498 vty_out(vty
, " bgp router-id %s\n",
7499 inet_ntoa(bgp
->router_id_static
));
7501 /* BGP log-neighbor-changes. */
7502 if (!!bgp_flag_check(bgp
, BGP_FLAG_LOG_NEIGHBOR_CHANGES
)
7503 != DFLT_BGP_LOG_NEIGHBOR_CHANGES
)
7504 vty_out(vty
, " %sbgp log-neighbor-changes\n",
7506 BGP_FLAG_LOG_NEIGHBOR_CHANGES
)
7510 /* BGP configuration. */
7511 if (bgp_flag_check(bgp
, BGP_FLAG_ALWAYS_COMPARE_MED
))
7512 vty_out(vty
, " bgp always-compare-med\n");
7514 /* BGP default ipv4-unicast. */
7515 if (bgp_flag_check(bgp
, BGP_FLAG_NO_DEFAULT_IPV4
))
7516 vty_out(vty
, " no bgp default ipv4-unicast\n");
7518 /* BGP default local-preference. */
7519 if (bgp
->default_local_pref
!= BGP_DEFAULT_LOCAL_PREF
)
7520 vty_out(vty
, " bgp default local-preference %u\n",
7521 bgp
->default_local_pref
);
7523 /* BGP default show-hostname */
7524 if (!!bgp_flag_check(bgp
, BGP_FLAG_SHOW_HOSTNAME
)
7525 != DFLT_BGP_SHOW_HOSTNAME
)
7526 vty_out(vty
, " %sbgp default show-hostname\n",
7527 bgp_flag_check(bgp
, BGP_FLAG_SHOW_HOSTNAME
)
7531 /* BGP default subgroup-pkt-queue-max. */
7532 if (bgp
->default_subgroup_pkt_queue_max
7533 != BGP_DEFAULT_SUBGROUP_PKT_QUEUE_MAX
)
7534 vty_out(vty
, " bgp default subgroup-pkt-queue-max %u\n",
7535 bgp
->default_subgroup_pkt_queue_max
);
7537 /* BGP client-to-client reflection. */
7538 if (bgp_flag_check(bgp
, BGP_FLAG_NO_CLIENT_TO_CLIENT
))
7539 vty_out(vty
, " no bgp client-to-client reflection\n");
7541 /* BGP cluster ID. */
7542 if (CHECK_FLAG(bgp
->config
, BGP_CONFIG_CLUSTER_ID
))
7543 vty_out(vty
, " bgp cluster-id %s\n",
7544 inet_ntoa(bgp
->cluster_id
));
7546 /* Disable ebgp connected nexthop check */
7547 if (bgp_flag_check(bgp
, BGP_FLAG_DISABLE_NH_CONNECTED_CHK
))
7549 " bgp disable-ebgp-connected-route-check\n");
7551 /* Confederation identifier*/
7552 if (CHECK_FLAG(bgp
->config
, BGP_CONFIG_CONFEDERATION
))
7553 vty_out(vty
, " bgp confederation identifier %i\n",
7556 /* Confederation peer */
7557 if (bgp
->confed_peers_cnt
> 0) {
7560 vty_out(vty
, " bgp confederation peers");
7562 for (i
= 0; i
< bgp
->confed_peers_cnt
; i
++)
7563 vty_out(vty
, " %u", bgp
->confed_peers
[i
]);
7568 /* BGP deterministic-med. */
7569 if (!!bgp_flag_check(bgp
, BGP_FLAG_DETERMINISTIC_MED
)
7570 != DFLT_BGP_DETERMINISTIC_MED
)
7571 vty_out(vty
, " %sbgp deterministic-med\n",
7572 bgp_flag_check(bgp
, BGP_FLAG_DETERMINISTIC_MED
)
7576 /* BGP update-delay. */
7577 bgp_config_write_update_delay(vty
, bgp
);
7579 if (bgp
->v_maxmed_onstartup
7580 != BGP_MAXMED_ONSTARTUP_UNCONFIGURED
) {
7581 vty_out(vty
, " bgp max-med on-startup %u",
7582 bgp
->v_maxmed_onstartup
);
7583 if (bgp
->maxmed_onstartup_value
7584 != BGP_MAXMED_VALUE_DEFAULT
)
7586 bgp
->maxmed_onstartup_value
);
7589 if (bgp
->v_maxmed_admin
!= BGP_MAXMED_ADMIN_UNCONFIGURED
) {
7590 vty_out(vty
, " bgp max-med administrative");
7591 if (bgp
->maxmed_admin_value
!= BGP_MAXMED_VALUE_DEFAULT
)
7592 vty_out(vty
, " %u", bgp
->maxmed_admin_value
);
7597 bgp_config_write_wpkt_quanta(vty
, bgp
);
7599 bgp_config_write_rpkt_quanta(vty
, bgp
);
7602 bgp_config_write_coalesce_time(vty
, bgp
);
7604 /* BGP graceful-restart. */
7605 if (bgp
->stalepath_time
!= BGP_DEFAULT_STALEPATH_TIME
)
7607 " bgp graceful-restart stalepath-time %u\n",
7608 bgp
->stalepath_time
);
7609 if (bgp
->restart_time
!= BGP_DEFAULT_RESTART_TIME
)
7610 vty_out(vty
, " bgp graceful-restart restart-time %u\n",
7612 if (bgp_flag_check(bgp
, BGP_FLAG_GRACEFUL_RESTART
))
7613 vty_out(vty
, " bgp graceful-restart\n");
7615 /* BGP graceful-shutdown */
7616 if (bgp_flag_check(bgp
, BGP_FLAG_GRACEFUL_SHUTDOWN
))
7617 vty_out(vty
, " bgp graceful-shutdown\n");
7619 /* BGP graceful-restart Preserve State F bit. */
7620 if (bgp_flag_check(bgp
, BGP_FLAG_GR_PRESERVE_FWD
))
7622 " bgp graceful-restart preserve-fw-state\n");
7624 /* BGP bestpath method. */
7625 if (bgp_flag_check(bgp
, BGP_FLAG_ASPATH_IGNORE
))
7626 vty_out(vty
, " bgp bestpath as-path ignore\n");
7627 if (bgp_flag_check(bgp
, BGP_FLAG_ASPATH_CONFED
))
7628 vty_out(vty
, " bgp bestpath as-path confed\n");
7630 if (bgp_flag_check(bgp
, BGP_FLAG_ASPATH_MULTIPATH_RELAX
)) {
7631 if (bgp_flag_check(bgp
,
7632 BGP_FLAG_MULTIPATH_RELAX_AS_SET
)) {
7634 " bgp bestpath as-path multipath-relax as-set\n");
7637 " bgp bestpath as-path multipath-relax\n");
7641 if (bgp_flag_check(bgp
, BGP_FLAG_RR_ALLOW_OUTBOUND_POLICY
)) {
7643 " bgp route-reflector allow-outbound-policy\n");
7645 if (bgp_flag_check(bgp
, BGP_FLAG_COMPARE_ROUTER_ID
))
7646 vty_out(vty
, " bgp bestpath compare-routerid\n");
7647 if (bgp_flag_check(bgp
, BGP_FLAG_MED_CONFED
)
7648 || bgp_flag_check(bgp
, BGP_FLAG_MED_MISSING_AS_WORST
)) {
7649 vty_out(vty
, " bgp bestpath med");
7650 if (bgp_flag_check(bgp
, BGP_FLAG_MED_CONFED
))
7651 vty_out(vty
, " confed");
7652 if (bgp_flag_check(bgp
, BGP_FLAG_MED_MISSING_AS_WORST
))
7653 vty_out(vty
, " missing-as-worst");
7657 /* BGP network import check. */
7658 if (!!bgp_flag_check(bgp
, BGP_FLAG_IMPORT_CHECK
)
7659 != DFLT_BGP_IMPORT_CHECK
)
7660 vty_out(vty
, " %sbgp network import-check\n",
7661 bgp_flag_check(bgp
, BGP_FLAG_IMPORT_CHECK
)
7665 /* BGP flag dampening. */
7666 if (CHECK_FLAG(bgp
->af_flags
[AFI_IP
][SAFI_UNICAST
],
7667 BGP_CONFIG_DAMPENING
))
7668 bgp_config_write_damp(vty
);
7670 /* BGP timers configuration. */
7671 if (bgp
->default_keepalive
!= BGP_DEFAULT_KEEPALIVE
7672 && bgp
->default_holdtime
!= BGP_DEFAULT_HOLDTIME
)
7673 vty_out(vty
, " timers bgp %u %u\n",
7674 bgp
->default_keepalive
, bgp
->default_holdtime
);
7677 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
7678 bgp_config_write_peer_global(vty
, bgp
, group
->conf
);
7681 /* Normal neighbor configuration. */
7682 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
7683 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
))
7684 bgp_config_write_peer_global(vty
, bgp
, peer
);
7687 /* listen range and limit for dynamic BGP neighbors */
7688 bgp_config_write_listen(vty
, bgp
);
7691 * BGP default autoshutdown neighbors
7693 * This must be placed after any peer and peer-group
7694 * configuration, to avoid setting all peers to shutdown after
7695 * a daemon restart, which is undesired behavior. (see #2286)
7697 if (bgp
->autoshutdown
)
7698 vty_out(vty
, " bgp default shutdown\n");
7700 /* No auto-summary */
7701 if (bgp_option_check(BGP_OPT_CONFIG_CISCO
))
7702 vty_out(vty
, " no auto-summary\n");
7704 /* IPv4 unicast configuration. */
7705 bgp_config_write_family(vty
, bgp
, AFI_IP
, SAFI_UNICAST
);
7707 /* IPv4 multicast configuration. */
7708 bgp_config_write_family(vty
, bgp
, AFI_IP
, SAFI_MULTICAST
);
7710 /* IPv4 labeled-unicast configuration. */
7711 bgp_config_write_family(vty
, bgp
, AFI_IP
, SAFI_LABELED_UNICAST
);
7713 /* IPv4 VPN configuration. */
7714 bgp_config_write_family(vty
, bgp
, AFI_IP
, SAFI_MPLS_VPN
);
7716 /* ENCAPv4 configuration. */
7717 bgp_config_write_family(vty
, bgp
, AFI_IP
, SAFI_ENCAP
);
7719 /* FLOWSPEC v4 configuration. */
7720 bgp_config_write_family(vty
, bgp
, AFI_IP
, SAFI_FLOWSPEC
);
7722 /* IPv6 unicast configuration. */
7723 bgp_config_write_family(vty
, bgp
, AFI_IP6
, SAFI_UNICAST
);
7725 /* IPv6 multicast configuration. */
7726 bgp_config_write_family(vty
, bgp
, AFI_IP6
, SAFI_MULTICAST
);
7728 /* IPv6 labeled-unicast configuration. */
7729 bgp_config_write_family(vty
, bgp
, AFI_IP6
,
7730 SAFI_LABELED_UNICAST
);
7732 /* IPv6 VPN configuration. */
7733 bgp_config_write_family(vty
, bgp
, AFI_IP6
, SAFI_MPLS_VPN
);
7735 /* ENCAPv6 configuration. */
7736 bgp_config_write_family(vty
, bgp
, AFI_IP6
, SAFI_ENCAP
);
7738 /* FLOWSPEC v6 configuration. */
7739 bgp_config_write_family(vty
, bgp
, AFI_IP6
, SAFI_FLOWSPEC
);
7741 /* EVPN configuration. */
7742 bgp_config_write_family(vty
, bgp
, AFI_L2VPN
, SAFI_EVPN
);
7745 bgp_rfapi_cfg_write(vty
, bgp
);
7748 vty_out(vty
, "!\n");
7753 void bgp_master_init(struct thread_master
*master
)
7757 memset(&bgp_master
, 0, sizeof(struct bgp_master
));
7760 bm
->bgp
= list_new();
7761 bm
->listen_sockets
= list_new();
7762 bm
->port
= BGP_PORT_DEFAULT
;
7763 bm
->master
= master
;
7764 bm
->start_time
= bgp_clock();
7765 bm
->t_rmap_update
= NULL
;
7766 bm
->rmap_update_timer
= RMAP_DEFAULT_UPDATE_TIMER
;
7767 bm
->terminating
= false;
7769 bgp_process_queue_init();
7771 /* init the rd id space.
7772 assign 0th index in the bitfield,
7773 so that we start with id 1
7775 bf_init(bm
->rd_idspace
, UINT16_MAX
);
7776 bf_assign_zero_index(bm
->rd_idspace
);
7778 /* Enable multiple instances by default. */
7779 bgp_option_set(BGP_OPT_MULTIPLE_INSTANCE
);
7781 /* mpls label dynamic allocation pool */
7782 bgp_lp_init(bm
->master
, &bm
->labelpool
);
7784 QOBJ_REG(bm
, bgp_master
);
7788 * Free up connected routes and interfaces for a BGP instance. Invoked upon
7789 * instance delete (non-default only) or BGP exit.
7791 static void bgp_if_finish(struct bgp
*bgp
)
7793 struct vrf
*vrf
= vrf_lookup_by_id(bgp
->vrf_id
);
7794 struct interface
*ifp
;
7796 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_VIEW
|| !vrf
)
7799 FOR_ALL_INTERFACES (vrf
, ifp
) {
7800 struct listnode
*c_node
, *c_nnode
;
7801 struct connected
*c
;
7803 for (ALL_LIST_ELEMENTS(ifp
->connected
, c_node
, c_nnode
, c
))
7804 bgp_connected_delete(bgp
, c
);
7808 static void bgp_viewvrf_autocomplete(vector comps
, struct cmd_token
*token
)
7810 struct vrf
*vrf
= NULL
;
7811 struct listnode
*next
;
7814 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
)
7815 vector_set(comps
, XSTRDUP(MTYPE_COMPLETION
, vrf
->name
));
7817 for (ALL_LIST_ELEMENTS_RO(bm
->bgp
, next
, bgp
)) {
7818 if (bgp
->inst_type
!= BGP_INSTANCE_TYPE_VIEW
)
7821 vector_set(comps
, XSTRDUP(MTYPE_COMPLETION
, bgp
->name
));
7825 static const struct cmd_variable_handler bgp_viewvrf_var_handlers
[] = {
7826 {.tokenname
= "VIEWVRFNAME", .completions
= bgp_viewvrf_autocomplete
},
7827 {.completions
= NULL
},
7830 struct frr_pthread
*bgp_pth_io
;
7831 struct frr_pthread
*bgp_pth_ka
;
7833 static void bgp_pthreads_init()
7835 assert(!bgp_pth_io
);
7836 assert(!bgp_pth_ka
);
7840 struct frr_pthread_attr io
= {
7841 .start
= frr_pthread_attr_default
.start
,
7842 .stop
= frr_pthread_attr_default
.stop
,
7844 struct frr_pthread_attr ka
= {
7845 .start
= bgp_keepalives_start
,
7846 .stop
= bgp_keepalives_stop
,
7848 bgp_pth_io
= frr_pthread_new(&io
, "BGP I/O thread", "bgpd_io");
7849 bgp_pth_ka
= frr_pthread_new(&ka
, "BGP Keepalives thread", "bgpd_ka");
7852 void bgp_pthreads_run()
7854 frr_pthread_run(bgp_pth_io
, NULL
);
7855 frr_pthread_run(bgp_pth_ka
, NULL
);
7857 /* Wait until threads are ready. */
7858 frr_pthread_wait_running(bgp_pth_io
);
7859 frr_pthread_wait_running(bgp_pth_ka
);
7862 void bgp_pthreads_finish()
7864 frr_pthread_stop_all();
7865 frr_pthread_finish();
7868 void bgp_init(unsigned short instance
)
7871 /* allocates some vital data structures used by peer commands in
7874 /* pre-init pthreads */
7875 bgp_pthreads_init();
7878 bgp_zebra_init(bm
->master
, instance
);
7881 vnc_zebra_init(bm
->master
);
7884 /* BGP VTY commands installation. */
7892 bgp_route_map_init();
7893 bgp_scan_vty_init();
7898 bgp_ethernetvpn_init();
7899 bgp_flowspec_vty_init();
7901 /* Access list initialize. */
7903 access_list_add_hook(peer_distribute_update
);
7904 access_list_delete_hook(peer_distribute_update
);
7906 /* Filter list initialize. */
7908 as_list_add_hook(peer_aslist_add
);
7909 as_list_delete_hook(peer_aslist_del
);
7911 /* Prefix list initialize.*/
7913 prefix_list_add_hook(peer_prefix_list_update
);
7914 prefix_list_delete_hook(peer_prefix_list_update
);
7916 /* Community list initialize. */
7917 bgp_clist
= community_list_init();
7922 cmd_variable_handler_register(bgp_viewvrf_var_handlers
);
7925 void bgp_terminate(void)
7929 struct listnode
*node
, *nnode
;
7930 struct listnode
*mnode
, *mnnode
;
7934 /* Close the listener sockets first as this prevents peers from
7936 * to reconnect on receiving the peer unconfig message. In the presence
7937 * of a large number of peers this will ensure that no peer is left with
7938 * a dangling connection
7940 /* reverse bgp_master_init */
7943 if (bm
->listen_sockets
)
7944 list_delete(&bm
->listen_sockets
);
7946 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
))
7947 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
7948 if (peer
->status
== Established
7949 || peer
->status
== OpenSent
7950 || peer
->status
== OpenConfirm
)
7951 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
7952 BGP_NOTIFY_CEASE_PEER_UNCONFIG
);
7954 if (bm
->process_main_queue
)
7955 work_queue_free_and_null(&bm
->process_main_queue
);
7957 if (bm
->t_rmap_update
)
7958 BGP_TIMER_OFF(bm
->t_rmap_update
);