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"
89 #include "bgpd/bgp_evpn_private.h"
90 #include "bgpd/bgp_mac.h"
92 DEFINE_MTYPE_STATIC(BGPD
, PEER_TX_SHUTDOWN_MSG
, "Peer shutdown message (TX)");
93 DEFINE_MTYPE_STATIC(BGPD
, BGP_EVPN_INFO
, "BGP EVPN instance information");
94 DEFINE_QOBJ_TYPE(bgp_master
)
96 DEFINE_QOBJ_TYPE(peer
)
97 DEFINE_HOOK(bgp_inst_delete
, (struct bgp
*bgp
), (bgp
))
99 /* BGP process wide configuration. */
100 static struct bgp_master bgp_master
;
102 /* BGP process wide configuration pointer to export. */
103 struct bgp_master
*bm
;
105 /* BGP community-list. */
106 struct community_list_handler
*bgp_clist
;
108 unsigned int multipath_num
= MULTIPATH_NUM
;
110 static void bgp_if_finish(struct bgp
*bgp
);
111 static void peer_drop_dynamic_neighbor(struct peer
*peer
);
113 extern struct zclient
*zclient
;
115 /* handle main socket creation or deletion */
116 static int bgp_check_main_socket(bool create
, struct bgp
*bgp
)
118 static int bgp_server_main_created
;
121 if (bgp_server_main_created
)
123 if (bgp_socket(bgp
, bm
->port
, bm
->address
) < 0)
124 return BGP_ERR_INVALID_VALUE
;
125 bgp_server_main_created
= 1;
128 if (!bgp_server_main_created
)
131 bgp_server_main_created
= 0;
135 void bgp_session_reset(struct peer
*peer
)
137 if (peer
->doppelganger
&& (peer
->doppelganger
->status
!= Deleted
)
138 && !(CHECK_FLAG(peer
->doppelganger
->flags
, PEER_FLAG_CONFIG_NODE
)))
139 peer_delete(peer
->doppelganger
);
141 BGP_EVENT_ADD(peer
, BGP_Stop
);
145 * During session reset, we may delete the doppelganger peer, which would
146 * be the next node to the current node. If the session reset was invoked
147 * during walk of peer list, we would end up accessing the freed next
148 * node. This function moves the next node along.
150 static void bgp_session_reset_safe(struct peer
*peer
, struct listnode
**nnode
)
155 n
= (nnode
) ? *nnode
: NULL
;
156 npeer
= (n
) ? listgetdata(n
) : NULL
;
158 if (peer
->doppelganger
&& (peer
->doppelganger
->status
!= Deleted
)
159 && !(CHECK_FLAG(peer
->doppelganger
->flags
,
160 PEER_FLAG_CONFIG_NODE
))) {
161 if (peer
->doppelganger
== npeer
)
162 /* nnode and *nnode are confirmed to be non-NULL here */
163 *nnode
= (*nnode
)->next
;
164 peer_delete(peer
->doppelganger
);
167 BGP_EVENT_ADD(peer
, BGP_Stop
);
170 /* BGP global flag manipulation. */
171 int bgp_option_set(int flag
)
175 case BGP_OPT_NO_LISTEN
:
176 case BGP_OPT_NO_ZEBRA
:
177 SET_FLAG(bm
->options
, flag
);
180 return BGP_ERR_INVALID_FLAG
;
185 int bgp_option_unset(int flag
)
189 case BGP_OPT_NO_ZEBRA
:
191 UNSET_FLAG(bm
->options
, flag
);
194 return BGP_ERR_INVALID_FLAG
;
199 int bgp_option_check(int flag
)
201 return CHECK_FLAG(bm
->options
, flag
);
204 /* Internal function to set BGP structure configureation flag. */
205 static void bgp_config_set(struct bgp
*bgp
, int config
)
207 SET_FLAG(bgp
->config
, config
);
210 static void bgp_config_unset(struct bgp
*bgp
, int config
)
212 UNSET_FLAG(bgp
->config
, config
);
215 static int bgp_config_check(struct bgp
*bgp
, int config
)
217 return CHECK_FLAG(bgp
->config
, config
);
220 /* Set BGP router identifier; distinguish between explicit config and other
223 static int bgp_router_id_set(struct bgp
*bgp
, const struct in_addr
*id
,
227 struct listnode
*node
, *nnode
;
229 if (IPV4_ADDR_SAME(&bgp
->router_id
, id
))
232 /* EVPN uses router id in RD, withdraw them */
233 if (is_evpn_enabled())
234 bgp_evpn_handle_router_id_update(bgp
, true);
236 vpn_handle_router_id_update(bgp
, true, is_config
);
238 IPV4_ADDR_COPY(&bgp
->router_id
, id
);
240 /* Set all peer's local identifier with this value. */
241 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
242 IPV4_ADDR_COPY(&peer
->local_id
, id
);
244 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
245 peer
->last_reset
= PEER_DOWN_RID_CHANGE
;
246 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
247 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
251 /* EVPN uses router id in RD, update them */
252 if (is_evpn_enabled())
253 bgp_evpn_handle_router_id_update(bgp
, false);
255 vpn_handle_router_id_update(bgp
, false, is_config
);
260 void bgp_router_id_zebra_bump(vrf_id_t vrf_id
, const struct prefix
*router_id
)
262 struct listnode
*node
, *nnode
;
264 struct in_addr
*addr
= NULL
;
266 if (router_id
!= NULL
)
267 addr
= (struct in_addr
*)&(router_id
->u
.prefix4
);
269 if (vrf_id
== VRF_DEFAULT
) {
270 /* Router-id change for default VRF has to also update all
272 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
)) {
273 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
)
277 bgp
->router_id_zebra
= *addr
;
279 addr
= &bgp
->router_id_zebra
;
281 if (!bgp
->router_id_static
.s_addr
) {
282 /* Router ID is updated if there are no active
285 if (bgp
->established_peers
== 0) {
286 if (BGP_DEBUG(zebra
, ZEBRA
))
288 "RID change : vrf %s(%u), RTR ID %s",
292 bgp_router_id_set(bgp
, addr
, false);
297 bgp
= bgp_lookup_by_vrf_id(vrf_id
);
300 bgp
->router_id_zebra
= *addr
;
302 addr
= &bgp
->router_id_zebra
;
304 if (!bgp
->router_id_static
.s_addr
) {
305 /* Router ID is updated if there are no active
308 if (bgp
->established_peers
== 0) {
309 if (BGP_DEBUG(zebra
, ZEBRA
))
311 "RID change : vrf %s(%u), RTR ID %s",
315 bgp_router_id_set(bgp
, addr
, false);
323 void bgp_router_id_static_set(struct bgp
*bgp
, struct in_addr id
)
325 bgp
->router_id_static
= id
;
326 bgp_router_id_set(bgp
,
327 id
.s_addr
!= INADDR_ANY
? &id
: &bgp
->router_id_zebra
,
328 true /* is config */);
331 /* BGP's cluster-id control. */
332 int bgp_cluster_id_set(struct bgp
*bgp
, struct in_addr
*cluster_id
)
335 struct listnode
*node
, *nnode
;
337 if (bgp_config_check(bgp
, BGP_CONFIG_CLUSTER_ID
)
338 && IPV4_ADDR_SAME(&bgp
->cluster_id
, cluster_id
))
341 IPV4_ADDR_COPY(&bgp
->cluster_id
, cluster_id
);
342 bgp_config_set(bgp
, BGP_CONFIG_CLUSTER_ID
);
344 /* Clear all IBGP peer. */
345 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
346 if (peer
->sort
!= BGP_PEER_IBGP
)
349 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
350 peer
->last_reset
= PEER_DOWN_CLID_CHANGE
;
351 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
352 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
358 int bgp_cluster_id_unset(struct bgp
*bgp
)
361 struct listnode
*node
, *nnode
;
363 if (!bgp_config_check(bgp
, BGP_CONFIG_CLUSTER_ID
))
366 bgp
->cluster_id
.s_addr
= 0;
367 bgp_config_unset(bgp
, BGP_CONFIG_CLUSTER_ID
);
369 /* Clear all IBGP peer. */
370 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
371 if (peer
->sort
!= BGP_PEER_IBGP
)
374 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
375 peer
->last_reset
= PEER_DOWN_CLID_CHANGE
;
376 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
377 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
383 /* time_t value that is monotonicly increasing
384 * and uneffected by adjustments to system clock
386 time_t bgp_clock(void)
394 /* BGP timer configuration. */
395 void bgp_timers_set(struct bgp
*bgp
, uint32_t keepalive
, uint32_t holdtime
,
396 uint32_t connect_retry
)
398 bgp
->default_keepalive
=
399 (keepalive
< holdtime
/ 3 ? keepalive
: holdtime
/ 3);
400 bgp
->default_holdtime
= holdtime
;
401 bgp
->default_connect_retry
= connect_retry
;
404 /* mostly for completeness - CLI uses its own defaults */
405 void bgp_timers_unset(struct bgp
*bgp
)
407 bgp
->default_keepalive
= BGP_DEFAULT_KEEPALIVE
;
408 bgp
->default_holdtime
= BGP_DEFAULT_HOLDTIME
;
409 bgp
->default_connect_retry
= BGP_DEFAULT_CONNECT_RETRY
;
412 /* BGP confederation configuration. */
413 int bgp_confederation_id_set(struct bgp
*bgp
, as_t as
)
416 struct listnode
*node
, *nnode
;
420 return BGP_ERR_INVALID_AS
;
422 /* Remember - were we doing confederation before? */
423 already_confed
= bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
);
425 bgp_config_set(bgp
, BGP_CONFIG_CONFEDERATION
);
427 /* If we were doing confederation already, this is just an external
428 AS change. Just Reset EBGP sessions, not CONFED sessions. If we
429 were not doing confederation before, reset all EBGP sessions. */
430 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
431 bgp_peer_sort_t ptype
= peer_sort(peer
);
433 /* We're looking for peers who's AS is not local or part of our
435 if (already_confed
) {
436 if (ptype
== BGP_PEER_EBGP
) {
438 if (BGP_IS_VALID_STATE_FOR_NOTIF(
441 PEER_DOWN_CONFED_ID_CHANGE
;
443 peer
, BGP_NOTIFY_CEASE
,
444 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
446 bgp_session_reset_safe(peer
, &nnode
);
449 /* Not doign confederation before, so reset every
452 if (ptype
!= BGP_PEER_IBGP
) {
453 /* Reset the local_as to be our EBGP one */
454 if (ptype
== BGP_PEER_EBGP
)
456 if (BGP_IS_VALID_STATE_FOR_NOTIF(
459 PEER_DOWN_CONFED_ID_CHANGE
;
461 peer
, BGP_NOTIFY_CEASE
,
462 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
464 bgp_session_reset_safe(peer
, &nnode
);
471 int bgp_confederation_id_unset(struct bgp
*bgp
)
474 struct listnode
*node
, *nnode
;
477 bgp_config_unset(bgp
, BGP_CONFIG_CONFEDERATION
);
479 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
480 /* We're looking for peers who's AS is not local */
481 if (peer_sort(peer
) != BGP_PEER_IBGP
) {
482 peer
->local_as
= bgp
->as
;
483 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
484 peer
->last_reset
= PEER_DOWN_CONFED_ID_CHANGE
;
485 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
486 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
490 bgp_session_reset_safe(peer
, &nnode
);
496 /* Is an AS part of the confed or not? */
497 bool bgp_confederation_peers_check(struct bgp
*bgp
, as_t as
)
504 for (i
= 0; i
< bgp
->confed_peers_cnt
; i
++)
505 if (bgp
->confed_peers
[i
] == as
)
511 /* Add an AS to the confederation set. */
512 int bgp_confederation_peers_add(struct bgp
*bgp
, as_t as
)
515 struct listnode
*node
, *nnode
;
518 return BGP_ERR_INVALID_BGP
;
521 return BGP_ERR_INVALID_AS
;
523 if (bgp_confederation_peers_check(bgp
, as
))
526 if (bgp
->confed_peers
)
528 XREALLOC(MTYPE_BGP_CONFED_LIST
, bgp
->confed_peers
,
529 (bgp
->confed_peers_cnt
+ 1) * sizeof(as_t
));
532 XMALLOC(MTYPE_BGP_CONFED_LIST
,
533 (bgp
->confed_peers_cnt
+ 1) * sizeof(as_t
));
535 bgp
->confed_peers
[bgp
->confed_peers_cnt
] = as
;
536 bgp
->confed_peers_cnt
++;
538 if (bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
)) {
539 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
540 if (peer
->as
== as
) {
541 peer
->local_as
= bgp
->as
;
542 if (BGP_IS_VALID_STATE_FOR_NOTIF(
545 PEER_DOWN_CONFED_PEER_CHANGE
;
547 peer
, BGP_NOTIFY_CEASE
,
548 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
550 bgp_session_reset_safe(peer
, &nnode
);
557 /* Delete an AS from the confederation set. */
558 int bgp_confederation_peers_remove(struct bgp
*bgp
, as_t as
)
563 struct listnode
*node
, *nnode
;
568 if (!bgp_confederation_peers_check(bgp
, as
))
571 for (i
= 0; i
< bgp
->confed_peers_cnt
; i
++)
572 if (bgp
->confed_peers
[i
] == as
)
573 for (j
= i
+ 1; j
< bgp
->confed_peers_cnt
; j
++)
574 bgp
->confed_peers
[j
- 1] = bgp
->confed_peers
[j
];
576 bgp
->confed_peers_cnt
--;
578 if (bgp
->confed_peers_cnt
== 0) {
579 if (bgp
->confed_peers
)
580 XFREE(MTYPE_BGP_CONFED_LIST
, bgp
->confed_peers
);
581 bgp
->confed_peers
= NULL
;
584 XREALLOC(MTYPE_BGP_CONFED_LIST
, bgp
->confed_peers
,
585 bgp
->confed_peers_cnt
* sizeof(as_t
));
587 /* Now reset any peer who's remote AS has just been removed from the
589 if (bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
)) {
590 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
591 if (peer
->as
== as
) {
592 peer
->local_as
= bgp
->confed_id
;
593 if (BGP_IS_VALID_STATE_FOR_NOTIF(
596 PEER_DOWN_CONFED_PEER_CHANGE
;
598 peer
, BGP_NOTIFY_CEASE
,
599 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
601 bgp_session_reset_safe(peer
, &nnode
);
609 /* Local preference configuration. */
610 int bgp_default_local_preference_set(struct bgp
*bgp
, uint32_t local_pref
)
615 bgp
->default_local_pref
= local_pref
;
620 int bgp_default_local_preference_unset(struct bgp
*bgp
)
625 bgp
->default_local_pref
= BGP_DEFAULT_LOCAL_PREF
;
630 /* Local preference configuration. */
631 int bgp_default_subgroup_pkt_queue_max_set(struct bgp
*bgp
, uint32_t queue_size
)
636 bgp
->default_subgroup_pkt_queue_max
= queue_size
;
641 int bgp_default_subgroup_pkt_queue_max_unset(struct bgp
*bgp
)
645 bgp
->default_subgroup_pkt_queue_max
=
646 BGP_DEFAULT_SUBGROUP_PKT_QUEUE_MAX
;
651 /* Listen limit configuration. */
652 int bgp_listen_limit_set(struct bgp
*bgp
, int listen_limit
)
657 bgp
->dynamic_neighbors_limit
= listen_limit
;
662 int bgp_listen_limit_unset(struct bgp
*bgp
)
667 bgp
->dynamic_neighbors_limit
= BGP_DYNAMIC_NEIGHBORS_LIMIT_DEFAULT
;
672 int bgp_map_afi_safi_iana2int(iana_afi_t pkt_afi
, iana_safi_t pkt_safi
,
673 afi_t
*afi
, safi_t
*safi
)
675 /* Map from IANA values to internal values, return error if
676 * values are unrecognized.
678 *afi
= afi_iana2int(pkt_afi
);
679 *safi
= safi_iana2int(pkt_safi
);
680 if (*afi
== AFI_MAX
|| *safi
== SAFI_MAX
)
686 int bgp_map_afi_safi_int2iana(afi_t afi
, safi_t safi
, iana_afi_t
*pkt_afi
,
687 iana_safi_t
*pkt_safi
)
689 /* Map from internal values to IANA values, return error if
690 * internal values are bad (unexpected).
692 if (afi
== AFI_MAX
|| safi
== SAFI_MAX
)
694 *pkt_afi
= afi_int2iana(afi
);
695 *pkt_safi
= safi_int2iana(safi
);
699 struct peer_af
*peer_af_create(struct peer
*peer
, afi_t afi
, safi_t safi
)
708 afid
= afindex(afi
, safi
);
709 if (afid
>= BGP_AF_MAX
)
713 assert(peer
->peer_af_array
[afid
] == NULL
);
715 /* Allocate new peer af */
716 af
= XCALLOC(MTYPE_BGP_PEER_AF
, sizeof(struct peer_af
));
718 peer
->peer_af_array
[afid
] = af
;
723 bgp
->af_peer_count
[afi
][safi
]++;
728 struct peer_af
*peer_af_find(struct peer
*peer
, afi_t afi
, safi_t safi
)
735 afid
= afindex(afi
, safi
);
736 if (afid
>= BGP_AF_MAX
)
739 return peer
->peer_af_array
[afid
];
742 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
];
760 bgp_stop_announce_route_timer(af
);
762 if (PAF_SUBGRP(af
)) {
763 if (BGP_DEBUG(update_groups
, UPDATE_GROUPS
))
764 zlog_debug("u%" PRIu64
":s%" PRIu64
" remove peer %s",
765 af
->subgroup
->update_group
->id
,
766 af
->subgroup
->id
, peer
->host
);
770 update_subgroup_remove_peer(af
->subgroup
, af
);
772 if (bgp
->af_peer_count
[afi
][safi
])
773 bgp
->af_peer_count
[afi
][safi
]--;
775 peer
->peer_af_array
[afid
] = NULL
;
776 XFREE(MTYPE_BGP_PEER_AF
, af
);
780 /* Peer comparison function for sorting. */
781 int peer_cmp(struct peer
*p1
, struct peer
*p2
)
783 if (p1
->group
&& !p2
->group
)
786 if (!p1
->group
&& p2
->group
)
789 if (p1
->group
== p2
->group
) {
790 if (p1
->conf_if
&& !p2
->conf_if
)
793 if (!p1
->conf_if
&& p2
->conf_if
)
796 if (p1
->conf_if
&& p2
->conf_if
)
797 return if_cmp_name_func(p1
->conf_if
, p2
->conf_if
);
799 return strcmp(p1
->group
->name
, p2
->group
->name
);
801 return sockunion_cmp(&p1
->su
, &p2
->su
);
804 static unsigned int peer_hash_key_make(const void *p
)
806 const struct peer
*peer
= p
;
807 return sockunion_hash(&peer
->su
);
810 static bool peer_hash_same(const void *p1
, const void *p2
)
812 const struct peer
*peer1
= p1
;
813 const struct peer
*peer2
= p2
;
814 return (sockunion_same(&peer1
->su
, &peer2
->su
)
815 && CHECK_FLAG(peer1
->flags
, PEER_FLAG_CONFIG_NODE
)
816 == CHECK_FLAG(peer2
->flags
, PEER_FLAG_CONFIG_NODE
));
819 void peer_flag_inherit(struct peer
*peer
, uint32_t flag
)
823 /* Skip if peer is not a peer-group member. */
824 if (!peer_group_active(peer
))
827 /* Unset override flag to signal inheritance from peer-group. */
828 UNSET_FLAG(peer
->flags_override
, flag
);
831 * Inherit flag state from peer-group. If the flag of the peer-group is
832 * not being inverted, the peer must inherit the inverse of the current
833 * peer-group flag state.
835 group_val
= CHECK_FLAG(peer
->group
->conf
->flags
, flag
);
836 if (!CHECK_FLAG(peer
->group
->conf
->flags_invert
, flag
)
837 && CHECK_FLAG(peer
->flags_invert
, flag
))
838 COND_FLAG(peer
->flags
, flag
, !group_val
);
840 COND_FLAG(peer
->flags
, flag
, group_val
);
843 int peer_af_flag_check(struct peer
*peer
, afi_t afi
, safi_t safi
, uint32_t flag
)
845 return CHECK_FLAG(peer
->af_flags
[afi
][safi
], flag
);
848 void peer_af_flag_inherit(struct peer
*peer
, afi_t afi
, safi_t safi
,
853 /* Skip if peer is not a peer-group member. */
854 if (!peer_group_active(peer
))
857 /* Unset override flag to signal inheritance from peer-group. */
858 UNSET_FLAG(peer
->af_flags_override
[afi
][safi
], flag
);
861 * Inherit flag state from peer-group. If the flag of the peer-group is
862 * not being inverted, the peer must inherit the inverse of the current
863 * peer-group flag state.
865 group_val
= CHECK_FLAG(peer
->group
->conf
->af_flags
[afi
][safi
], flag
);
866 if (!CHECK_FLAG(peer
->group
->conf
->af_flags_invert
[afi
][safi
], flag
)
867 && CHECK_FLAG(peer
->af_flags_invert
[afi
][safi
], flag
))
868 COND_FLAG(peer
->af_flags
[afi
][safi
], flag
, !group_val
);
870 COND_FLAG(peer
->af_flags
[afi
][safi
], flag
, group_val
);
873 /* Check peer's AS number and determines if this peer is IBGP or EBGP */
874 static inline bgp_peer_sort_t
peer_calc_sort(struct peer
*peer
)
881 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
882 if (peer
->as_type
== AS_INTERNAL
)
883 return BGP_PEER_IBGP
;
885 else if (peer
->as_type
== AS_EXTERNAL
)
886 return BGP_PEER_EBGP
;
888 else if (peer
->as_type
== AS_SPECIFIED
&& peer
->as
) {
890 return (bgp
->as
== peer
->as
? BGP_PEER_IBGP
898 peer1
= listnode_head(peer
->group
->peer
);
903 return BGP_PEER_INTERNAL
;
907 if (bgp
&& CHECK_FLAG(bgp
->config
, BGP_CONFIG_CONFEDERATION
)) {
908 if (peer
->local_as
== 0)
909 return BGP_PEER_INTERNAL
;
911 if (peer
->local_as
== peer
->as
) {
912 if (bgp
->as
== bgp
->confed_id
) {
913 if (peer
->local_as
== bgp
->as
)
914 return BGP_PEER_IBGP
;
916 return BGP_PEER_EBGP
;
918 if (peer
->local_as
== bgp
->confed_id
)
919 return BGP_PEER_EBGP
;
921 return BGP_PEER_IBGP
;
925 if (bgp_confederation_peers_check(bgp
, peer
->as
))
926 return BGP_PEER_CONFED
;
928 return BGP_PEER_EBGP
;
930 if (peer
->as_type
== AS_UNSPECIFIED
) {
931 /* check if in peer-group with AS information */
933 && (peer
->group
->conf
->as_type
!= AS_UNSPECIFIED
)) {
934 if (peer
->group
->conf
->as_type
937 == peer
->group
->conf
->as
)
938 return BGP_PEER_IBGP
;
940 return BGP_PEER_EBGP
;
941 } else if (peer
->group
->conf
->as_type
943 return BGP_PEER_IBGP
;
945 return BGP_PEER_EBGP
;
947 /* no AS information anywhere, let caller know */
948 return BGP_PEER_UNSPECIFIED
;
949 } else if (peer
->as_type
!= AS_SPECIFIED
)
950 return (peer
->as_type
== AS_INTERNAL
? BGP_PEER_IBGP
953 return (peer
->local_as
== 0
955 : peer
->local_as
== peer
->as
? BGP_PEER_IBGP
960 /* Calculate and cache the peer "sort" */
961 bgp_peer_sort_t
peer_sort(struct peer
*peer
)
963 peer
->sort
= peer_calc_sort(peer
);
967 bgp_peer_sort_t
peer_sort_lookup(struct peer
*peer
)
972 static void peer_free(struct peer
*peer
)
977 assert(peer
->status
== Deleted
);
981 /* this /ought/ to have been done already through bgp_stop earlier,
982 * but just to be sure..
986 bgp_writes_off(peer
);
987 assert(!peer
->t_write
);
988 assert(!peer
->t_read
);
989 BGP_EVENT_FLUSH(peer
);
991 pthread_mutex_destroy(&peer
->io_mtx
);
993 /* Free connected nexthop, if present */
994 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
)
995 && !peer_dynamic_neighbor(peer
))
996 bgp_delete_connected_nexthop(family2afi(peer
->su
.sa
.sa_family
),
999 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG
, peer
->tx_shutdown_message
);
1001 XFREE(MTYPE_PEER_DESC
, peer
->desc
);
1002 XFREE(MTYPE_BGP_PEER_HOST
, peer
->host
);
1003 XFREE(MTYPE_BGP_PEER_HOST
, peer
->domainname
);
1004 XFREE(MTYPE_BGP_PEER_IFNAME
, peer
->ifname
);
1006 /* Update source configuration. */
1007 if (peer
->update_source
) {
1008 sockunion_free(peer
->update_source
);
1009 peer
->update_source
= NULL
;
1012 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
1014 XFREE(MTYPE_TMP
, peer
->notify
.data
);
1015 memset(&peer
->notify
, 0, sizeof(struct bgp_notify
));
1017 if (peer
->clear_node_queue
)
1018 work_queue_free_and_null(&peer
->clear_node_queue
);
1020 bgp_sync_delete(peer
);
1022 XFREE(MTYPE_PEER_CONF_IF
, peer
->conf_if
);
1024 bfd_info_free(&(peer
->bfd_info
));
1026 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
1027 for (safi
= SAFI_UNICAST
; safi
< SAFI_MAX
; safi
++) {
1028 bgp_addpath_set_peer_type(peer
, afi
, safi
,
1033 bgp_unlock(peer
->bgp
);
1035 memset(peer
, 0, sizeof(struct peer
));
1037 XFREE(MTYPE_BGP_PEER
, peer
);
1040 /* increase reference count on a struct peer */
1041 struct peer
*peer_lock_with_caller(const char *name
, struct peer
*peer
)
1043 assert(peer
&& (peer
->lock
>= 0));
1046 zlog_debug("%s peer_lock %p %d", name
, peer
, peer
->lock
);
1054 /* decrease reference count on a struct peer
1055 * struct peer is freed and NULL returned if last reference
1057 struct peer
*peer_unlock_with_caller(const char *name
, struct peer
*peer
)
1059 assert(peer
&& (peer
->lock
> 0));
1062 zlog_debug("%s peer_unlock %p %d", name
, peer
, peer
->lock
);
1067 if (peer
->lock
== 0) {
1074 /* BGP GR changes */
1076 int bgp_global_gr_init(struct bgp
*bgp
)
1078 if (BGP_DEBUG(graceful_restart
, GRACEFUL_RESTART
))
1079 zlog_debug("%s called ..", __func__
);
1081 int local_GLOBAL_GR_FSM
[BGP_GLOBAL_GR_MODE
][BGP_GLOBAL_GR_EVENT_CMD
] = {
1082 /* GLOBAL_HELPER Mode */
1085 /*GLOBAL_GR_cmd*/ /*no_Global_GR_cmd*/
1086 GLOBAL_GR
, GLOBAL_INVALID
,
1087 /*GLOBAL_DISABLE_cmd*/ /*no_Global_Disable_cmd*/
1088 GLOBAL_DISABLE
, GLOBAL_INVALID
1090 /* GLOBAL_GR Mode */
1093 /*GLOBAL_GR_cmd*/ /*no_Global_GR_cmd*/
1094 GLOBAL_INVALID
, GLOBAL_HELPER
,
1095 /*GLOBAL_DISABLE_cmd*/ /*no_Global_Disable_cmd*/
1096 GLOBAL_DISABLE
, GLOBAL_INVALID
1098 /* GLOBAL_DISABLE Mode */
1101 /*GLOBAL_GR_cmd */ /*no_Global_GR_cmd*/
1102 GLOBAL_GR
, GLOBAL_INVALID
,
1103 /*GLOBAL_DISABLE_cmd*//*no_Global_Disable_cmd*/
1104 GLOBAL_INVALID
, GLOBAL_HELPER
1106 /* GLOBAL_INVALID Mode */
1109 /*GLOBAL_GR_cmd*/ /*no_Global_GR_cmd*/
1110 GLOBAL_INVALID
, GLOBAL_INVALID
,
1111 /*GLOBAL_DISABLE_cmd*/ /*no_Global_Disable_cmd*/
1112 GLOBAL_INVALID
, GLOBAL_INVALID
1115 memcpy(bgp
->GLOBAL_GR_FSM
, local_GLOBAL_GR_FSM
,
1116 sizeof(local_GLOBAL_GR_FSM
));
1118 bgp
->global_gr_present_state
= GLOBAL_HELPER
;
1119 bgp
->present_zebra_gr_state
= ZEBRA_GR_DISABLE
;
1121 return BGP_GR_SUCCESS
;
1124 int bgp_peer_gr_init(struct peer
*peer
)
1126 if (BGP_DEBUG(graceful_restart
, GRACEFUL_RESTART
))
1127 zlog_debug("%s called ..", __func__
);
1129 struct bgp_peer_gr local_Peer_GR_FSM
[BGP_PEER_GR_MODE
]
1130 [BGP_PEER_GR_EVENT_CMD
] = {
1132 /* PEER_HELPER Mode */
1133 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1134 { PEER_GR
, bgp_peer_gr_action
}, {PEER_INVALID
, NULL
},
1135 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1136 {PEER_DISABLE
, bgp_peer_gr_action
}, {PEER_INVALID
, NULL
},
1137 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1138 { PEER_INVALID
, NULL
}, {PEER_GLOBAL_INHERIT
,
1139 bgp_peer_gr_action
}
1143 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1144 { PEER_INVALID
, NULL
}, { PEER_GLOBAL_INHERIT
,
1145 bgp_peer_gr_action
},
1146 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1147 {PEER_DISABLE
, bgp_peer_gr_action
}, { PEER_INVALID
, NULL
},
1148 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1149 { PEER_HELPER
, bgp_peer_gr_action
}, { PEER_INVALID
, NULL
}
1152 /* PEER_DISABLE Mode */
1153 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1154 { PEER_GR
, bgp_peer_gr_action
}, { PEER_INVALID
, NULL
},
1155 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1156 { PEER_INVALID
, NULL
}, { PEER_GLOBAL_INHERIT
,
1157 bgp_peer_gr_action
},
1158 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1159 { PEER_HELPER
, bgp_peer_gr_action
}, { PEER_INVALID
, NULL
}
1162 /* PEER_INVALID Mode */
1163 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1164 { PEER_INVALID
, NULL
}, { PEER_INVALID
, NULL
},
1165 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1166 { PEER_INVALID
, NULL
}, { PEER_INVALID
, NULL
},
1167 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1168 { PEER_INVALID
, NULL
}, { PEER_INVALID
, NULL
},
1171 /* PEER_GLOBAL_INHERIT Mode */
1172 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1173 { PEER_GR
, bgp_peer_gr_action
}, { PEER_INVALID
, NULL
},
1174 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1175 { PEER_DISABLE
, bgp_peer_gr_action
}, { PEER_INVALID
, NULL
},
1176 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1177 { PEER_HELPER
, bgp_peer_gr_action
}, { PEER_INVALID
, NULL
}
1180 memcpy(&peer
->PEER_GR_FSM
, local_Peer_GR_FSM
,
1181 sizeof(local_Peer_GR_FSM
));
1182 peer
->peer_gr_present_state
= PEER_GLOBAL_INHERIT
;
1183 bgp_peer_move_to_gr_mode(peer
, PEER_GLOBAL_INHERIT
);
1185 return BGP_GR_SUCCESS
;
1188 /* Allocate new peer object, implicitely locked. */
1189 struct peer
*peer_new(struct bgp
*bgp
)
1196 /* bgp argument is absolutely required */
1199 /* Allocate new peer. */
1200 peer
= XCALLOC(MTYPE_BGP_PEER
, sizeof(struct peer
));
1202 /* Set default value. */
1204 peer
->v_start
= BGP_INIT_START_TIMER
;
1205 peer
->v_connect
= bgp
->default_connect_retry
;
1206 peer
->status
= Idle
;
1207 peer
->ostatus
= Idle
;
1208 peer
->cur_event
= peer
->last_event
= peer
->last_major_event
= 0;
1209 peer
->bgp
= bgp_lock(bgp
);
1210 peer
= peer_lock(peer
); /* initial reference */
1211 peer
->password
= NULL
;
1213 /* Set default flags. */
1214 FOREACH_AFI_SAFI (afi
, safi
) {
1215 SET_FLAG(peer
->af_flags
[afi
][safi
], PEER_FLAG_SEND_COMMUNITY
);
1216 SET_FLAG(peer
->af_flags
[afi
][safi
],
1217 PEER_FLAG_SEND_EXT_COMMUNITY
);
1218 SET_FLAG(peer
->af_flags
[afi
][safi
],
1219 PEER_FLAG_SEND_LARGE_COMMUNITY
);
1221 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1222 PEER_FLAG_SEND_COMMUNITY
);
1223 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1224 PEER_FLAG_SEND_EXT_COMMUNITY
);
1225 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1226 PEER_FLAG_SEND_LARGE_COMMUNITY
);
1227 peer
->addpath_type
[afi
][safi
] = BGP_ADDPATH_NONE
;
1230 /* set nexthop-unchanged for l2vpn evpn by default */
1231 SET_FLAG(peer
->af_flags
[AFI_L2VPN
][SAFI_EVPN
],
1232 PEER_FLAG_NEXTHOP_UNCHANGED
);
1234 SET_FLAG(peer
->sflags
, PEER_STATUS_CAPABILITY_OPEN
);
1236 /* Initialize per peer bgp GR FSM */
1237 bgp_peer_gr_init(peer
);
1239 /* Create buffers. */
1240 peer
->ibuf
= stream_fifo_new();
1241 peer
->obuf
= stream_fifo_new();
1242 pthread_mutex_init(&peer
->io_mtx
, NULL
);
1244 /* We use a larger buffer for peer->obuf_work in the event that:
1245 * - We RX a BGP_UPDATE where the attributes alone are just
1246 * under BGP_MAX_PACKET_SIZE
1247 * - The user configures an outbound route-map that does many as-path
1248 * prepends or adds many communities. At most they can have
1249 * CMD_ARGC_MAX args in a route-map so there is a finite limit on how
1250 * large they can make the attributes.
1252 * Having a buffer with BGP_MAX_PACKET_SIZE_OVERFLOW allows us to avoid
1253 * bounds checking for every single attribute as we construct an
1257 stream_new(BGP_MAX_PACKET_SIZE
+ BGP_MAX_PACKET_SIZE_OVERFLOW
);
1259 ringbuf_new(BGP_MAX_PACKET_SIZE
* BGP_READ_PACKET_MAX
);
1261 peer
->scratch
= stream_new(BGP_MAX_PACKET_SIZE
);
1263 bgp_sync_init(peer
);
1265 /* Get service port number. */
1266 sp
= getservbyname("bgp", "tcp");
1267 peer
->port
= (sp
== NULL
) ? BGP_PORT_DEFAULT
: ntohs(sp
->s_port
);
1269 QOBJ_REG(peer
, peer
);
1274 * This function is invoked when a duplicate peer structure associated with
1275 * a neighbor is being deleted. If this about-to-be-deleted structure is
1276 * the one with all the config, then we have to copy over the info.
1278 void peer_xfer_config(struct peer
*peer_dst
, struct peer
*peer_src
)
1280 struct peer_af
*paf
;
1288 /* The following function is used by both peer group config copy to
1289 * individual peer and when we transfer config
1291 if (peer_src
->change_local_as
)
1292 peer_dst
->change_local_as
= peer_src
->change_local_as
;
1294 /* peer flags apply */
1295 peer_dst
->flags
= peer_src
->flags
;
1296 peer_dst
->cap
= peer_src
->cap
;
1298 peer_dst
->peer_gr_present_state
= peer_src
->peer_gr_present_state
;
1299 peer_dst
->peer_gr_new_status_flag
= peer_src
->peer_gr_new_status_flag
;
1301 peer_dst
->local_as
= peer_src
->local_as
;
1302 peer_dst
->port
= peer_src
->port
;
1303 (void)peer_sort(peer_dst
);
1304 peer_dst
->rmap_type
= peer_src
->rmap_type
;
1307 peer_dst
->holdtime
= peer_src
->holdtime
;
1308 peer_dst
->keepalive
= peer_src
->keepalive
;
1309 peer_dst
->connect
= peer_src
->connect
;
1310 peer_dst
->v_holdtime
= peer_src
->v_holdtime
;
1311 peer_dst
->v_keepalive
= peer_src
->v_keepalive
;
1312 peer_dst
->routeadv
= peer_src
->routeadv
;
1313 peer_dst
->v_routeadv
= peer_src
->v_routeadv
;
1315 /* password apply */
1316 if (peer_src
->password
&& !peer_dst
->password
)
1317 peer_dst
->password
=
1318 XSTRDUP(MTYPE_PEER_PASSWORD
, peer_src
->password
);
1320 FOREACH_AFI_SAFI (afi
, safi
) {
1321 peer_dst
->afc
[afi
][safi
] = peer_src
->afc
[afi
][safi
];
1322 peer_dst
->af_flags
[afi
][safi
] = peer_src
->af_flags
[afi
][safi
];
1323 peer_dst
->allowas_in
[afi
][safi
] =
1324 peer_src
->allowas_in
[afi
][safi
];
1325 peer_dst
->weight
[afi
][safi
] = peer_src
->weight
[afi
][safi
];
1326 peer_dst
->addpath_type
[afi
][safi
] =
1327 peer_src
->addpath_type
[afi
][safi
];
1330 for (afidx
= BGP_AF_START
; afidx
< BGP_AF_MAX
; afidx
++) {
1331 paf
= peer_src
->peer_af_array
[afidx
];
1333 peer_af_create(peer_dst
, paf
->afi
, paf
->safi
);
1336 /* update-source apply */
1337 if (peer_src
->update_source
) {
1338 if (peer_dst
->update_source
)
1339 sockunion_free(peer_dst
->update_source
);
1340 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer_dst
->update_if
);
1341 peer_dst
->update_source
=
1342 sockunion_dup(peer_src
->update_source
);
1343 } else if (peer_src
->update_if
) {
1344 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer_dst
->update_if
);
1345 if (peer_dst
->update_source
) {
1346 sockunion_free(peer_dst
->update_source
);
1347 peer_dst
->update_source
= NULL
;
1349 peer_dst
->update_if
=
1350 XSTRDUP(MTYPE_PEER_UPDATE_SOURCE
, peer_src
->update_if
);
1353 if (peer_src
->ifname
) {
1354 XFREE(MTYPE_BGP_PEER_IFNAME
, peer_dst
->ifname
);
1357 XSTRDUP(MTYPE_BGP_PEER_IFNAME
, peer_src
->ifname
);
1361 static int bgp_peer_conf_if_to_su_update_v4(struct peer
*peer
,
1362 struct interface
*ifp
)
1364 struct connected
*ifc
;
1367 struct listnode
*node
;
1369 /* If our IPv4 address on the interface is /30 or /31, we can derive the
1370 * IPv4 address of the other end.
1372 for (ALL_LIST_ELEMENTS_RO(ifp
->connected
, node
, ifc
)) {
1373 if (ifc
->address
&& (ifc
->address
->family
== AF_INET
)) {
1374 PREFIX_COPY_IPV4(&p
, CONNECTED_PREFIX(ifc
));
1375 if (p
.prefixlen
== 30) {
1376 peer
->su
.sa
.sa_family
= AF_INET
;
1377 addr
= ntohl(p
.u
.prefix4
.s_addr
);
1379 peer
->su
.sin
.sin_addr
.s_addr
=
1381 else if (addr
% 4 == 2)
1382 peer
->su
.sin
.sin_addr
.s_addr
=
1384 #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
1385 peer
->su
.sin
.sin_len
=
1386 sizeof(struct sockaddr_in
);
1387 #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
1389 } else if (p
.prefixlen
== 31) {
1390 peer
->su
.sa
.sa_family
= AF_INET
;
1391 addr
= ntohl(p
.u
.prefix4
.s_addr
);
1393 peer
->su
.sin
.sin_addr
.s_addr
=
1396 peer
->su
.sin
.sin_addr
.s_addr
=
1398 #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
1399 peer
->su
.sin
.sin_len
=
1400 sizeof(struct sockaddr_in
);
1401 #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
1403 } else if (bgp_debug_neighbor_events(peer
))
1405 "%s: IPv4 interface address is not /30 or /31, v4 session not started",
1413 static bool bgp_peer_conf_if_to_su_update_v6(struct peer
*peer
,
1414 struct interface
*ifp
)
1416 struct nbr_connected
*ifc_nbr
;
1418 /* Have we learnt the peer's IPv6 link-local address? */
1419 if (ifp
->nbr_connected
1420 && (ifc_nbr
= listnode_head(ifp
->nbr_connected
))) {
1421 peer
->su
.sa
.sa_family
= AF_INET6
;
1422 memcpy(&peer
->su
.sin6
.sin6_addr
, &ifc_nbr
->address
->u
.prefix
,
1423 sizeof(struct in6_addr
));
1425 peer
->su
.sin6
.sin6_len
= sizeof(struct sockaddr_in6
);
1427 peer
->su
.sin6
.sin6_scope_id
= ifp
->ifindex
;
1435 * Set or reset the peer address socketunion structure based on the
1436 * learnt/derived peer address. If the address has changed, update the
1437 * password on the listen socket, if needed.
1439 void bgp_peer_conf_if_to_su_update(struct peer
*peer
)
1441 struct interface
*ifp
;
1443 int peer_addr_updated
= 0;
1449 * Our peer structure is stored in the bgp->peerhash
1450 * release it before we modify anything.
1452 hash_release(peer
->bgp
->peerhash
, peer
);
1454 prev_family
= peer
->su
.sa
.sa_family
;
1455 if ((ifp
= if_lookup_by_name(peer
->conf_if
, peer
->bgp
->vrf_id
))) {
1457 /* If BGP unnumbered is not "v6only", we first see if we can
1459 * peer's IPv4 address.
1461 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_IFPEER_V6ONLY
))
1463 bgp_peer_conf_if_to_su_update_v4(peer
, ifp
);
1465 /* If "v6only" or we can't derive peer's IPv4 address, see if
1467 * learnt the peer's IPv6 link-local address. This is from the
1469 * IPv6 address in router advertisement.
1471 if (!peer_addr_updated
)
1473 bgp_peer_conf_if_to_su_update_v6(peer
, ifp
);
1475 /* If we could derive the peer address, we may need to install the
1477 * configured for the peer, if any, on the listen socket. Otherwise,
1479 * that peer's address is not available and uninstall the password, if
1482 if (peer_addr_updated
) {
1483 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
)
1484 && prev_family
== AF_UNSPEC
)
1487 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
)
1488 && prev_family
!= AF_UNSPEC
)
1489 bgp_md5_unset(peer
);
1490 peer
->su
.sa
.sa_family
= AF_UNSPEC
;
1491 memset(&peer
->su
.sin6
.sin6_addr
, 0, sizeof(struct in6_addr
));
1495 * Since our su changed we need to del/add peer to the peerhash
1497 hash_get(peer
->bgp
->peerhash
, peer
, hash_alloc_intern
);
1500 static void bgp_recalculate_afi_safi_bestpaths(struct bgp
*bgp
, afi_t afi
,
1503 struct bgp_node
*rn
, *nrn
;
1504 struct bgp_table
*table
;
1506 for (rn
= bgp_table_top(bgp
->rib
[afi
][safi
]); rn
;
1507 rn
= bgp_route_next(rn
)) {
1508 table
= bgp_node_get_bgp_table_info(rn
);
1509 if (table
!= NULL
) {
1510 /* Special handling for 2-level routing
1512 if (safi
== SAFI_MPLS_VPN
|| safi
== SAFI_ENCAP
1513 || safi
== SAFI_EVPN
) {
1514 for (nrn
= bgp_table_top(table
);
1515 nrn
; nrn
= bgp_route_next(nrn
))
1516 bgp_process(bgp
, nrn
, afi
, safi
);
1518 bgp_process(bgp
, rn
, afi
, safi
);
1523 /* Force a bestpath recalculation for all prefixes. This is used
1524 * when 'bgp bestpath' commands are entered.
1526 void bgp_recalculate_all_bestpaths(struct bgp
*bgp
)
1531 FOREACH_AFI_SAFI (afi
, safi
) {
1532 bgp_recalculate_afi_safi_bestpaths(bgp
, afi
, safi
);
1537 * Create new BGP peer.
1539 * conf_if and su are mutually exclusive if configuring from the cli.
1540 * If we are handing a doppelganger, then we *must* pass in both
1541 * the original peer's su and conf_if, so that we can appropriately
1542 * track the bgp->peerhash( ie we don't want to remove the current
1543 * one from the config ).
1545 struct peer
*peer_create(union sockunion
*su
, const char *conf_if
,
1546 struct bgp
*bgp
, as_t local_as
, as_t remote_as
,
1547 int as_type
, afi_t afi
, safi_t safi
,
1548 struct peer_group
*group
)
1552 char buf
[SU_ADDRSTRLEN
];
1554 peer
= peer_new(bgp
);
1556 peer
->conf_if
= XSTRDUP(MTYPE_PEER_CONF_IF
, conf_if
);
1560 bgp_peer_conf_if_to_su_update(peer
);
1561 XFREE(MTYPE_BGP_PEER_HOST
, peer
->host
);
1562 peer
->host
= XSTRDUP(MTYPE_BGP_PEER_HOST
, conf_if
);
1565 sockunion2str(su
, buf
, SU_ADDRSTRLEN
);
1566 XFREE(MTYPE_BGP_PEER_HOST
, peer
->host
);
1567 peer
->host
= XSTRDUP(MTYPE_BGP_PEER_HOST
, buf
);
1569 peer
->local_as
= local_as
;
1570 peer
->as
= remote_as
;
1571 peer
->as_type
= as_type
;
1572 peer
->local_id
= bgp
->router_id
;
1573 peer
->v_holdtime
= bgp
->default_holdtime
;
1574 peer
->v_keepalive
= bgp
->default_keepalive
;
1575 peer
->v_routeadv
= (peer_sort(peer
) == BGP_PEER_IBGP
)
1576 ? BGP_DEFAULT_IBGP_ROUTEADV
1577 : BGP_DEFAULT_EBGP_ROUTEADV
;
1579 peer
= peer_lock(peer
); /* bgp peer list reference */
1580 peer
->group
= group
;
1581 listnode_add_sort(bgp
->peer
, peer
);
1582 hash_get(bgp
->peerhash
, peer
, hash_alloc_intern
);
1584 /* Adjust update-group coalesce timer heuristics for # peers. */
1585 if (bgp
->heuristic_coalesce
) {
1586 long ct
= BGP_DEFAULT_SUBGROUP_COALESCE_TIME
1588 * BGP_PEER_ADJUST_SUBGROUP_COALESCE_TIME
);
1589 bgp
->coalesce_time
= MIN(BGP_MAX_SUBGROUP_COALESCE_TIME
, ct
);
1592 active
= peer_active(peer
);
1594 if (peer
->su
.sa
.sa_family
== AF_UNSPEC
)
1595 peer
->last_reset
= PEER_DOWN_NBR_ADDR
;
1597 peer
->last_reset
= PEER_DOWN_NOAFI_ACTIVATED
;
1600 /* Last read and reset time set */
1601 peer
->readtime
= peer
->resettime
= bgp_clock();
1603 /* Default TTL set. */
1604 peer
->ttl
= (peer
->sort
== BGP_PEER_IBGP
) ? MAXTTL
: BGP_DEFAULT_TTL
;
1606 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
1609 peer
->afc
[afi
][safi
] = 1;
1610 peer_af_create(peer
, afi
, safi
);
1613 /* auto shutdown if configured */
1614 if (bgp
->autoshutdown
)
1615 peer_flag_set(peer
, PEER_FLAG_SHUTDOWN
);
1616 /* Set up peer's events and timers. */
1617 else if (!active
&& peer_active(peer
))
1618 bgp_timer_set(peer
);
1620 bgp_peer_gr_flags_update(peer
);
1621 BGP_GR_ROUTER_DETECT_AND_SEND_CAPABILITY_TO_ZEBRA(bgp
, bgp
->peer
);
1626 /* Make accept BGP peer. This function is only called from the test code */
1627 struct peer
*peer_create_accept(struct bgp
*bgp
)
1631 peer
= peer_new(bgp
);
1633 peer
= peer_lock(peer
); /* bgp peer list reference */
1634 listnode_add_sort(bgp
->peer
, peer
);
1640 * Return true if we have a peer configured to use this afi/safi
1642 int bgp_afi_safi_peer_exists(struct bgp
*bgp
, afi_t afi
, safi_t safi
)
1644 struct listnode
*node
;
1647 for (ALL_LIST_ELEMENTS_RO(bgp
->peer
, node
, peer
)) {
1648 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
))
1651 if (peer
->afc
[afi
][safi
])
1658 /* Change peer's AS number. */
1659 void peer_as_change(struct peer
*peer
, as_t as
, int as_specified
)
1661 bgp_peer_sort_t origtype
, newtype
;
1664 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
1665 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
1666 peer
->last_reset
= PEER_DOWN_REMOTE_AS_CHANGE
;
1667 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
1668 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
1670 bgp_session_reset(peer
);
1672 origtype
= peer_sort_lookup(peer
);
1674 peer
->as_type
= as_specified
;
1676 if (bgp_config_check(peer
->bgp
, BGP_CONFIG_CONFEDERATION
)
1677 && !bgp_confederation_peers_check(peer
->bgp
, as
)
1678 && peer
->bgp
->as
!= as
)
1679 peer
->local_as
= peer
->bgp
->confed_id
;
1681 peer
->local_as
= peer
->bgp
->as
;
1683 newtype
= peer_sort(peer
);
1684 /* Advertisement-interval reset */
1685 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_ROUTEADV
)) {
1686 peer
->v_routeadv
= (newtype
== BGP_PEER_IBGP
)
1687 ? BGP_DEFAULT_IBGP_ROUTEADV
1688 : BGP_DEFAULT_EBGP_ROUTEADV
;
1692 if (newtype
== BGP_PEER_IBGP
)
1694 else if (origtype
== BGP_PEER_IBGP
)
1695 peer
->ttl
= BGP_DEFAULT_TTL
;
1697 /* reflector-client reset */
1698 if (newtype
!= BGP_PEER_IBGP
) {
1699 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_UNICAST
],
1700 PEER_FLAG_REFLECTOR_CLIENT
);
1701 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_MULTICAST
],
1702 PEER_FLAG_REFLECTOR_CLIENT
);
1703 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_LABELED_UNICAST
],
1704 PEER_FLAG_REFLECTOR_CLIENT
);
1705 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_MPLS_VPN
],
1706 PEER_FLAG_REFLECTOR_CLIENT
);
1707 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_ENCAP
],
1708 PEER_FLAG_REFLECTOR_CLIENT
);
1709 UNSET_FLAG(peer
->af_flags
[AFI_IP
][SAFI_FLOWSPEC
],
1710 PEER_FLAG_REFLECTOR_CLIENT
);
1711 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_UNICAST
],
1712 PEER_FLAG_REFLECTOR_CLIENT
);
1713 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_MULTICAST
],
1714 PEER_FLAG_REFLECTOR_CLIENT
);
1715 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_LABELED_UNICAST
],
1716 PEER_FLAG_REFLECTOR_CLIENT
);
1717 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_MPLS_VPN
],
1718 PEER_FLAG_REFLECTOR_CLIENT
);
1719 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_ENCAP
],
1720 PEER_FLAG_REFLECTOR_CLIENT
);
1721 UNSET_FLAG(peer
->af_flags
[AFI_IP6
][SAFI_FLOWSPEC
],
1722 PEER_FLAG_REFLECTOR_CLIENT
);
1723 UNSET_FLAG(peer
->af_flags
[AFI_L2VPN
][SAFI_EVPN
],
1724 PEER_FLAG_REFLECTOR_CLIENT
);
1727 /* local-as reset */
1728 if (newtype
!= BGP_PEER_EBGP
) {
1729 peer
->change_local_as
= 0;
1730 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS
);
1731 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
1732 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
1736 /* If peer does not exist, create new one. If peer already exists,
1737 set AS number to the peer. */
1738 int peer_remote_as(struct bgp
*bgp
, union sockunion
*su
, const char *conf_if
,
1739 as_t
*as
, int as_type
, afi_t afi
, safi_t safi
)
1745 peer
= peer_lookup_by_conf_if(bgp
, conf_if
);
1747 peer
= peer_lookup(bgp
, su
);
1750 /* Not allowed for a dynamic peer. */
1751 if (peer_dynamic_neighbor(peer
)) {
1753 return BGP_ERR_INVALID_FOR_DYNAMIC_PEER
;
1756 /* When this peer is a member of peer-group. */
1758 /* peer-group already has AS number/internal/external */
1759 if (peer
->group
->conf
->as
1760 || peer
->group
->conf
->as_type
) {
1761 /* Return peer group's AS number. */
1762 *as
= peer
->group
->conf
->as
;
1763 return BGP_ERR_PEER_GROUP_MEMBER
;
1766 bgp_peer_sort_t peer_sort_type
=
1767 peer_sort(peer
->group
->conf
);
1769 /* Explicit AS numbers used, compare AS numbers */
1770 if (as_type
== AS_SPECIFIED
) {
1771 if (((peer_sort_type
== BGP_PEER_IBGP
)
1772 && (bgp
->as
!= *as
))
1773 || ((peer_sort_type
== BGP_PEER_EBGP
)
1774 && (bgp
->as
== *as
))) {
1776 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT
;
1779 /* internal/external used, compare as-types */
1780 if (((peer_sort_type
== BGP_PEER_IBGP
)
1781 && (as_type
!= AS_INTERNAL
))
1782 || ((peer_sort_type
== BGP_PEER_EBGP
)
1783 && (as_type
!= AS_EXTERNAL
))) {
1785 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT
;
1790 /* Existing peer's AS number change. */
1791 if (((peer
->as_type
== AS_SPECIFIED
) && peer
->as
!= *as
)
1792 || (peer
->as_type
!= as_type
))
1793 peer_as_change(peer
, *as
, as_type
);
1796 return BGP_ERR_NO_INTERFACE_CONFIG
;
1798 /* If the peer is not part of our confederation, and its not an
1799 iBGP peer then spoof the source AS */
1800 if (bgp_config_check(bgp
, BGP_CONFIG_CONFEDERATION
)
1801 && !bgp_confederation_peers_check(bgp
, *as
)
1803 local_as
= bgp
->confed_id
;
1807 /* If this is IPv4 unicast configuration and "no bgp default
1808 ipv4-unicast" is specified. */
1810 if (CHECK_FLAG(bgp
->flags
, BGP_FLAG_NO_DEFAULT_IPV4
)
1811 && afi
== AFI_IP
&& safi
== SAFI_UNICAST
)
1812 peer_create(su
, conf_if
, bgp
, local_as
, *as
, as_type
, 0,
1815 peer_create(su
, conf_if
, bgp
, local_as
, *as
, as_type
,
1822 static void peer_group2peer_config_copy_af(struct peer_group
*group
,
1823 struct peer
*peer
, afi_t afi
,
1827 int out
= FILTER_OUT
;
1829 uint32_t pflags_ovrd
;
1830 uint8_t *pfilter_ovrd
;
1834 pflags_ovrd
= peer
->af_flags_override
[afi
][safi
];
1835 pfilter_ovrd
= &peer
->filter_override
[afi
][safi
][in
];
1837 /* peer af_flags apply */
1838 flags_tmp
= conf
->af_flags
[afi
][safi
] & ~pflags_ovrd
;
1839 flags_tmp
^= conf
->af_flags_invert
[afi
][safi
]
1840 ^ peer
->af_flags_invert
[afi
][safi
];
1841 flags_tmp
&= ~pflags_ovrd
;
1843 UNSET_FLAG(peer
->af_flags
[afi
][safi
], ~pflags_ovrd
);
1844 SET_FLAG(peer
->af_flags
[afi
][safi
], flags_tmp
);
1845 SET_FLAG(peer
->af_flags_invert
[afi
][safi
],
1846 conf
->af_flags_invert
[afi
][safi
]);
1848 /* maximum-prefix */
1849 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_MAX_PREFIX
)) {
1850 PEER_ATTR_INHERIT(peer
, group
, pmax
[afi
][safi
]);
1851 PEER_ATTR_INHERIT(peer
, group
, pmax_threshold
[afi
][safi
]);
1852 PEER_ATTR_INHERIT(peer
, group
, pmax_restart
[afi
][safi
]);
1856 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_ALLOWAS_IN
))
1857 PEER_ATTR_INHERIT(peer
, group
, allowas_in
[afi
][safi
]);
1860 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_WEIGHT
))
1861 PEER_ATTR_INHERIT(peer
, group
, weight
[afi
][safi
]);
1863 /* default-originate route-map */
1864 if (!CHECK_FLAG(pflags_ovrd
, PEER_FLAG_DEFAULT_ORIGINATE
)) {
1865 PEER_STR_ATTR_INHERIT(peer
, group
, default_rmap
[afi
][safi
].name
,
1866 MTYPE_ROUTE_MAP_NAME
);
1867 PEER_ATTR_INHERIT(peer
, group
, default_rmap
[afi
][safi
].map
);
1870 /* inbound filter apply */
1871 if (!CHECK_FLAG(pfilter_ovrd
[in
], PEER_FT_DISTRIBUTE_LIST
)) {
1872 PEER_STR_ATTR_INHERIT(peer
, group
,
1873 filter
[afi
][safi
].dlist
[in
].name
,
1874 MTYPE_BGP_FILTER_NAME
);
1875 PEER_ATTR_INHERIT(peer
, group
,
1876 filter
[afi
][safi
].dlist
[in
].alist
);
1879 if (!CHECK_FLAG(pfilter_ovrd
[in
], PEER_FT_PREFIX_LIST
)) {
1880 PEER_STR_ATTR_INHERIT(peer
, group
,
1881 filter
[afi
][safi
].plist
[in
].name
,
1882 MTYPE_BGP_FILTER_NAME
);
1883 PEER_ATTR_INHERIT(peer
, group
,
1884 filter
[afi
][safi
].plist
[in
].plist
);
1887 if (!CHECK_FLAG(pfilter_ovrd
[in
], PEER_FT_FILTER_LIST
)) {
1888 PEER_STR_ATTR_INHERIT(peer
, group
,
1889 filter
[afi
][safi
].aslist
[in
].name
,
1890 MTYPE_BGP_FILTER_NAME
);
1891 PEER_ATTR_INHERIT(peer
, group
,
1892 filter
[afi
][safi
].aslist
[in
].aslist
);
1895 if (!CHECK_FLAG(pfilter_ovrd
[RMAP_IN
], PEER_FT_ROUTE_MAP
)) {
1896 PEER_STR_ATTR_INHERIT(peer
, group
,
1897 filter
[afi
][safi
].map
[in
].name
,
1898 MTYPE_BGP_FILTER_NAME
);
1899 PEER_ATTR_INHERIT(peer
, group
,
1900 filter
[afi
][safi
].map
[RMAP_IN
].map
);
1903 /* outbound filter apply */
1904 if (!CHECK_FLAG(pfilter_ovrd
[out
], PEER_FT_DISTRIBUTE_LIST
)) {
1905 PEER_STR_ATTR_INHERIT(peer
, group
,
1906 filter
[afi
][safi
].dlist
[out
].name
,
1907 MTYPE_BGP_FILTER_NAME
);
1908 PEER_ATTR_INHERIT(peer
, group
,
1909 filter
[afi
][safi
].dlist
[out
].alist
);
1912 if (!CHECK_FLAG(pfilter_ovrd
[out
], PEER_FT_PREFIX_LIST
)) {
1913 PEER_STR_ATTR_INHERIT(peer
, group
,
1914 filter
[afi
][safi
].plist
[out
].name
,
1915 MTYPE_BGP_FILTER_NAME
);
1916 PEER_ATTR_INHERIT(peer
, group
,
1917 filter
[afi
][safi
].plist
[out
].plist
);
1920 if (!CHECK_FLAG(pfilter_ovrd
[out
], PEER_FT_FILTER_LIST
)) {
1921 PEER_STR_ATTR_INHERIT(peer
, group
,
1922 filter
[afi
][safi
].aslist
[out
].name
,
1923 MTYPE_BGP_FILTER_NAME
);
1924 PEER_ATTR_INHERIT(peer
, group
,
1925 filter
[afi
][safi
].aslist
[out
].aslist
);
1928 if (!CHECK_FLAG(pfilter_ovrd
[RMAP_OUT
], PEER_FT_ROUTE_MAP
)) {
1929 PEER_STR_ATTR_INHERIT(peer
, group
,
1930 filter
[afi
][safi
].map
[RMAP_OUT
].name
,
1931 MTYPE_BGP_FILTER_NAME
);
1932 PEER_ATTR_INHERIT(peer
, group
,
1933 filter
[afi
][safi
].map
[RMAP_OUT
].map
);
1936 /* nondirectional filter apply */
1937 if (!CHECK_FLAG(pfilter_ovrd
[0], PEER_FT_UNSUPPRESS_MAP
)) {
1938 PEER_STR_ATTR_INHERIT(peer
, group
, filter
[afi
][safi
].usmap
.name
,
1939 MTYPE_BGP_FILTER_NAME
);
1940 PEER_ATTR_INHERIT(peer
, group
, filter
[afi
][safi
].usmap
.map
);
1943 if (peer
->addpath_type
[afi
][safi
] == BGP_ADDPATH_NONE
) {
1944 peer
->addpath_type
[afi
][safi
] = conf
->addpath_type
[afi
][safi
];
1945 bgp_addpath_type_changed(conf
->bgp
);
1949 static int peer_activate_af(struct peer
*peer
, afi_t afi
, safi_t safi
)
1954 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
1955 flog_err(EC_BGP_PEER_GROUP
, "%s was called for peer-group %s",
1956 __func__
, peer
->host
);
1960 /* Do not activate a peer for both SAFI_UNICAST and SAFI_LABELED_UNICAST
1962 if ((safi
== SAFI_UNICAST
&& peer
->afc
[afi
][SAFI_LABELED_UNICAST
])
1963 || (safi
== SAFI_LABELED_UNICAST
&& peer
->afc
[afi
][SAFI_UNICAST
]))
1964 return BGP_ERR_PEER_SAFI_CONFLICT
;
1966 /* Nothing to do if we've already activated this peer */
1967 if (peer
->afc
[afi
][safi
])
1970 if (peer_af_create(peer
, afi
, safi
) == NULL
)
1973 active
= peer_active(peer
);
1974 peer
->afc
[afi
][safi
] = 1;
1977 peer_group2peer_config_copy_af(peer
->group
, peer
, afi
, safi
);
1979 if (!active
&& peer_active(peer
)) {
1980 bgp_timer_set(peer
);
1982 if (peer
->status
== Established
) {
1983 if (CHECK_FLAG(peer
->cap
, PEER_CAP_DYNAMIC_RCV
)) {
1984 peer
->afc_adv
[afi
][safi
] = 1;
1985 bgp_capability_send(peer
, afi
, safi
,
1987 CAPABILITY_ACTION_SET
);
1988 if (peer
->afc_recv
[afi
][safi
]) {
1989 peer
->afc_nego
[afi
][safi
] = 1;
1990 bgp_announce_route(peer
, afi
, safi
);
1993 peer
->last_reset
= PEER_DOWN_AF_ACTIVATE
;
1994 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
1995 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
1998 if (peer
->status
== OpenSent
|| peer
->status
== OpenConfirm
) {
1999 peer
->last_reset
= PEER_DOWN_AF_ACTIVATE
;
2000 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2001 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2004 * If we are turning on a AFI/SAFI locally and we've
2005 * started bringing a peer up, we need to tell
2006 * the other peer to restart because we might loose
2007 * configuration here because when the doppelganger
2008 * gets to a established state due to how
2009 * we resolve we could just overwrite the afi/safi
2012 other
= peer
->doppelganger
;
2014 && (other
->status
== OpenSent
2015 || other
->status
== OpenConfirm
)) {
2016 other
->last_reset
= PEER_DOWN_AF_ACTIVATE
;
2017 bgp_notify_send(other
, BGP_NOTIFY_CEASE
,
2018 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2025 /* Activate the peer or peer group for specified AFI and SAFI. */
2026 int peer_activate(struct peer
*peer
, afi_t afi
, safi_t safi
)
2029 struct peer_group
*group
;
2030 struct listnode
*node
, *nnode
;
2031 struct peer
*tmp_peer
;
2034 /* Nothing to do if we've already activated this peer */
2035 if (peer
->afc
[afi
][safi
])
2040 /* This is a peer-group so activate all of the members of the
2041 * peer-group as well */
2042 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
2044 /* Do not activate a peer for both SAFI_UNICAST and
2045 * SAFI_LABELED_UNICAST */
2046 if ((safi
== SAFI_UNICAST
2047 && peer
->afc
[afi
][SAFI_LABELED_UNICAST
])
2048 || (safi
== SAFI_LABELED_UNICAST
2049 && peer
->afc
[afi
][SAFI_UNICAST
]))
2050 return BGP_ERR_PEER_SAFI_CONFLICT
;
2052 peer
->afc
[afi
][safi
] = 1;
2053 group
= peer
->group
;
2055 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, tmp_peer
)) {
2056 ret
|= peer_activate_af(tmp_peer
, afi
, safi
);
2059 ret
|= peer_activate_af(peer
, afi
, safi
);
2062 /* If this is the first peer to be activated for this
2063 * afi/labeled-unicast recalc bestpaths to trigger label allocation */
2064 if (safi
== SAFI_LABELED_UNICAST
2065 && !bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
]) {
2067 if (BGP_DEBUG(zebra
, ZEBRA
))
2069 "peer(s) are now active for labeled-unicast, allocate MPLS labels");
2071 bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
] = 1;
2072 bgp_recalculate_afi_safi_bestpaths(bgp
, afi
, SAFI_UNICAST
);
2075 if (safi
== SAFI_FLOWSPEC
) {
2076 /* connect to table manager */
2077 bgp_zebra_init_tm_connect(bgp
);
2082 static bool non_peergroup_deactivate_af(struct peer
*peer
, afi_t afi
,
2085 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
2086 flog_err(EC_BGP_PEER_GROUP
, "%s was called for peer-group %s",
2087 __func__
, peer
->host
);
2091 /* Nothing to do if we've already deactivated this peer */
2092 if (!peer
->afc
[afi
][safi
])
2095 /* De-activate the address family configuration. */
2096 peer
->afc
[afi
][safi
] = 0;
2098 if (peer_af_delete(peer
, afi
, safi
) != 0) {
2099 flog_err(EC_BGP_PEER_DELETE
,
2100 "couldn't delete af structure for peer %s(%s, %s)",
2101 peer
->host
, afi2str(afi
), safi2str(safi
));
2105 if (peer
->status
== Established
) {
2106 if (CHECK_FLAG(peer
->cap
, PEER_CAP_DYNAMIC_RCV
)) {
2107 peer
->afc_adv
[afi
][safi
] = 0;
2108 peer
->afc_nego
[afi
][safi
] = 0;
2110 if (peer_active_nego(peer
)) {
2111 bgp_capability_send(peer
, afi
, safi
,
2113 CAPABILITY_ACTION_UNSET
);
2114 bgp_clear_route(peer
, afi
, safi
);
2115 peer
->pcount
[afi
][safi
] = 0;
2117 peer
->last_reset
= PEER_DOWN_NEIGHBOR_DELETE
;
2118 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2119 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2122 peer
->last_reset
= PEER_DOWN_NEIGHBOR_DELETE
;
2123 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2124 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2131 int peer_deactivate(struct peer
*peer
, afi_t afi
, safi_t safi
)
2134 struct peer_group
*group
;
2135 struct peer
*tmp_peer
;
2136 struct listnode
*node
, *nnode
;
2139 /* Nothing to do if we've already de-activated this peer */
2140 if (!peer
->afc
[afi
][safi
])
2143 /* This is a peer-group so de-activate all of the members of the
2144 * peer-group as well */
2145 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
2146 peer
->afc
[afi
][safi
] = 0;
2147 group
= peer
->group
;
2149 if (peer_af_delete(peer
, afi
, safi
) != 0) {
2152 "couldn't delete af structure for peer %s(%s, %s)",
2153 peer
->host
, afi2str(afi
), safi2str(safi
));
2156 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, tmp_peer
)) {
2157 ret
|= non_peergroup_deactivate_af(tmp_peer
, afi
, safi
);
2160 ret
|= non_peergroup_deactivate_af(peer
, afi
, safi
);
2165 /* If this is the last peer to be deactivated for this
2166 * afi/labeled-unicast recalc bestpaths to trigger label deallocation */
2167 if (safi
== SAFI_LABELED_UNICAST
2168 && bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
]
2169 && !bgp_afi_safi_peer_exists(bgp
, afi
, safi
)) {
2171 if (BGP_DEBUG(zebra
, ZEBRA
))
2173 "peer(s) are no longer active for labeled-unicast, deallocate MPLS labels");
2175 bgp
->allocate_mpls_labels
[afi
][SAFI_UNICAST
] = 0;
2176 bgp_recalculate_afi_safi_bestpaths(bgp
, afi
, SAFI_UNICAST
);
2181 int peer_afc_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int enable
)
2184 return peer_activate(peer
, afi
, safi
);
2186 return peer_deactivate(peer
, afi
, safi
);
2189 void peer_nsf_stop(struct peer
*peer
)
2194 UNSET_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
);
2195 UNSET_FLAG(peer
->sflags
, PEER_STATUS_NSF_MODE
);
2197 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++)
2198 for (safi
= SAFI_UNICAST
; safi
<= SAFI_MPLS_VPN
; safi
++)
2199 peer
->nsf
[afi
][safi
] = 0;
2201 if (peer
->t_gr_restart
) {
2202 BGP_TIMER_OFF(peer
->t_gr_restart
);
2203 if (bgp_debug_neighbor_events(peer
))
2204 zlog_debug("%s graceful restart timer stopped",
2207 if (peer
->t_gr_stale
) {
2208 BGP_TIMER_OFF(peer
->t_gr_stale
);
2209 if (bgp_debug_neighbor_events(peer
))
2211 "%s graceful restart stalepath timer stopped",
2214 bgp_clear_route_all(peer
);
2217 /* Delete peer from confguration.
2219 * The peer is moved to a dead-end "Deleted" neighbour-state, to allow
2220 * it to "cool off" and refcounts to hit 0, at which state it is freed.
2222 * This function /should/ take care to be idempotent, to guard against
2223 * it being called multiple times through stray events that come in
2224 * that happen to result in this function being called again. That
2225 * said, getting here for a "Deleted" peer is a bug in the neighbour
2228 int peer_delete(struct peer
*peer
)
2234 struct bgp_filter
*filter
;
2235 struct listnode
*pn
;
2238 assert(peer
->status
!= Deleted
);
2241 accept_peer
= CHECK_FLAG(peer
->sflags
, PEER_STATUS_ACCEPT_PEER
);
2243 bgp_keepalives_off(peer
);
2244 bgp_reads_off(peer
);
2245 bgp_writes_off(peer
);
2246 assert(!CHECK_FLAG(peer
->thread_flags
, PEER_THREAD_WRITES_ON
));
2247 assert(!CHECK_FLAG(peer
->thread_flags
, PEER_THREAD_READS_ON
));
2248 assert(!CHECK_FLAG(peer
->thread_flags
, PEER_THREAD_KEEPALIVES_ON
));
2250 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
))
2251 peer_nsf_stop(peer
);
2253 SET_FLAG(peer
->flags
, PEER_FLAG_DELETE
);
2255 bgp_bfd_deregister_peer(peer
);
2257 /* If this peer belongs to peer group, clear up the
2260 if (peer_dynamic_neighbor(peer
))
2261 peer_drop_dynamic_neighbor(peer
);
2263 if ((pn
= listnode_lookup(peer
->group
->peer
, peer
))) {
2265 peer
); /* group->peer list reference */
2266 list_delete_node(peer
->group
->peer
, pn
);
2271 /* Withdraw all information from routing table. We can not use
2272 * BGP_EVENT_ADD (peer, BGP_Stop) at here. Because the event is
2273 * executed after peer structure is deleted.
2275 peer
->last_reset
= PEER_DOWN_NEIGHBOR_DELETE
;
2277 UNSET_FLAG(peer
->flags
, PEER_FLAG_DELETE
);
2279 if (peer
->doppelganger
) {
2280 peer
->doppelganger
->doppelganger
= NULL
;
2281 peer
->doppelganger
= NULL
;
2284 UNSET_FLAG(peer
->sflags
, PEER_STATUS_ACCEPT_PEER
);
2285 bgp_fsm_change_status(peer
, Deleted
);
2287 /* Remove from NHT */
2288 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
))
2289 bgp_unlink_nexthop_by_peer(peer
);
2291 /* Password configuration */
2292 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
)) {
2293 XFREE(MTYPE_PEER_PASSWORD
, peer
->password
);
2295 if (!accept_peer
&& !BGP_PEER_SU_UNSPEC(peer
)
2296 && !CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
2297 bgp_md5_unset(peer
);
2300 bgp_timer_set(peer
); /* stops all timers for Deleted */
2302 /* Delete from all peer list. */
2303 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)
2304 && (pn
= listnode_lookup(bgp
->peer
, peer
))) {
2305 peer_unlock(peer
); /* bgp peer list reference */
2306 list_delete_node(bgp
->peer
, pn
);
2307 hash_release(bgp
->peerhash
, peer
);
2312 stream_fifo_free(peer
->ibuf
);
2317 stream_fifo_free(peer
->obuf
);
2321 if (peer
->ibuf_work
) {
2322 ringbuf_del(peer
->ibuf_work
);
2323 peer
->ibuf_work
= NULL
;
2326 if (peer
->obuf_work
) {
2327 stream_free(peer
->obuf_work
);
2328 peer
->obuf_work
= NULL
;
2331 if (peer
->scratch
) {
2332 stream_free(peer
->scratch
);
2333 peer
->scratch
= NULL
;
2336 /* Local and remote addresses. */
2337 if (peer
->su_local
) {
2338 sockunion_free(peer
->su_local
);
2339 peer
->su_local
= NULL
;
2342 if (peer
->su_remote
) {
2343 sockunion_free(peer
->su_remote
);
2344 peer
->su_remote
= NULL
;
2347 /* Free filter related memory. */
2348 FOREACH_AFI_SAFI (afi
, safi
) {
2349 filter
= &peer
->filter
[afi
][safi
];
2351 for (i
= FILTER_IN
; i
< FILTER_MAX
; i
++) {
2352 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->dlist
[i
].name
);
2353 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->plist
[i
].name
);
2354 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->aslist
[i
].name
);
2357 for (i
= RMAP_IN
; i
< RMAP_MAX
; i
++) {
2358 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[i
].name
);
2361 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
2362 XFREE(MTYPE_ROUTE_MAP_NAME
, peer
->default_rmap
[afi
][safi
].name
);
2365 FOREACH_AFI_SAFI (afi
, safi
)
2366 peer_af_delete(peer
, afi
, safi
);
2368 XFREE(MTYPE_BGP_PEER_HOST
, peer
->hostname
);
2369 XFREE(MTYPE_BGP_PEER_HOST
, peer
->domainname
);
2371 peer_unlock(peer
); /* initial reference */
2376 static int peer_group_cmp(struct peer_group
*g1
, struct peer_group
*g2
)
2378 return strcmp(g1
->name
, g2
->name
);
2381 /* Peer group cofiguration. */
2382 static struct peer_group
*peer_group_new(void)
2384 return XCALLOC(MTYPE_PEER_GROUP
, sizeof(struct peer_group
));
2387 static void peer_group_free(struct peer_group
*group
)
2389 XFREE(MTYPE_PEER_GROUP
, group
);
2392 struct peer_group
*peer_group_lookup(struct bgp
*bgp
, const char *name
)
2394 struct peer_group
*group
;
2395 struct listnode
*node
, *nnode
;
2397 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
2398 if (strcmp(group
->name
, name
) == 0)
2404 struct peer_group
*peer_group_get(struct bgp
*bgp
, const char *name
)
2406 struct peer_group
*group
;
2409 group
= peer_group_lookup(bgp
, name
);
2413 group
= peer_group_new();
2415 XFREE(MTYPE_PEER_GROUP_HOST
, group
->name
);
2416 group
->name
= XSTRDUP(MTYPE_PEER_GROUP_HOST
, name
);
2417 group
->peer
= list_new();
2418 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++)
2419 group
->listen_range
[afi
] = list_new();
2420 group
->conf
= peer_new(bgp
);
2421 if (!CHECK_FLAG(bgp
->flags
, BGP_FLAG_NO_DEFAULT_IPV4
))
2422 group
->conf
->afc
[AFI_IP
][SAFI_UNICAST
] = 1;
2423 XFREE(MTYPE_BGP_PEER_HOST
, group
->conf
->host
);
2424 group
->conf
->host
= XSTRDUP(MTYPE_BGP_PEER_HOST
, name
);
2425 group
->conf
->group
= group
;
2426 group
->conf
->as
= 0;
2427 group
->conf
->ttl
= BGP_DEFAULT_TTL
;
2428 group
->conf
->gtsm_hops
= BGP_GTSM_HOPS_DISABLED
;
2429 group
->conf
->v_routeadv
= BGP_DEFAULT_EBGP_ROUTEADV
;
2430 SET_FLAG(group
->conf
->sflags
, PEER_STATUS_GROUP
);
2431 listnode_add_sort(bgp
->group
, group
);
2436 static void peer_group2peer_config_copy(struct peer_group
*group
,
2446 peer
->as
= conf
->as
;
2449 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_LOCAL_AS
))
2450 peer
->change_local_as
= conf
->change_local_as
;
2452 /* If peer-group has configured TTL then override it */
2453 if (conf
->ttl
!= BGP_DEFAULT_TTL
)
2454 peer
->ttl
= conf
->ttl
;
2457 peer
->gtsm_hops
= conf
->gtsm_hops
;
2459 /* peer flags apply */
2460 flags_tmp
= conf
->flags
& ~peer
->flags_override
;
2461 flags_tmp
^= conf
->flags_invert
^ peer
->flags_invert
;
2462 flags_tmp
&= ~peer
->flags_override
;
2464 UNSET_FLAG(peer
->flags
, ~peer
->flags_override
);
2465 SET_FLAG(peer
->flags
, flags_tmp
);
2466 SET_FLAG(peer
->flags_invert
, conf
->flags_invert
);
2468 /* peer timers apply */
2469 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_TIMER
)) {
2470 PEER_ATTR_INHERIT(peer
, group
, holdtime
);
2471 PEER_ATTR_INHERIT(peer
, group
, keepalive
);
2474 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_TIMER_CONNECT
)) {
2475 PEER_ATTR_INHERIT(peer
, group
, connect
);
2476 if (CHECK_FLAG(conf
->flags
, PEER_FLAG_TIMER_CONNECT
))
2477 peer
->v_connect
= conf
->connect
;
2479 peer
->v_connect
= peer
->bgp
->default_connect_retry
;
2482 /* advertisement-interval apply */
2483 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_ROUTEADV
)) {
2484 PEER_ATTR_INHERIT(peer
, group
, routeadv
);
2485 if (CHECK_FLAG(conf
->flags
, PEER_FLAG_ROUTEADV
))
2486 peer
->v_routeadv
= conf
->routeadv
;
2488 peer
->v_routeadv
= (peer_sort(peer
) == BGP_PEER_IBGP
)
2489 ? BGP_DEFAULT_IBGP_ROUTEADV
2490 : BGP_DEFAULT_EBGP_ROUTEADV
;
2493 /* password apply */
2494 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_PASSWORD
))
2495 PEER_STR_ATTR_INHERIT(peer
, group
, password
,
2496 MTYPE_PEER_PASSWORD
);
2498 if (!BGP_PEER_SU_UNSPEC(peer
))
2501 /* update-source apply */
2502 if (!CHECK_FLAG(peer
->flags_override
, PEER_FLAG_UPDATE_SOURCE
)) {
2503 if (conf
->update_source
) {
2504 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
2505 PEER_SU_ATTR_INHERIT(peer
, group
, update_source
);
2506 } else if (conf
->update_if
) {
2507 sockunion_free(peer
->update_source
);
2508 PEER_STR_ATTR_INHERIT(peer
, group
, update_if
,
2509 MTYPE_PEER_UPDATE_SOURCE
);
2513 bgp_bfd_peer_group2peer_copy(conf
, peer
);
2516 /* Peer group's remote AS configuration. */
2517 int peer_group_remote_as(struct bgp
*bgp
, const char *group_name
, as_t
*as
,
2520 struct peer_group
*group
;
2522 struct listnode
*node
, *nnode
;
2524 group
= peer_group_lookup(bgp
, group_name
);
2528 if ((as_type
== group
->conf
->as_type
) && (group
->conf
->as
== *as
))
2532 /* When we setup peer-group AS number all peer group member's AS
2533 number must be updated to same number. */
2534 peer_as_change(group
->conf
, *as
, as_type
);
2536 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2537 if (((peer
->as_type
== AS_SPECIFIED
) && peer
->as
!= *as
)
2538 || (peer
->as_type
!= as_type
))
2539 peer_as_change(peer
, *as
, as_type
);
2545 void peer_notify_unconfig(struct peer
*peer
)
2547 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
2548 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2549 BGP_NOTIFY_CEASE_PEER_UNCONFIG
);
2552 void peer_group_notify_unconfig(struct peer_group
*group
)
2554 struct peer
*peer
, *other
;
2555 struct listnode
*node
, *nnode
;
2557 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2558 other
= peer
->doppelganger
;
2559 if (other
&& other
->status
!= Deleted
) {
2560 other
->group
= NULL
;
2561 peer_notify_unconfig(other
);
2563 peer_notify_unconfig(peer
);
2567 int peer_group_delete(struct peer_group
*group
)
2571 struct prefix
*prefix
;
2573 struct listnode
*node
, *nnode
;
2578 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2579 other
= peer
->doppelganger
;
2581 if (other
&& other
->status
!= Deleted
) {
2582 other
->group
= NULL
;
2586 list_delete(&group
->peer
);
2588 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
2589 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
,
2591 prefix_free(&prefix
);
2593 list_delete(&group
->listen_range
[afi
]);
2596 XFREE(MTYPE_PEER_GROUP_HOST
, group
->name
);
2599 bfd_info_free(&(group
->conf
->bfd_info
));
2601 group
->conf
->group
= NULL
;
2602 peer_delete(group
->conf
);
2604 /* Delete from all peer_group list. */
2605 listnode_delete(bgp
->group
, group
);
2607 peer_group_free(group
);
2612 int peer_group_remote_as_delete(struct peer_group
*group
)
2614 struct peer
*peer
, *other
;
2615 struct listnode
*node
, *nnode
;
2617 if ((group
->conf
->as_type
== AS_UNSPECIFIED
)
2618 || ((!group
->conf
->as
) && (group
->conf
->as_type
== AS_SPECIFIED
)))
2621 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2622 other
= peer
->doppelganger
;
2626 if (other
&& other
->status
!= Deleted
) {
2627 other
->group
= NULL
;
2631 list_delete_all_node(group
->peer
);
2633 group
->conf
->as
= 0;
2634 group
->conf
->as_type
= AS_UNSPECIFIED
;
2639 int peer_group_listen_range_add(struct peer_group
*group
, struct prefix
*range
)
2641 struct prefix
*prefix
;
2642 struct listnode
*node
, *nnode
;
2645 afi
= family2afi(range
->family
);
2647 /* Group needs remote AS configured. */
2648 if (group
->conf
->as_type
== AS_UNSPECIFIED
)
2649 return BGP_ERR_PEER_GROUP_NO_REMOTE_AS
;
2651 /* Ensure no duplicates. Currently we don't care about overlaps. */
2652 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
, prefix
)) {
2653 if (prefix_same(range
, prefix
))
2657 prefix
= prefix_new();
2658 prefix_copy(prefix
, range
);
2659 listnode_add(group
->listen_range
[afi
], prefix
);
2661 /* Update passwords for new ranges */
2662 if (group
->conf
->password
)
2663 bgp_md5_set_prefix(prefix
, group
->conf
->password
);
2668 int peer_group_listen_range_del(struct peer_group
*group
, struct prefix
*range
)
2670 struct prefix
*prefix
, prefix2
;
2671 struct listnode
*node
, *nnode
;
2674 char buf
[PREFIX2STR_BUFFER
];
2676 afi
= family2afi(range
->family
);
2678 /* Identify the listen range. */
2679 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
, prefix
)) {
2680 if (prefix_same(range
, prefix
))
2685 return BGP_ERR_DYNAMIC_NEIGHBORS_RANGE_NOT_FOUND
;
2687 prefix2str(prefix
, buf
, sizeof(buf
));
2689 /* Dispose off any dynamic neighbors that exist due to this listen range
2691 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
2692 if (!peer_dynamic_neighbor(peer
))
2695 sockunion2hostprefix(&peer
->su
, &prefix2
);
2696 if (prefix_match(prefix
, &prefix2
)) {
2697 if (bgp_debug_neighbor_events(peer
))
2699 "Deleting dynamic neighbor %s group %s upon "
2700 "delete of listen range %s",
2701 peer
->host
, group
->name
, buf
);
2706 /* Get rid of the listen range */
2707 listnode_delete(group
->listen_range
[afi
], prefix
);
2709 /* Remove passwords for deleted ranges */
2710 if (group
->conf
->password
)
2711 bgp_md5_unset_prefix(prefix
);
2716 /* Bind specified peer to peer group. */
2717 int peer_group_bind(struct bgp
*bgp
, union sockunion
*su
, struct peer
*peer
,
2718 struct peer_group
*group
, as_t
*as
)
2720 int first_member
= 0;
2723 bgp_peer_sort_t ptype
, gtype
;
2725 /* Lookup the peer. */
2727 peer
= peer_lookup(bgp
, su
);
2729 /* The peer exist, bind it to the peer-group */
2731 /* When the peer already belongs to a peer-group, check the
2733 if (peer_group_active(peer
)) {
2735 /* The peer is already bound to the peer-group,
2738 if (strcmp(peer
->group
->name
, group
->name
) == 0)
2741 return BGP_ERR_PEER_GROUP_CANT_CHANGE
;
2744 /* The peer has not specified a remote-as, inherit it from the
2746 if (peer
->as_type
== AS_UNSPECIFIED
) {
2747 peer
->as_type
= group
->conf
->as_type
;
2748 peer
->as
= group
->conf
->as
;
2749 peer
->sort
= group
->conf
->sort
;
2752 ptype
= peer_sort(peer
);
2753 if (!group
->conf
->as
&& ptype
!= BGP_PEER_UNSPECIFIED
) {
2754 gtype
= peer_sort(group
->conf
);
2755 if ((gtype
!= BGP_PEER_INTERNAL
) && (gtype
!= ptype
)) {
2758 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT
;
2761 if (gtype
== BGP_PEER_INTERNAL
)
2765 peer_group2peer_config_copy(group
, peer
);
2767 FOREACH_AFI_SAFI (afi
, safi
) {
2768 if (group
->conf
->afc
[afi
][safi
]) {
2769 peer
->afc
[afi
][safi
] = 1;
2771 if (peer_af_find(peer
, afi
, safi
)
2772 || peer_af_create(peer
, afi
, safi
)) {
2773 peer_group2peer_config_copy_af(
2774 group
, peer
, afi
, safi
);
2776 } else if (peer
->afc
[afi
][safi
])
2777 peer_deactivate(peer
, afi
, safi
);
2781 assert(group
&& peer
->group
== group
);
2783 listnode_delete(bgp
->peer
, peer
);
2785 peer
->group
= group
;
2786 listnode_add_sort(bgp
->peer
, peer
);
2788 peer
= peer_lock(peer
); /* group->peer list reference */
2789 listnode_add(group
->peer
, peer
);
2793 gtype
= peer_sort(group
->conf
);
2794 /* Advertisement-interval reset */
2795 if (!CHECK_FLAG(group
->conf
->flags
,
2796 PEER_FLAG_ROUTEADV
)) {
2797 group
->conf
->v_routeadv
=
2798 (gtype
== BGP_PEER_IBGP
)
2799 ? BGP_DEFAULT_IBGP_ROUTEADV
2800 : BGP_DEFAULT_EBGP_ROUTEADV
;
2803 /* ebgp-multihop reset */
2804 if (gtype
== BGP_PEER_IBGP
)
2805 group
->conf
->ttl
= MAXTTL
;
2807 /* local-as reset */
2808 if (gtype
!= BGP_PEER_EBGP
) {
2809 group
->conf
->change_local_as
= 0;
2810 peer_flag_unset(group
->conf
,
2811 PEER_FLAG_LOCAL_AS
);
2812 peer_flag_unset(group
->conf
,
2813 PEER_FLAG_LOCAL_AS_NO_PREPEND
);
2814 peer_flag_unset(group
->conf
,
2815 PEER_FLAG_LOCAL_AS_REPLACE_AS
);
2819 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
2821 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
2822 peer
->last_reset
= PEER_DOWN_RMAP_BIND
;
2823 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
2824 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
2826 bgp_session_reset(peer
);
2830 /* Create a new peer. */
2832 if ((group
->conf
->as_type
== AS_SPECIFIED
)
2833 && (!group
->conf
->as
)) {
2834 return BGP_ERR_PEER_GROUP_NO_REMOTE_AS
;
2837 peer
= peer_create(su
, NULL
, bgp
, bgp
->as
, group
->conf
->as
,
2838 group
->conf
->as_type
, 0, 0, group
);
2840 peer
= peer_lock(peer
); /* group->peer list reference */
2841 listnode_add(group
->peer
, peer
);
2843 peer_group2peer_config_copy(group
, peer
);
2845 /* If the peer-group is active for this afi/safi then activate
2847 FOREACH_AFI_SAFI (afi
, safi
) {
2848 if (group
->conf
->afc
[afi
][safi
]) {
2849 peer
->afc
[afi
][safi
] = 1;
2850 peer_af_create(peer
, afi
, safi
);
2851 peer_group2peer_config_copy_af(group
, peer
, afi
,
2853 } else if (peer
->afc
[afi
][safi
])
2854 peer_deactivate(peer
, afi
, safi
);
2857 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
2859 /* Set up peer's events and timers. */
2860 if (peer_active(peer
))
2861 bgp_timer_set(peer
);
2867 static int bgp_startup_timer_expire(struct thread
*thread
)
2871 bgp
= THREAD_ARG(thread
);
2872 bgp
->t_startup
= NULL
;
2878 * On shutdown we call the cleanup function which
2879 * does a free of the link list nodes, free up
2880 * the data we are pointing at too.
2882 static void bgp_vrf_string_name_delete(void *data
)
2886 XFREE(MTYPE_TMP
, vname
);
2889 /* BGP instance creation by `router bgp' commands. */
2890 static struct bgp
*bgp_create(as_t
*as
, const char *name
,
2891 enum bgp_instance_type inst_type
)
2897 if ((bgp
= XCALLOC(MTYPE_BGP
, sizeof(struct bgp
))) == NULL
)
2900 if (BGP_DEBUG(zebra
, ZEBRA
)) {
2901 if (inst_type
== BGP_INSTANCE_TYPE_DEFAULT
)
2902 zlog_debug("Creating Default VRF, AS %u", *as
);
2904 zlog_debug("Creating %s %s, AS %u",
2905 (inst_type
== BGP_INSTANCE_TYPE_VRF
)
2911 /* Default the EVPN VRF to the default one */
2912 if (inst_type
== BGP_INSTANCE_TYPE_DEFAULT
&& !bgp_master
.bgp_evpn
) {
2918 bgp
->heuristic_coalesce
= true;
2919 bgp
->inst_type
= inst_type
;
2920 bgp
->vrf_id
= (inst_type
== BGP_INSTANCE_TYPE_DEFAULT
) ? VRF_DEFAULT
2922 bgp
->peer_self
= peer_new(bgp
);
2923 XFREE(MTYPE_BGP_PEER_HOST
, bgp
->peer_self
->host
);
2924 bgp
->peer_self
->host
=
2925 XSTRDUP(MTYPE_BGP_PEER_HOST
, "Static announcement");
2926 XFREE(MTYPE_BGP_PEER_HOST
, bgp
->peer_self
->hostname
);
2927 if (cmd_hostname_get())
2928 bgp
->peer_self
->hostname
=
2929 XSTRDUP(MTYPE_BGP_PEER_HOST
, cmd_hostname_get());
2931 XFREE(MTYPE_BGP_PEER_HOST
, bgp
->peer_self
->domainname
);
2932 if (cmd_domainname_get())
2933 bgp
->peer_self
->domainname
=
2934 XSTRDUP(MTYPE_BGP_PEER_HOST
, cmd_domainname_get());
2935 bgp
->peer
= list_new();
2936 bgp
->peer
->cmp
= (int (*)(void *, void *))peer_cmp
;
2937 bgp
->peerhash
= hash_create(peer_hash_key_make
, peer_hash_same
,
2939 bgp
->peerhash
->max_size
= BGP_PEER_MAX_HASH_SIZE
;
2941 bgp
->group
= list_new();
2942 bgp
->group
->cmp
= (int (*)(void *, void *))peer_group_cmp
;
2944 FOREACH_AFI_SAFI (afi
, safi
) {
2945 bgp
->route
[afi
][safi
] = bgp_table_init(bgp
, afi
, safi
);
2946 bgp
->aggregate
[afi
][safi
] = bgp_table_init(bgp
, afi
, safi
);
2947 bgp
->rib
[afi
][safi
] = bgp_table_init(bgp
, afi
, safi
);
2949 /* Enable maximum-paths */
2950 bgp_maximum_paths_set(bgp
, afi
, safi
, BGP_PEER_EBGP
,
2952 bgp_maximum_paths_set(bgp
, afi
, safi
, BGP_PEER_IBGP
,
2954 /* Initialize graceful restart info */
2955 bgp
->gr_info
[afi
][safi
].eor_required
= 0;
2956 bgp
->gr_info
[afi
][safi
].eor_received
= 0;
2957 bgp
->gr_info
[afi
][safi
].t_select_deferral
= NULL
;
2958 bgp
->gr_info
[afi
][safi
].t_route_select
= NULL
;
2959 bgp
->gr_info
[afi
][safi
].route_list
= list_new();
2962 bgp
->v_update_delay
= BGP_UPDATE_DELAY_DEF
;
2963 bgp
->default_local_pref
= BGP_DEFAULT_LOCAL_PREF
;
2964 bgp
->default_subgroup_pkt_queue_max
=
2965 BGP_DEFAULT_SUBGROUP_PKT_QUEUE_MAX
;
2966 bgp_timers_unset(bgp
);
2967 bgp
->restart_time
= BGP_DEFAULT_RESTART_TIME
;
2968 bgp
->stalepath_time
= BGP_DEFAULT_STALEPATH_TIME
;
2969 bgp
->select_defer_time
= BGP_DEFAULT_SELECT_DEFERRAL_TIME
;
2970 bgp
->rib_stale_time
= BGP_DEFAULT_RIB_STALE_TIME
;
2971 bgp
->dynamic_neighbors_limit
= BGP_DYNAMIC_NEIGHBORS_LIMIT_DEFAULT
;
2972 bgp
->dynamic_neighbors_count
= 0;
2973 bgp
->lb_ref_bw
= BGP_LINK_BW_REF_BW
;
2974 bgp
->lb_handling
= BGP_LINK_BW_ECMP
;
2975 bgp
->ebgp_requires_policy
= DEFAULT_EBGP_POLICY_DISABLED
;
2976 bgp
->reject_as_sets
= BGP_REJECT_AS_SETS_DISABLED
;
2977 bgp_addpath_init_bgp_data(&bgp
->tx_addpath
);
2982 if (inst_type
!= BGP_INSTANCE_TYPE_VRF
) {
2983 bgp
->rfapi
= bgp_rfapi_new(bgp
);
2985 assert(bgp
->rfapi_cfg
);
2987 #endif /* ENABLE_BGP_VNC */
2989 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
2990 bgp
->vpn_policy
[afi
].bgp
= bgp
;
2991 bgp
->vpn_policy
[afi
].afi
= afi
;
2992 bgp
->vpn_policy
[afi
].tovpn_label
= MPLS_LABEL_NONE
;
2993 bgp
->vpn_policy
[afi
].tovpn_zebra_vrf_label_last_sent
=
2996 bgp
->vpn_policy
[afi
].import_vrf
= list_new();
2997 bgp
->vpn_policy
[afi
].import_vrf
->del
=
2998 bgp_vrf_string_name_delete
;
2999 bgp
->vpn_policy
[afi
].export_vrf
= list_new();
3000 bgp
->vpn_policy
[afi
].export_vrf
->del
=
3001 bgp_vrf_string_name_delete
;
3004 bgp
->name
= XSTRDUP(MTYPE_BGP
, name
);
3006 thread_add_timer(bm
->master
, bgp_startup_timer_expire
, bgp
,
3007 bgp
->restart_time
, &bgp
->t_startup
);
3009 /* printable name we can use in debug messages */
3010 if (inst_type
== BGP_INSTANCE_TYPE_DEFAULT
) {
3011 bgp
->name_pretty
= XSTRDUP(MTYPE_BGP
, "VRF default");
3021 len
= 4 + 1 + strlen(n
) + 1; /* "view foo\0" */
3023 bgp
->name_pretty
= XCALLOC(MTYPE_BGP
, len
);
3024 snprintf(bgp
->name_pretty
, len
, "%s %s",
3025 (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
)
3031 atomic_store_explicit(&bgp
->wpkt_quanta
, BGP_WRITE_PACKET_MAX
,
3032 memory_order_relaxed
);
3033 atomic_store_explicit(&bgp
->rpkt_quanta
, BGP_READ_PACKET_MAX
,
3034 memory_order_relaxed
);
3035 bgp
->coalesce_time
= BGP_DEFAULT_SUBGROUP_COALESCE_TIME
;
3039 update_bgp_group_init(bgp
);
3041 /* assign a unique rd id for auto derivation of vrf's RD */
3042 bf_assign_index(bm
->rd_idspace
, bgp
->vrf_rd_id
);
3044 bgp
->evpn_info
= XCALLOC(MTYPE_BGP_EVPN_INFO
,
3045 sizeof(struct bgp_evpn_info
));
3050 /*initilize global GR FSM */
3051 bgp_global_gr_init(bgp
);
3055 /* Return the "default VRF" instance of BGP. */
3056 struct bgp
*bgp_get_default(void)
3059 struct listnode
*node
, *nnode
;
3061 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
))
3062 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_DEFAULT
)
3067 /* Lookup BGP entry. */
3068 struct bgp
*bgp_lookup(as_t as
, const char *name
)
3071 struct listnode
*node
, *nnode
;
3073 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
))
3075 && ((bgp
->name
== NULL
&& name
== NULL
)
3076 || (bgp
->name
&& name
&& strcmp(bgp
->name
, name
) == 0)))
3081 /* Lookup BGP structure by view name. */
3082 struct bgp
*bgp_lookup_by_name(const char *name
)
3085 struct listnode
*node
, *nnode
;
3087 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
))
3088 if ((bgp
->name
== NULL
&& name
== NULL
)
3089 || (bgp
->name
&& name
&& strcmp(bgp
->name
, name
) == 0))
3094 /* Lookup BGP instance based on VRF id. */
3095 /* Note: Only to be used for incoming messages from Zebra. */
3096 struct bgp
*bgp_lookup_by_vrf_id(vrf_id_t vrf_id
)
3100 /* Lookup VRF (in tree) and follow link. */
3101 vrf
= vrf_lookup_by_id(vrf_id
);
3104 return (vrf
->info
) ? (struct bgp
*)vrf
->info
: NULL
;
3107 /* Sets the BGP instance where EVPN is enabled */
3108 void bgp_set_evpn(struct bgp
*bgp
)
3110 if (bm
->bgp_evpn
== bgp
)
3113 /* First, release the reference count we hold on the instance */
3115 bgp_unlock(bm
->bgp_evpn
);
3119 /* Increase the reference count on this new VRF */
3121 bgp_lock(bm
->bgp_evpn
);
3124 /* Returns the BGP instance where EVPN is enabled, if any */
3125 struct bgp
*bgp_get_evpn(void)
3127 return bm
->bgp_evpn
;
3130 /* handle socket creation or deletion, if necessary
3131 * this is called for all new BGP instances
3133 int bgp_handle_socket(struct bgp
*bgp
, struct vrf
*vrf
, vrf_id_t old_vrf_id
,
3138 /* Create BGP server socket, if listen mode not disabled */
3139 if (!bgp
|| bgp_option_check(BGP_OPT_NO_LISTEN
))
3141 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
) {
3143 * suppress vrf socket
3146 bgp_close_vrf_socket(bgp
);
3150 return BGP_ERR_INVALID_VALUE
;
3152 * if vrf_id did not change
3154 if (vrf
->vrf_id
== old_vrf_id
)
3156 if (old_vrf_id
!= VRF_UNKNOWN
) {
3157 /* look for old socket. close it. */
3158 bgp_close_vrf_socket(bgp
);
3160 /* if backend is not yet identified ( VRF_UNKNOWN) then
3161 * creation will be done later
3163 if (vrf
->vrf_id
== VRF_UNKNOWN
)
3165 ret
= bgp_socket(bgp
, bm
->port
, bm
->address
);
3167 return BGP_ERR_INVALID_VALUE
;
3170 return bgp_check_main_socket(create
, bgp
);
3173 /* Called from VTY commands. */
3174 int bgp_get(struct bgp
**bgp_val
, as_t
*as
, const char *name
,
3175 enum bgp_instance_type inst_type
)
3178 struct vrf
*vrf
= NULL
;
3180 /* Multiple instance check. */
3182 bgp
= bgp_lookup_by_name(name
);
3184 bgp
= bgp_get_default();
3186 /* Already exists. */
3188 if (bgp
->as
!= *as
) {
3190 return BGP_ERR_INSTANCE_MISMATCH
;
3192 if (bgp
->inst_type
!= inst_type
)
3193 return BGP_ERR_INSTANCE_MISMATCH
;
3198 bgp
= bgp_create(as
, name
, inst_type
);
3199 if (bgp_option_check(BGP_OPT_NO_ZEBRA
) && name
)
3200 bgp
->vrf_id
= vrf_generate_id();
3201 bgp_router_id_set(bgp
, &bgp
->router_id_zebra
, true);
3202 bgp_address_init(bgp
);
3203 bgp_tip_hash_init(bgp
);
3207 bgp
->t_rmap_def_originate_eval
= NULL
;
3209 /* If Default instance or VRF, link to the VRF structure, if present. */
3210 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_DEFAULT
3211 || bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
) {
3212 vrf
= bgp_vrf_lookup_by_instance_type(bgp
);
3214 bgp_vrf_link(bgp
, vrf
);
3216 /* BGP server socket already processed if BGP instance
3217 * already part of the list
3219 bgp_handle_socket(bgp
, vrf
, VRF_UNKNOWN
, true);
3220 listnode_add(bm
->bgp
, bgp
);
3222 if (IS_BGP_INST_KNOWN_TO_ZEBRA(bgp
)) {
3223 if (BGP_DEBUG(zebra
, ZEBRA
))
3224 zlog_debug("%s: Registering BGP instance %s to zebra",
3226 bgp_zebra_instance_register(bgp
);
3233 * Make BGP instance "up". Applies only to VRFs (non-default) and
3234 * implies the VRF has been learnt from Zebra.
3236 void bgp_instance_up(struct bgp
*bgp
)
3239 struct listnode
*node
, *next
;
3241 /* Register with zebra. */
3242 bgp_zebra_instance_register(bgp
);
3244 /* Kick off any peers that may have been configured. */
3245 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
)) {
3246 if (!BGP_PEER_START_SUPPRESSED(peer
))
3247 BGP_EVENT_ADD(peer
, BGP_Start
);
3250 /* Process any networks that have been configured. */
3251 bgp_static_add(bgp
);
3255 * Make BGP instance "down". Applies only to VRFs (non-default) and
3256 * implies the VRF has been deleted by Zebra.
3258 void bgp_instance_down(struct bgp
*bgp
)
3261 struct listnode
*node
;
3262 struct listnode
*next
;
3265 if (bgp
->t_rmap_def_originate_eval
) {
3266 BGP_TIMER_OFF(bgp
->t_rmap_def_originate_eval
);
3267 bgp_unlock(bgp
); /* TODO - This timer is started with a lock -
3271 /* Bring down peers, so corresponding routes are purged. */
3272 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
)) {
3273 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
3274 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3275 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
);
3277 bgp_session_reset(peer
);
3280 /* Purge network and redistributed routes. */
3281 bgp_purge_static_redist_routes(bgp
);
3283 /* Cleanup registered nexthops (flags) */
3284 bgp_cleanup_nexthops(bgp
);
3287 /* Delete BGP instance. */
3288 int bgp_delete(struct bgp
*bgp
)
3291 struct peer_group
*group
;
3292 struct listnode
*node
, *next
;
3297 struct graceful_restart_info
*gr_info
;
3301 hook_call(bgp_inst_delete
, bgp
);
3303 THREAD_OFF(bgp
->t_startup
);
3304 THREAD_OFF(bgp
->t_maxmed_onstartup
);
3305 THREAD_OFF(bgp
->t_update_delay
);
3306 THREAD_OFF(bgp
->t_establish_wait
);
3308 /* Set flag indicating bgp instance delete in progress */
3309 SET_FLAG(bgp
->flags
, BGP_FLAG_DELETE_IN_PROGRESS
);
3311 /* Delete the graceful restart info */
3312 FOREACH_AFI_SAFI (afi
, safi
) {
3313 gr_info
= &bgp
->gr_info
[afi
][safi
];
3317 BGP_TIMER_OFF(gr_info
->t_select_deferral
);
3318 BGP_TIMER_OFF(gr_info
->t_route_select
);
3319 if (gr_info
->route_list
)
3320 list_delete(&gr_info
->route_list
);
3323 if (BGP_DEBUG(zebra
, ZEBRA
)) {
3324 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_DEFAULT
)
3325 zlog_debug("Deleting Default VRF");
3327 zlog_debug("Deleting %s %s",
3328 (bgp
->inst_type
== BGP_INSTANCE_TYPE_VRF
)
3334 /* unmap from RT list */
3335 bgp_evpn_vrf_delete(bgp
);
3337 /* unmap bgp vrf label */
3338 vpn_leak_zebra_vrf_label_withdraw(bgp
, AFI_IP
);
3339 vpn_leak_zebra_vrf_label_withdraw(bgp
, AFI_IP6
);
3342 if (bgp
->t_rmap_def_originate_eval
) {
3343 BGP_TIMER_OFF(bgp
->t_rmap_def_originate_eval
);
3344 bgp_unlock(bgp
); /* TODO - This timer is started with a lock -
3348 /* Inform peers we're going down. */
3349 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
)) {
3350 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
3351 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3352 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
);
3355 /* Delete static routes (networks). */
3356 bgp_static_delete(bgp
);
3358 /* Unset redistribution. */
3359 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++)
3360 for (i
= 0; i
< ZEBRA_ROUTE_MAX
; i
++)
3361 if (i
!= ZEBRA_ROUTE_BGP
)
3362 bgp_redistribute_unset(bgp
, afi
, i
, 0);
3364 /* Free peers and peer-groups. */
3365 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, next
, group
))
3366 peer_group_delete(group
);
3368 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, next
, peer
))
3371 if (bgp
->peer_self
) {
3372 peer_delete(bgp
->peer_self
);
3373 bgp
->peer_self
= NULL
;
3376 update_bgp_group_free(bgp
);
3378 /* TODO - Other memory may need to be freed - e.g., NHT */
3383 bgp_cleanup_routes(bgp
);
3385 for (afi
= 0; afi
< AFI_MAX
; ++afi
) {
3386 if (!bgp
->vpn_policy
[afi
].import_redirect_rtlist
)
3389 &bgp
->vpn_policy
[afi
]
3390 .import_redirect_rtlist
);
3391 bgp
->vpn_policy
[afi
].import_redirect_rtlist
= NULL
;
3394 /* Deregister from Zebra, if needed */
3395 if (IS_BGP_INST_KNOWN_TO_ZEBRA(bgp
)) {
3396 if (BGP_DEBUG(zebra
, ZEBRA
))
3398 "%s: deregistering this bgp %s instance from zebra",
3399 __func__
, bgp
->name
);
3400 bgp_zebra_instance_deregister(bgp
);
3403 /* Remove visibility via the master list - there may however still be
3404 * routes to be processed still referencing the struct bgp.
3406 listnode_delete(bm
->bgp
, bgp
);
3408 /* Free interfaces in this instance. */
3411 vrf
= bgp_vrf_lookup_by_instance_type(bgp
);
3412 bgp_handle_socket(bgp
, vrf
, VRF_UNKNOWN
, false);
3414 bgp_vrf_unlink(bgp
, vrf
);
3416 /* Update EVPN VRF pointer */
3417 if (bm
->bgp_evpn
== bgp
) {
3418 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_DEFAULT
)
3421 bgp_set_evpn(bgp_get_default());
3424 thread_master_free_unused(bm
->master
);
3425 bgp_unlock(bgp
); /* initial reference */
3430 void bgp_free(struct bgp
*bgp
)
3434 struct bgp_table
*table
;
3435 struct bgp_node
*rn
;
3436 struct bgp_rmap
*rmap
;
3440 list_delete(&bgp
->group
);
3441 list_delete(&bgp
->peer
);
3443 if (bgp
->peerhash
) {
3444 hash_free(bgp
->peerhash
);
3445 bgp
->peerhash
= NULL
;
3448 FOREACH_AFI_SAFI (afi
, safi
) {
3449 /* Special handling for 2-level routing tables. */
3450 if (safi
== SAFI_MPLS_VPN
|| safi
== SAFI_ENCAP
3451 || safi
== SAFI_EVPN
) {
3452 for (rn
= bgp_table_top(bgp
->rib
[afi
][safi
]); rn
;
3453 rn
= bgp_route_next(rn
)) {
3454 table
= bgp_node_get_bgp_table_info(rn
);
3455 bgp_table_finish(&table
);
3458 if (bgp
->route
[afi
][safi
])
3459 bgp_table_finish(&bgp
->route
[afi
][safi
]);
3460 if (bgp
->aggregate
[afi
][safi
])
3461 bgp_table_finish(&bgp
->aggregate
[afi
][safi
]);
3462 if (bgp
->rib
[afi
][safi
])
3463 bgp_table_finish(&bgp
->rib
[afi
][safi
]);
3464 rmap
= &bgp
->table_map
[afi
][safi
];
3465 XFREE(MTYPE_ROUTE_MAP_NAME
, rmap
->name
);
3468 bgp_scan_finish(bgp
);
3469 bgp_address_destroy(bgp
);
3470 bgp_tip_hash_destroy(bgp
);
3472 /* release the auto RD id */
3473 bf_release_index(bm
->rd_idspace
, bgp
->vrf_rd_id
);
3475 bgp_evpn_cleanup(bgp
);
3476 bgp_pbr_cleanup(bgp
);
3477 XFREE(MTYPE_BGP_EVPN_INFO
, bgp
->evpn_info
);
3479 for (afi
= AFI_IP
; afi
< AFI_MAX
; afi
++) {
3480 vpn_policy_direction_t dir
;
3482 if (bgp
->vpn_policy
[afi
].import_vrf
)
3483 list_delete(&bgp
->vpn_policy
[afi
].import_vrf
);
3484 if (bgp
->vpn_policy
[afi
].export_vrf
)
3485 list_delete(&bgp
->vpn_policy
[afi
].export_vrf
);
3487 dir
= BGP_VPN_POLICY_DIR_FROMVPN
;
3488 if (bgp
->vpn_policy
[afi
].rtlist
[dir
])
3489 ecommunity_free(&bgp
->vpn_policy
[afi
].rtlist
[dir
]);
3490 dir
= BGP_VPN_POLICY_DIR_TOVPN
;
3491 if (bgp
->vpn_policy
[afi
].rtlist
[dir
])
3492 ecommunity_free(&bgp
->vpn_policy
[afi
].rtlist
[dir
]);
3495 XFREE(MTYPE_BGP
, bgp
->name
);
3496 XFREE(MTYPE_BGP
, bgp
->name_pretty
);
3498 XFREE(MTYPE_BGP
, bgp
);
3501 struct peer
*peer_lookup_by_conf_if(struct bgp
*bgp
, const char *conf_if
)
3504 struct listnode
*node
, *nnode
;
3510 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3511 if (peer
->conf_if
&& !strcmp(peer
->conf_if
, conf_if
)
3512 && !CHECK_FLAG(peer
->sflags
,
3513 PEER_STATUS_ACCEPT_PEER
))
3515 } else if (bm
->bgp
!= NULL
) {
3516 struct listnode
*bgpnode
, *nbgpnode
;
3518 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
))
3519 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3521 && !strcmp(peer
->conf_if
, conf_if
)
3522 && !CHECK_FLAG(peer
->sflags
,
3523 PEER_STATUS_ACCEPT_PEER
))
3529 struct peer
*peer_lookup_by_hostname(struct bgp
*bgp
, const char *hostname
)
3532 struct listnode
*node
, *nnode
;
3538 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3539 if (peer
->hostname
&& !strcmp(peer
->hostname
, hostname
)
3540 && !CHECK_FLAG(peer
->sflags
,
3541 PEER_STATUS_ACCEPT_PEER
))
3543 } else if (bm
->bgp
!= NULL
) {
3544 struct listnode
*bgpnode
, *nbgpnode
;
3546 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
))
3547 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
3549 && !strcmp(peer
->hostname
, hostname
)
3550 && !CHECK_FLAG(peer
->sflags
,
3551 PEER_STATUS_ACCEPT_PEER
))
3557 struct peer
*peer_lookup(struct bgp
*bgp
, union sockunion
*su
)
3559 struct peer
*peer
= NULL
;
3560 struct peer tmp_peer
;
3562 memset(&tmp_peer
, 0, sizeof(struct peer
));
3565 * We do not want to find the doppelganger peer so search for the peer
3567 * the hash that has PEER_FLAG_CONFIG_NODE
3569 SET_FLAG(tmp_peer
.flags
, PEER_FLAG_CONFIG_NODE
);
3574 peer
= hash_lookup(bgp
->peerhash
, &tmp_peer
);
3575 } else if (bm
->bgp
!= NULL
) {
3576 struct listnode
*bgpnode
, *nbgpnode
;
3578 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
)) {
3579 peer
= hash_lookup(bgp
->peerhash
, &tmp_peer
);
3588 struct peer
*peer_create_bind_dynamic_neighbor(struct bgp
*bgp
,
3589 union sockunion
*su
,
3590 struct peer_group
*group
)
3596 /* Create peer first; we've already checked group config is valid. */
3597 peer
= peer_create(su
, NULL
, bgp
, bgp
->as
, group
->conf
->as
,
3598 group
->conf
->as_type
, 0, 0, group
);
3603 peer
= peer_lock(peer
);
3604 listnode_add(group
->peer
, peer
);
3606 peer_group2peer_config_copy(group
, peer
);
3609 * Bind peer for all AFs configured for the group. We don't call
3610 * peer_group_bind as that is sub-optimal and does some stuff we don't
3613 FOREACH_AFI_SAFI (afi
, safi
) {
3614 if (!group
->conf
->afc
[afi
][safi
])
3616 peer
->afc
[afi
][safi
] = 1;
3618 if (!peer_af_find(peer
, afi
, safi
))
3619 peer_af_create(peer
, afi
, safi
);
3621 peer_group2peer_config_copy_af(group
, peer
, afi
, safi
);
3624 /* Mark as dynamic, but also as a "config node" for other things to
3626 SET_FLAG(peer
->flags
, PEER_FLAG_DYNAMIC_NEIGHBOR
);
3627 SET_FLAG(peer
->flags
, PEER_FLAG_CONFIG_NODE
);
3633 peer_group_lookup_dynamic_neighbor_range(struct peer_group
*group
,
3634 struct prefix
*prefix
)
3636 struct listnode
*node
, *nnode
;
3637 struct prefix
*range
;
3640 afi
= family2afi(prefix
->family
);
3642 if (group
->listen_range
[afi
])
3643 for (ALL_LIST_ELEMENTS(group
->listen_range
[afi
], node
, nnode
,
3645 if (prefix_match(range
, prefix
))
3652 peer_group_lookup_dynamic_neighbor(struct bgp
*bgp
, struct prefix
*prefix
,
3653 struct prefix
**listen_range
)
3655 struct prefix
*range
= NULL
;
3656 struct peer_group
*group
= NULL
;
3657 struct listnode
*node
, *nnode
;
3659 *listen_range
= NULL
;
3661 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
))
3662 if ((range
= peer_group_lookup_dynamic_neighbor_range(
3665 } else if (bm
->bgp
!= NULL
) {
3666 struct listnode
*bgpnode
, *nbgpnode
;
3668 for (ALL_LIST_ELEMENTS(bm
->bgp
, bgpnode
, nbgpnode
, bgp
))
3669 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
))
3670 if ((range
= peer_group_lookup_dynamic_neighbor_range(
3676 *listen_range
= range
;
3677 return (group
&& range
) ? group
: NULL
;
3680 struct peer
*peer_lookup_dynamic_neighbor(struct bgp
*bgp
, union sockunion
*su
)
3682 struct peer_group
*group
;
3685 struct prefix prefix
;
3686 struct prefix
*listen_range
;
3688 char buf
[PREFIX2STR_BUFFER
];
3689 char buf1
[PREFIX2STR_BUFFER
];
3691 sockunion2hostprefix(su
, &prefix
);
3693 /* See if incoming connection matches a configured listen range. */
3694 group
= peer_group_lookup_dynamic_neighbor(bgp
, &prefix
, &listen_range
);
3705 prefix2str(&prefix
, buf
, sizeof(buf
));
3706 prefix2str(listen_range
, buf1
, sizeof(buf1
));
3708 if (bgp_debug_neighbor_events(NULL
))
3710 "Dynamic Neighbor %s matches group %s listen range %s",
3711 buf
, group
->name
, buf1
);
3713 /* Are we within the listen limit? */
3714 dncount
= gbgp
->dynamic_neighbors_count
;
3716 if (dncount
>= gbgp
->dynamic_neighbors_limit
) {
3717 if (bgp_debug_neighbor_events(NULL
))
3718 zlog_debug("Dynamic Neighbor %s rejected - at limit %d",
3719 inet_sutop(su
, buf
),
3720 gbgp
->dynamic_neighbors_limit
);
3724 /* Ensure group is not disabled. */
3725 if (CHECK_FLAG(group
->conf
->flags
, PEER_FLAG_SHUTDOWN
)) {
3726 if (bgp_debug_neighbor_events(NULL
))
3728 "Dynamic Neighbor %s rejected - group %s disabled",
3733 /* Check that at least one AF is activated for the group. */
3734 if (!peer_group_af_configured(group
)) {
3735 if (bgp_debug_neighbor_events(NULL
))
3737 "Dynamic Neighbor %s rejected - no AF activated for group %s",
3742 /* Create dynamic peer and bind to associated group. */
3743 peer
= peer_create_bind_dynamic_neighbor(gbgp
, su
, group
);
3746 gbgp
->dynamic_neighbors_count
= ++dncount
;
3748 if (bgp_debug_neighbor_events(peer
))
3749 zlog_debug("%s Dynamic Neighbor added, group %s count %d",
3750 peer
->host
, group
->name
, dncount
);
3755 static void peer_drop_dynamic_neighbor(struct peer
*peer
)
3758 if (peer
->group
->bgp
) {
3759 dncount
= peer
->group
->bgp
->dynamic_neighbors_count
;
3761 peer
->group
->bgp
->dynamic_neighbors_count
= --dncount
;
3763 if (bgp_debug_neighbor_events(peer
))
3764 zlog_debug("%s dropped from group %s, count %d", peer
->host
,
3765 peer
->group
->name
, dncount
);
3768 /* If peer is configured at least one address family return 1. */
3769 bool peer_active(struct peer
*peer
)
3771 if (BGP_PEER_SU_UNSPEC(peer
))
3773 if (peer
->afc
[AFI_IP
][SAFI_UNICAST
] || peer
->afc
[AFI_IP
][SAFI_MULTICAST
]
3774 || peer
->afc
[AFI_IP
][SAFI_LABELED_UNICAST
]
3775 || peer
->afc
[AFI_IP
][SAFI_MPLS_VPN
] || peer
->afc
[AFI_IP
][SAFI_ENCAP
]
3776 || peer
->afc
[AFI_IP
][SAFI_FLOWSPEC
]
3777 || peer
->afc
[AFI_IP6
][SAFI_UNICAST
]
3778 || peer
->afc
[AFI_IP6
][SAFI_MULTICAST
]
3779 || peer
->afc
[AFI_IP6
][SAFI_LABELED_UNICAST
]
3780 || peer
->afc
[AFI_IP6
][SAFI_MPLS_VPN
]
3781 || peer
->afc
[AFI_IP6
][SAFI_ENCAP
]
3782 || peer
->afc
[AFI_IP6
][SAFI_FLOWSPEC
]
3783 || peer
->afc
[AFI_L2VPN
][SAFI_EVPN
])
3788 /* If peer is negotiated at least one address family return 1. */
3789 bool peer_active_nego(struct peer
*peer
)
3791 if (peer
->afc_nego
[AFI_IP
][SAFI_UNICAST
]
3792 || peer
->afc_nego
[AFI_IP
][SAFI_MULTICAST
]
3793 || peer
->afc_nego
[AFI_IP
][SAFI_LABELED_UNICAST
]
3794 || peer
->afc_nego
[AFI_IP
][SAFI_MPLS_VPN
]
3795 || peer
->afc_nego
[AFI_IP
][SAFI_ENCAP
]
3796 || peer
->afc_nego
[AFI_IP
][SAFI_FLOWSPEC
]
3797 || peer
->afc_nego
[AFI_IP6
][SAFI_UNICAST
]
3798 || peer
->afc_nego
[AFI_IP6
][SAFI_MULTICAST
]
3799 || peer
->afc_nego
[AFI_IP6
][SAFI_LABELED_UNICAST
]
3800 || peer
->afc_nego
[AFI_IP6
][SAFI_MPLS_VPN
]
3801 || peer
->afc_nego
[AFI_IP6
][SAFI_ENCAP
]
3802 || peer
->afc_nego
[AFI_IP6
][SAFI_FLOWSPEC
]
3803 || peer
->afc_nego
[AFI_L2VPN
][SAFI_EVPN
])
3808 void peer_change_action(struct peer
*peer
, afi_t afi
, safi_t safi
,
3809 enum peer_change_type type
)
3811 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
3814 if (peer
->status
!= Established
)
3817 if (type
== peer_change_reset
) {
3818 /* If we're resetting session, we've to delete both peer struct
3820 if ((peer
->doppelganger
)
3821 && (peer
->doppelganger
->status
!= Deleted
)
3822 && (!CHECK_FLAG(peer
->doppelganger
->flags
,
3823 PEER_FLAG_CONFIG_NODE
)))
3824 peer_delete(peer
->doppelganger
);
3826 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3827 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
3828 } else if (type
== peer_change_reset_in
) {
3829 if (CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_OLD_RCV
)
3830 || CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_NEW_RCV
))
3831 bgp_route_refresh_send(peer
, afi
, safi
, 0, 0, 0);
3833 if ((peer
->doppelganger
)
3834 && (peer
->doppelganger
->status
!= Deleted
)
3835 && (!CHECK_FLAG(peer
->doppelganger
->flags
,
3836 PEER_FLAG_CONFIG_NODE
)))
3837 peer_delete(peer
->doppelganger
);
3839 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
3840 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
3842 } else if (type
== peer_change_reset_out
) {
3843 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
3844 bgp_announce_route(peer
, afi
, safi
);
3848 struct peer_flag_action
{
3852 /* This flag can be set for peer-group member. */
3853 uint8_t not_for_member
;
3855 /* Action when the flag is changed. */
3856 enum peer_change_type type
;
3859 static const struct peer_flag_action peer_flag_action_list
[] = {
3860 {PEER_FLAG_PASSIVE
, 0, peer_change_reset
},
3861 {PEER_FLAG_SHUTDOWN
, 0, peer_change_reset
},
3862 {PEER_FLAG_DONT_CAPABILITY
, 0, peer_change_none
},
3863 {PEER_FLAG_OVERRIDE_CAPABILITY
, 0, peer_change_none
},
3864 {PEER_FLAG_STRICT_CAP_MATCH
, 0, peer_change_none
},
3865 {PEER_FLAG_DYNAMIC_CAPABILITY
, 0, peer_change_reset
},
3866 {PEER_FLAG_DISABLE_CONNECTED_CHECK
, 0, peer_change_reset
},
3867 {PEER_FLAG_CAPABILITY_ENHE
, 0, peer_change_reset
},
3868 {PEER_FLAG_ENFORCE_FIRST_AS
, 0, peer_change_reset_in
},
3869 {PEER_FLAG_IFPEER_V6ONLY
, 0, peer_change_reset
},
3870 {PEER_FLAG_ROUTEADV
, 0, peer_change_none
},
3871 {PEER_FLAG_TIMER
, 0, peer_change_none
},
3872 {PEER_FLAG_TIMER_CONNECT
, 0, peer_change_none
},
3873 {PEER_FLAG_PASSWORD
, 0, peer_change_none
},
3874 {PEER_FLAG_LOCAL_AS
, 0, peer_change_none
},
3875 {PEER_FLAG_LOCAL_AS_NO_PREPEND
, 0, peer_change_none
},
3876 {PEER_FLAG_LOCAL_AS_REPLACE_AS
, 0, peer_change_none
},
3877 {PEER_FLAG_UPDATE_SOURCE
, 0, peer_change_none
},
3880 static const struct peer_flag_action peer_af_flag_action_list
[] = {
3881 {PEER_FLAG_SEND_COMMUNITY
, 1, peer_change_reset_out
},
3882 {PEER_FLAG_SEND_EXT_COMMUNITY
, 1, peer_change_reset_out
},
3883 {PEER_FLAG_SEND_LARGE_COMMUNITY
, 1, peer_change_reset_out
},
3884 {PEER_FLAG_NEXTHOP_SELF
, 1, peer_change_reset_out
},
3885 {PEER_FLAG_REFLECTOR_CLIENT
, 1, peer_change_reset
},
3886 {PEER_FLAG_RSERVER_CLIENT
, 1, peer_change_reset
},
3887 {PEER_FLAG_SOFT_RECONFIG
, 0, peer_change_reset_in
},
3888 {PEER_FLAG_AS_PATH_UNCHANGED
, 1, peer_change_reset_out
},
3889 {PEER_FLAG_NEXTHOP_UNCHANGED
, 1, peer_change_reset_out
},
3890 {PEER_FLAG_MED_UNCHANGED
, 1, peer_change_reset_out
},
3891 {PEER_FLAG_DEFAULT_ORIGINATE
, 0, peer_change_none
},
3892 {PEER_FLAG_REMOVE_PRIVATE_AS
, 1, peer_change_reset_out
},
3893 {PEER_FLAG_ALLOWAS_IN
, 0, peer_change_reset_in
},
3894 {PEER_FLAG_ALLOWAS_IN_ORIGIN
, 0, peer_change_reset_in
},
3895 {PEER_FLAG_ORF_PREFIX_SM
, 1, peer_change_reset
},
3896 {PEER_FLAG_ORF_PREFIX_RM
, 1, peer_change_reset
},
3897 {PEER_FLAG_MAX_PREFIX
, 0, peer_change_none
},
3898 {PEER_FLAG_MAX_PREFIX_WARNING
, 0, peer_change_none
},
3899 {PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED
, 0, peer_change_reset_out
},
3900 {PEER_FLAG_FORCE_NEXTHOP_SELF
, 1, peer_change_reset_out
},
3901 {PEER_FLAG_REMOVE_PRIVATE_AS_ALL
, 1, peer_change_reset_out
},
3902 {PEER_FLAG_REMOVE_PRIVATE_AS_REPLACE
, 1, peer_change_reset_out
},
3903 {PEER_FLAG_AS_OVERRIDE
, 1, peer_change_reset_out
},
3904 {PEER_FLAG_REMOVE_PRIVATE_AS_ALL_REPLACE
, 1, peer_change_reset_out
},
3905 {PEER_FLAG_WEIGHT
, 0, peer_change_reset_in
},
3908 /* Proper action set. */
3909 static int peer_flag_action_set(const struct peer_flag_action
*action_list
,
3910 int size
, struct peer_flag_action
*action
,
3917 const struct peer_flag_action
*match
= NULL
;
3919 /* Check peer's frag action. */
3920 for (i
= 0; i
< size
; i
++) {
3921 match
= &action_list
[i
];
3923 if (match
->flag
== 0)
3926 if (match
->flag
& flag
) {
3929 if (match
->type
== peer_change_reset_in
)
3931 if (match
->type
== peer_change_reset_out
)
3933 if (match
->type
== peer_change_reset
) {
3937 if (match
->not_for_member
)
3938 action
->not_for_member
= 1;
3942 /* Set peer clear type. */
3943 if (reset_in
&& reset_out
)
3944 action
->type
= peer_change_reset
;
3946 action
->type
= peer_change_reset_in
;
3948 action
->type
= peer_change_reset_out
;
3950 action
->type
= peer_change_none
;
3955 static void peer_flag_modify_action(struct peer
*peer
, uint32_t flag
)
3957 if (flag
== PEER_FLAG_SHUTDOWN
) {
3958 if (CHECK_FLAG(peer
->flags
, flag
)) {
3959 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
))
3960 peer_nsf_stop(peer
);
3962 UNSET_FLAG(peer
->sflags
, PEER_STATUS_PREFIX_OVERFLOW
);
3963 if (peer
->t_pmax_restart
) {
3964 BGP_TIMER_OFF(peer
->t_pmax_restart
);
3965 if (bgp_debug_neighbor_events(peer
))
3967 "%s Maximum-prefix restart timer canceled",
3971 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_NSF_WAIT
))
3972 peer_nsf_stop(peer
);
3974 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
3975 char *msg
= peer
->tx_shutdown_message
;
3978 if (!msg
&& peer_group_active(peer
))
3979 msg
= peer
->group
->conf
3980 ->tx_shutdown_message
;
3981 msglen
= msg
? strlen(msg
) : 0;
3986 uint8_t msgbuf
[129];
3989 memcpy(msgbuf
+ 1, msg
, msglen
);
3991 bgp_notify_send_with_data(
3992 peer
, BGP_NOTIFY_CEASE
,
3993 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
,
3994 msgbuf
, msglen
+ 1);
3997 peer
, BGP_NOTIFY_CEASE
,
3998 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN
);
4000 bgp_session_reset(peer
);
4002 peer
->v_start
= BGP_INIT_START_TIMER
;
4003 BGP_EVENT_ADD(peer
, BGP_Stop
);
4005 } else if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
4006 if (flag
== PEER_FLAG_DYNAMIC_CAPABILITY
)
4007 peer
->last_reset
= PEER_DOWN_CAPABILITY_CHANGE
;
4008 else if (flag
== PEER_FLAG_PASSIVE
)
4009 peer
->last_reset
= PEER_DOWN_PASSIVE_CHANGE
;
4010 else if (flag
== PEER_FLAG_DISABLE_CONNECTED_CHECK
)
4011 peer
->last_reset
= PEER_DOWN_MULTIHOP_CHANGE
;
4013 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4014 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4016 bgp_session_reset(peer
);
4019 /* Change specified peer flag. */
4020 static int peer_flag_modify(struct peer
*peer
, uint32_t flag
, int set
)
4024 bool invert
, member_invert
;
4025 struct peer
*member
;
4026 struct listnode
*node
, *nnode
;
4027 struct peer_flag_action action
;
4029 memset(&action
, 0, sizeof(struct peer_flag_action
));
4030 size
= sizeof(peer_flag_action_list
) / sizeof(struct peer_flag_action
);
4032 invert
= CHECK_FLAG(peer
->flags_invert
, flag
);
4033 found
= peer_flag_action_set(peer_flag_action_list
, size
, &action
,
4036 /* Abort if no flag action exists. */
4038 return BGP_ERR_INVALID_FLAG
;
4040 /* Check for flag conflict: STRICT_CAP_MATCH && OVERRIDE_CAPABILITY */
4041 if (set
&& CHECK_FLAG(peer
->flags
| flag
, PEER_FLAG_STRICT_CAP_MATCH
)
4042 && CHECK_FLAG(peer
->flags
| flag
, PEER_FLAG_OVERRIDE_CAPABILITY
))
4043 return BGP_ERR_PEER_FLAG_CONFLICT
;
4045 /* Handle flag updates where desired state matches current state. */
4046 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4047 if (set
&& CHECK_FLAG(peer
->flags
, flag
)) {
4048 COND_FLAG(peer
->flags_override
, flag
, !invert
);
4052 if (!set
&& !CHECK_FLAG(peer
->flags
, flag
)) {
4053 COND_FLAG(peer
->flags_override
, flag
, invert
);
4058 /* Inherit from peer-group or set/unset flags accordingly. */
4059 if (peer_group_active(peer
) && set
== invert
)
4060 peer_flag_inherit(peer
, flag
);
4062 COND_FLAG(peer
->flags
, flag
, set
);
4064 /* Check if handling a regular peer. */
4065 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4066 /* Update flag override state accordingly. */
4067 COND_FLAG(peer
->flags_override
, flag
, set
!= invert
);
4069 if (set
&& flag
== PEER_FLAG_CAPABILITY_ENHE
)
4070 bgp_nht_register_enhe_capability_interfaces(peer
);
4072 /* Execute flag action on peer. */
4073 if (action
.type
== peer_change_reset
)
4074 peer_flag_modify_action(peer
, flag
);
4076 /* Skip peer-group mechanics for regular peers. */
4081 * Update peer-group members, unless they are explicitely overriding
4082 * peer-group configuration.
4084 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4085 /* Skip peers with overridden configuration. */
4086 if (CHECK_FLAG(member
->flags_override
, flag
))
4089 /* Check if only member without group is inverted. */
4091 CHECK_FLAG(member
->flags_invert
, flag
) && !invert
;
4093 /* Skip peers with equivalent configuration. */
4094 if (set
!= member_invert
&& CHECK_FLAG(member
->flags
, flag
))
4097 if (set
== member_invert
&& !CHECK_FLAG(member
->flags
, flag
))
4100 /* Update flag on peer-group member. */
4101 COND_FLAG(member
->flags
, flag
, set
!= member_invert
);
4103 if (set
&& flag
== PEER_FLAG_CAPABILITY_ENHE
)
4104 bgp_nht_register_enhe_capability_interfaces(member
);
4106 /* Execute flag action on peer-group member. */
4107 if (action
.type
== peer_change_reset
)
4108 peer_flag_modify_action(member
, flag
);
4114 int peer_flag_set(struct peer
*peer
, uint32_t flag
)
4116 return peer_flag_modify(peer
, flag
, 1);
4119 int peer_flag_unset(struct peer
*peer
, uint32_t flag
)
4121 return peer_flag_modify(peer
, flag
, 0);
4124 static int peer_af_flag_modify(struct peer
*peer
, afi_t afi
, safi_t safi
,
4125 uint32_t flag
, bool set
)
4129 bool invert
, member_invert
;
4130 struct peer
*member
;
4131 struct listnode
*node
, *nnode
;
4132 struct peer_flag_action action
;
4133 bgp_peer_sort_t ptype
;
4135 memset(&action
, 0, sizeof(struct peer_flag_action
));
4136 size
= sizeof(peer_af_flag_action_list
)
4137 / sizeof(struct peer_flag_action
);
4139 invert
= CHECK_FLAG(peer
->af_flags_invert
[afi
][safi
], flag
);
4140 found
= peer_flag_action_set(peer_af_flag_action_list
, size
, &action
,
4143 /* Abort if flag action exists. */
4145 return BGP_ERR_INVALID_FLAG
;
4147 ptype
= peer_sort(peer
);
4148 /* Special check for reflector client. */
4149 if (flag
& PEER_FLAG_REFLECTOR_CLIENT
&& ptype
!= BGP_PEER_IBGP
)
4150 return BGP_ERR_NOT_INTERNAL_PEER
;
4152 /* Special check for remove-private-AS. */
4153 if (flag
& PEER_FLAG_REMOVE_PRIVATE_AS
&& ptype
== BGP_PEER_IBGP
)
4154 return BGP_ERR_REMOVE_PRIVATE_AS
;
4156 /* as-override is not allowed for IBGP peers */
4157 if (flag
& PEER_FLAG_AS_OVERRIDE
&& ptype
== BGP_PEER_IBGP
)
4158 return BGP_ERR_AS_OVERRIDE
;
4160 /* Handle flag updates where desired state matches current state. */
4161 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4162 if (set
&& CHECK_FLAG(peer
->af_flags
[afi
][safi
], flag
)) {
4163 COND_FLAG(peer
->af_flags_override
[afi
][safi
], flag
,
4168 if (!set
&& !CHECK_FLAG(peer
->af_flags
[afi
][safi
], flag
)) {
4169 COND_FLAG(peer
->af_flags_override
[afi
][safi
], flag
,
4176 * For EVPN we implicitly set the NEXTHOP_UNCHANGED flag,
4177 * if we are setting/unsetting flags which conflict with this flag
4178 * handle accordingly
4180 if (afi
== AFI_L2VPN
&& safi
== SAFI_EVPN
) {
4184 * if we are setting NEXTHOP_SELF, we need to unset the
4185 * NEXTHOP_UNCHANGED flag
4187 if (CHECK_FLAG(flag
, PEER_FLAG_NEXTHOP_SELF
) ||
4188 CHECK_FLAG(flag
, PEER_FLAG_FORCE_NEXTHOP_SELF
))
4189 UNSET_FLAG(peer
->af_flags
[afi
][safi
],
4190 PEER_FLAG_NEXTHOP_UNCHANGED
);
4194 * if we are unsetting NEXTHOP_SELF, we need to set the
4195 * NEXTHOP_UNCHANGED flag to reset the defaults for EVPN
4197 if (CHECK_FLAG(flag
, PEER_FLAG_NEXTHOP_SELF
) ||
4198 CHECK_FLAG(flag
, PEER_FLAG_FORCE_NEXTHOP_SELF
))
4199 SET_FLAG(peer
->af_flags
[afi
][safi
],
4200 PEER_FLAG_NEXTHOP_UNCHANGED
);
4205 * If the peer is a route server client let's not
4206 * muck with the nexthop on the way out the door
4208 if (flag
& PEER_FLAG_RSERVER_CLIENT
) {
4210 SET_FLAG(peer
->af_flags
[afi
][safi
],
4211 PEER_FLAG_NEXTHOP_UNCHANGED
);
4213 UNSET_FLAG(peer
->af_flags
[afi
][safi
],
4214 PEER_FLAG_NEXTHOP_UNCHANGED
);
4217 /* Inherit from peer-group or set/unset flags accordingly. */
4218 if (peer_group_active(peer
) && set
== invert
)
4219 peer_af_flag_inherit(peer
, afi
, safi
, flag
);
4221 COND_FLAG(peer
->af_flags
[afi
][safi
], flag
, set
);
4223 /* Execute action when peer is established. */
4224 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)
4225 && peer
->status
== Established
) {
4226 if (!set
&& flag
== PEER_FLAG_SOFT_RECONFIG
)
4227 bgp_clear_adj_in(peer
, afi
, safi
);
4229 if (flag
== PEER_FLAG_REFLECTOR_CLIENT
)
4230 peer
->last_reset
= PEER_DOWN_RR_CLIENT_CHANGE
;
4231 else if (flag
== PEER_FLAG_RSERVER_CLIENT
)
4232 peer
->last_reset
= PEER_DOWN_RS_CLIENT_CHANGE
;
4233 else if (flag
== PEER_FLAG_ORF_PREFIX_SM
)
4234 peer
->last_reset
= PEER_DOWN_CAPABILITY_CHANGE
;
4235 else if (flag
== PEER_FLAG_ORF_PREFIX_RM
)
4236 peer
->last_reset
= PEER_DOWN_CAPABILITY_CHANGE
;
4238 peer_change_action(peer
, afi
, safi
, action
.type
);
4242 /* Check if handling a regular peer. */
4243 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4244 COND_FLAG(peer
->af_flags_override
[afi
][safi
], flag
,
4248 * Update peer-group members, unless they are explicitely
4249 * overriding peer-group configuration.
4251 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
,
4253 /* Skip peers with overridden configuration. */
4254 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4258 /* Check if only member without group is inverted. */
4260 CHECK_FLAG(member
->af_flags_invert
[afi
][safi
],
4264 /* Skip peers with equivalent configuration. */
4265 if (set
!= member_invert
4266 && CHECK_FLAG(member
->af_flags
[afi
][safi
], flag
))
4269 if (set
== member_invert
4270 && !CHECK_FLAG(member
->af_flags
[afi
][safi
], flag
))
4273 /* Update flag on peer-group member. */
4274 COND_FLAG(member
->af_flags
[afi
][safi
], flag
,
4275 set
!= member_invert
);
4277 /* Execute flag action on peer-group member. */
4278 if (member
->status
== Established
) {
4279 if (!set
&& flag
== PEER_FLAG_SOFT_RECONFIG
)
4280 bgp_clear_adj_in(member
, afi
, safi
);
4282 if (flag
== PEER_FLAG_REFLECTOR_CLIENT
)
4283 member
->last_reset
=
4284 PEER_DOWN_RR_CLIENT_CHANGE
;
4286 == PEER_FLAG_RSERVER_CLIENT
)
4287 member
->last_reset
=
4288 PEER_DOWN_RS_CLIENT_CHANGE
;
4290 == PEER_FLAG_ORF_PREFIX_SM
)
4291 member
->last_reset
=
4292 PEER_DOWN_CAPABILITY_CHANGE
;
4294 == PEER_FLAG_ORF_PREFIX_RM
)
4295 member
->last_reset
=
4296 PEER_DOWN_CAPABILITY_CHANGE
;
4298 peer_change_action(member
, afi
, safi
,
4308 int peer_af_flag_set(struct peer
*peer
, afi_t afi
, safi_t safi
, uint32_t flag
)
4310 return peer_af_flag_modify(peer
, afi
, safi
, flag
, 1);
4313 int peer_af_flag_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, uint32_t flag
)
4315 return peer_af_flag_modify(peer
, afi
, safi
, flag
, 0);
4319 void peer_tx_shutdown_message_set(struct peer
*peer
, const char *msg
)
4321 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG
, peer
->tx_shutdown_message
);
4322 peer
->tx_shutdown_message
=
4323 msg
? XSTRDUP(MTYPE_PEER_TX_SHUTDOWN_MSG
, msg
) : NULL
;
4326 void peer_tx_shutdown_message_unset(struct peer
*peer
)
4328 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG
, peer
->tx_shutdown_message
);
4332 /* EBGP multihop configuration. */
4333 int peer_ebgp_multihop_set(struct peer
*peer
, int ttl
)
4335 struct peer_group
*group
;
4336 struct listnode
*node
, *nnode
;
4339 if (peer
->sort
== BGP_PEER_IBGP
|| peer
->conf_if
)
4342 /* see comment in peer_ttl_security_hops_set() */
4343 if (ttl
!= MAXTTL
) {
4344 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4345 group
= peer
->group
;
4346 if (group
->conf
->gtsm_hops
!= BGP_GTSM_HOPS_DISABLED
)
4347 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4349 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
,
4351 if (peer1
->sort
== BGP_PEER_IBGP
)
4354 if (peer1
->gtsm_hops
!= BGP_GTSM_HOPS_DISABLED
)
4355 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4358 if (peer
->gtsm_hops
!= BGP_GTSM_HOPS_DISABLED
)
4359 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4365 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4366 if (peer
->fd
>= 0 && peer
->sort
!= BGP_PEER_IBGP
) {
4367 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4368 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4369 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4371 bgp_session_reset(peer
);
4374 group
= peer
->group
;
4375 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
4376 if (peer
->sort
== BGP_PEER_IBGP
)
4379 peer
->ttl
= group
->conf
->ttl
;
4381 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4382 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4383 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4385 bgp_session_reset(peer
);
4391 int peer_ebgp_multihop_unset(struct peer
*peer
)
4393 struct peer_group
*group
;
4394 struct listnode
*node
, *nnode
;
4396 if (peer
->sort
== BGP_PEER_IBGP
)
4399 if (peer
->gtsm_hops
!= BGP_GTSM_HOPS_DISABLED
&& peer
->ttl
!= MAXTTL
)
4400 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
4402 if (peer_group_active(peer
))
4403 peer
->ttl
= peer
->group
->conf
->ttl
;
4405 peer
->ttl
= BGP_DEFAULT_TTL
;
4407 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4408 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4409 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4410 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4412 bgp_session_reset(peer
);
4414 group
= peer
->group
;
4415 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
4416 if (peer
->sort
== BGP_PEER_IBGP
)
4419 peer
->ttl
= BGP_DEFAULT_TTL
;
4421 if (peer
->fd
>= 0) {
4422 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
4424 peer
, BGP_NOTIFY_CEASE
,
4425 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4427 bgp_session_reset(peer
);
4434 /* Neighbor description. */
4435 void peer_description_set(struct peer
*peer
, const char *desc
)
4437 XFREE(MTYPE_PEER_DESC
, peer
->desc
);
4439 peer
->desc
= XSTRDUP(MTYPE_PEER_DESC
, desc
);
4442 void peer_description_unset(struct peer
*peer
)
4444 XFREE(MTYPE_PEER_DESC
, peer
->desc
);
4447 /* Neighbor update-source. */
4448 int peer_update_source_if_set(struct peer
*peer
, const char *ifname
)
4450 struct peer
*member
;
4451 struct listnode
*node
, *nnode
;
4453 /* Set flag and configuration on peer. */
4454 peer_flag_set(peer
, PEER_FLAG_UPDATE_SOURCE
);
4455 if (peer
->update_if
) {
4456 if (strcmp(peer
->update_if
, ifname
) == 0)
4458 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
4460 peer
->update_if
= XSTRDUP(MTYPE_PEER_UPDATE_SOURCE
, ifname
);
4461 sockunion_free(peer
->update_source
);
4462 peer
->update_source
= NULL
;
4464 /* Check if handling a regular peer. */
4465 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4466 /* Send notification or reset peer depending on state. */
4467 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
4468 peer
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4469 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4470 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4472 bgp_session_reset(peer
);
4474 /* Skip peer-group mechanics for regular peers. */
4479 * Set flag and configuration on all peer-group members, unless they are
4480 * explicitely overriding peer-group configuration.
4482 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4483 /* Skip peers with overridden configuration. */
4484 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_UPDATE_SOURCE
))
4487 /* Skip peers with the same configuration. */
4488 if (member
->update_if
) {
4489 if (strcmp(member
->update_if
, ifname
) == 0)
4491 XFREE(MTYPE_PEER_UPDATE_SOURCE
, member
->update_if
);
4494 /* Set flag and configuration on peer-group member. */
4495 SET_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
);
4496 member
->update_if
= XSTRDUP(MTYPE_PEER_UPDATE_SOURCE
, ifname
);
4497 sockunion_free(member
->update_source
);
4498 member
->update_source
= NULL
;
4500 /* Send notification or reset peer depending on state. */
4501 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
4502 member
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4503 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
4504 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4506 bgp_session_reset(member
);
4512 int peer_update_source_addr_set(struct peer
*peer
, const union sockunion
*su
)
4514 struct peer
*member
;
4515 struct listnode
*node
, *nnode
;
4517 /* Set flag and configuration on peer. */
4518 peer_flag_set(peer
, PEER_FLAG_UPDATE_SOURCE
);
4519 if (peer
->update_source
) {
4520 if (sockunion_cmp(peer
->update_source
, su
) == 0)
4522 sockunion_free(peer
->update_source
);
4524 peer
->update_source
= sockunion_dup(su
);
4525 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
4527 /* Check if handling a regular peer. */
4528 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4529 /* Send notification or reset peer depending on state. */
4530 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
4531 peer
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4532 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4533 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4535 bgp_session_reset(peer
);
4537 /* Skip peer-group mechanics for regular peers. */
4542 * Set flag and configuration on all peer-group members, unless they are
4543 * explicitely overriding peer-group configuration.
4545 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4546 /* Skip peers with overridden configuration. */
4547 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_UPDATE_SOURCE
))
4550 /* Skip peers with the same configuration. */
4551 if (member
->update_source
) {
4552 if (sockunion_cmp(member
->update_source
, su
) == 0)
4554 sockunion_free(member
->update_source
);
4557 /* Set flag and configuration on peer-group member. */
4558 SET_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
);
4559 member
->update_source
= sockunion_dup(su
);
4560 XFREE(MTYPE_PEER_UPDATE_SOURCE
, member
->update_if
);
4562 /* Send notification or reset peer depending on state. */
4563 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
4564 member
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4565 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
4566 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4568 bgp_session_reset(member
);
4574 int peer_update_source_unset(struct peer
*peer
)
4576 struct peer
*member
;
4577 struct listnode
*node
, *nnode
;
4579 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_UPDATE_SOURCE
))
4582 /* Inherit configuration from peer-group if peer is member. */
4583 if (peer_group_active(peer
)) {
4584 peer_flag_inherit(peer
, PEER_FLAG_UPDATE_SOURCE
);
4585 PEER_SU_ATTR_INHERIT(peer
, peer
->group
, update_source
);
4586 PEER_STR_ATTR_INHERIT(peer
, peer
->group
, update_if
,
4587 MTYPE_PEER_UPDATE_SOURCE
);
4589 /* Otherwise remove flag and configuration from peer. */
4590 peer_flag_unset(peer
, PEER_FLAG_UPDATE_SOURCE
);
4591 sockunion_free(peer
->update_source
);
4592 peer
->update_source
= NULL
;
4593 XFREE(MTYPE_PEER_UPDATE_SOURCE
, peer
->update_if
);
4596 /* Check if handling a regular peer. */
4597 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4598 /* Send notification or reset peer depending on state. */
4599 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
4600 peer
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4601 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
4602 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4604 bgp_session_reset(peer
);
4606 /* Skip peer-group mechanics for regular peers. */
4611 * Set flag and configuration on all peer-group members, unless they are
4612 * explicitely overriding peer-group configuration.
4614 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4615 /* Skip peers with overridden configuration. */
4616 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_UPDATE_SOURCE
))
4619 /* Skip peers with the same configuration. */
4620 if (!CHECK_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
)
4621 && !member
->update_source
&& !member
->update_if
)
4624 /* Remove flag and configuration on peer-group member. */
4625 UNSET_FLAG(member
->flags
, PEER_FLAG_UPDATE_SOURCE
);
4626 sockunion_free(member
->update_source
);
4627 member
->update_source
= NULL
;
4628 XFREE(MTYPE_PEER_UPDATE_SOURCE
, member
->update_if
);
4630 /* Send notification or reset peer depending on state. */
4631 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
4632 member
->last_reset
= PEER_DOWN_UPDATE_SOURCE_CHANGE
;
4633 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
4634 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
4636 bgp_session_reset(member
);
4642 int peer_default_originate_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
4643 const char *rmap
, struct route_map
*route_map
)
4645 struct peer
*member
;
4646 struct listnode
*node
, *nnode
;
4648 /* Set flag and configuration on peer. */
4649 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_DEFAULT_ORIGINATE
);
4651 if (!peer
->default_rmap
[afi
][safi
].name
4652 || strcmp(rmap
, peer
->default_rmap
[afi
][safi
].name
) != 0) {
4653 if (peer
->default_rmap
[afi
][safi
].name
)
4654 XFREE(MTYPE_ROUTE_MAP_NAME
,
4655 peer
->default_rmap
[afi
][safi
].name
);
4657 route_map_counter_decrement(peer
->default_rmap
[afi
][safi
].map
);
4658 peer
->default_rmap
[afi
][safi
].name
=
4659 XSTRDUP(MTYPE_ROUTE_MAP_NAME
, rmap
);
4660 peer
->default_rmap
[afi
][safi
].map
= route_map
;
4661 route_map_counter_increment(route_map
);
4664 if (peer
->default_rmap
[afi
][safi
].name
)
4665 XFREE(MTYPE_ROUTE_MAP_NAME
,
4666 peer
->default_rmap
[afi
][safi
].name
);
4668 route_map_counter_decrement(peer
->default_rmap
[afi
][safi
].map
);
4669 peer
->default_rmap
[afi
][safi
].name
= NULL
;
4670 peer
->default_rmap
[afi
][safi
].map
= NULL
;
4673 /* Check if handling a regular peer. */
4674 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4675 /* Update peer route announcements. */
4676 if (peer
->status
== Established
&& peer
->afc_nego
[afi
][safi
]) {
4677 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4678 bgp_default_originate(peer
, afi
, safi
, 0);
4679 bgp_announce_route(peer
, afi
, safi
);
4682 /* Skip peer-group mechanics for regular peers. */
4687 * Set flag and configuration on all peer-group members, unless they are
4688 * explicitely overriding peer-group configuration.
4690 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4691 /* Skip peers with overridden configuration. */
4692 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4693 PEER_FLAG_DEFAULT_ORIGINATE
))
4696 /* Set flag and configuration on peer-group member. */
4697 SET_FLAG(member
->af_flags
[afi
][safi
],
4698 PEER_FLAG_DEFAULT_ORIGINATE
);
4700 if (member
->default_rmap
[afi
][safi
].name
)
4701 XFREE(MTYPE_ROUTE_MAP_NAME
,
4702 member
->default_rmap
[afi
][safi
].name
);
4703 route_map_counter_decrement(
4704 member
->default_rmap
[afi
][safi
].map
);
4705 member
->default_rmap
[afi
][safi
].name
=
4706 XSTRDUP(MTYPE_ROUTE_MAP_NAME
, rmap
);
4707 member
->default_rmap
[afi
][safi
].map
= route_map
;
4708 route_map_counter_increment(route_map
);
4711 /* Update peer route announcements. */
4712 if (member
->status
== Established
4713 && member
->afc_nego
[afi
][safi
]) {
4714 update_group_adjust_peer(
4715 peer_af_find(member
, afi
, safi
));
4716 bgp_default_originate(member
, afi
, safi
, 0);
4717 bgp_announce_route(member
, afi
, safi
);
4724 int peer_default_originate_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
4726 struct peer
*member
;
4727 struct listnode
*node
, *nnode
;
4729 /* Inherit configuration from peer-group if peer is member. */
4730 if (peer_group_active(peer
)) {
4731 peer_af_flag_inherit(peer
, afi
, safi
,
4732 PEER_FLAG_DEFAULT_ORIGINATE
);
4733 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
4734 default_rmap
[afi
][safi
].name
,
4735 MTYPE_ROUTE_MAP_NAME
);
4736 PEER_ATTR_INHERIT(peer
, peer
->group
,
4737 default_rmap
[afi
][safi
].map
);
4739 /* Otherwise remove flag and configuration from peer. */
4740 peer_af_flag_unset(peer
, afi
, safi
,
4741 PEER_FLAG_DEFAULT_ORIGINATE
);
4742 if (peer
->default_rmap
[afi
][safi
].name
)
4743 XFREE(MTYPE_ROUTE_MAP_NAME
,
4744 peer
->default_rmap
[afi
][safi
].name
);
4745 route_map_counter_decrement(peer
->default_rmap
[afi
][safi
].map
);
4746 peer
->default_rmap
[afi
][safi
].name
= NULL
;
4747 peer
->default_rmap
[afi
][safi
].map
= NULL
;
4750 /* Check if handling a regular peer. */
4751 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
4752 /* Update peer route announcements. */
4753 if (peer
->status
== Established
&& peer
->afc_nego
[afi
][safi
]) {
4754 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4755 bgp_default_originate(peer
, afi
, safi
, 1);
4756 bgp_announce_route(peer
, afi
, safi
);
4759 /* Skip peer-group mechanics for regular peers. */
4764 * Remove flag and configuration from all peer-group members, unless
4765 * they are explicitely overriding peer-group configuration.
4767 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4768 /* Skip peers with overridden configuration. */
4769 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4770 PEER_FLAG_DEFAULT_ORIGINATE
))
4773 /* Remove flag and configuration on peer-group member. */
4774 UNSET_FLAG(peer
->af_flags
[afi
][safi
],
4775 PEER_FLAG_DEFAULT_ORIGINATE
);
4776 if (peer
->default_rmap
[afi
][safi
].name
)
4777 XFREE(MTYPE_ROUTE_MAP_NAME
,
4778 peer
->default_rmap
[afi
][safi
].name
);
4779 route_map_counter_decrement(peer
->default_rmap
[afi
][safi
].map
);
4780 peer
->default_rmap
[afi
][safi
].name
= NULL
;
4781 peer
->default_rmap
[afi
][safi
].map
= NULL
;
4783 /* Update peer route announcements. */
4784 if (peer
->status
== Established
&& peer
->afc_nego
[afi
][safi
]) {
4785 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4786 bgp_default_originate(peer
, afi
, safi
, 1);
4787 bgp_announce_route(peer
, afi
, safi
);
4794 void peer_port_set(struct peer
*peer
, uint16_t port
)
4799 void peer_port_unset(struct peer
*peer
)
4801 peer
->port
= BGP_PORT_DEFAULT
;
4805 * Helper function that is called after the name of the policy
4806 * being used by a peer has changed (AF specific). Automatically
4807 * initiates inbound or outbound processing as needed.
4809 static void peer_on_policy_change(struct peer
*peer
, afi_t afi
, safi_t safi
,
4813 update_group_adjust_peer(peer_af_find(peer
, afi
, safi
));
4814 if (peer
->status
== Established
)
4815 bgp_announce_route(peer
, afi
, safi
);
4817 if (peer
->status
!= Established
)
4820 if (CHECK_FLAG(peer
->af_flags
[afi
][safi
],
4821 PEER_FLAG_SOFT_RECONFIG
))
4822 bgp_soft_reconfig_in(peer
, afi
, safi
);
4823 else if (CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_OLD_RCV
)
4824 || CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_NEW_RCV
))
4825 bgp_route_refresh_send(peer
, afi
, safi
, 0, 0, 0);
4830 /* neighbor weight. */
4831 int peer_weight_set(struct peer
*peer
, afi_t afi
, safi_t safi
, uint16_t weight
)
4833 struct peer
*member
;
4834 struct listnode
*node
, *nnode
;
4836 /* Set flag and configuration on peer. */
4837 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_WEIGHT
);
4838 if (peer
->weight
[afi
][safi
] != weight
) {
4839 peer
->weight
[afi
][safi
] = weight
;
4840 peer_on_policy_change(peer
, afi
, safi
, 0);
4843 /* Skip peer-group mechanics for regular peers. */
4844 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4848 * Set flag and configuration on all peer-group members, unless they are
4849 * explicitely overriding peer-group configuration.
4851 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4852 /* Skip peers with overridden configuration. */
4853 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4857 /* Set flag and configuration on peer-group member. */
4858 SET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
);
4859 if (member
->weight
[afi
][safi
] != weight
) {
4860 member
->weight
[afi
][safi
] = weight
;
4861 peer_on_policy_change(member
, afi
, safi
, 0);
4868 int peer_weight_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
4870 struct peer
*member
;
4871 struct listnode
*node
, *nnode
;
4873 if (!CHECK_FLAG(peer
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
))
4876 /* Inherit configuration from peer-group if peer is member. */
4877 if (peer_group_active(peer
)) {
4878 peer_af_flag_inherit(peer
, afi
, safi
, PEER_FLAG_WEIGHT
);
4879 PEER_ATTR_INHERIT(peer
, peer
->group
, weight
[afi
][safi
]);
4881 peer_on_policy_change(peer
, afi
, safi
, 0);
4885 /* Remove flag and configuration from peer. */
4886 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_WEIGHT
);
4887 peer
->weight
[afi
][safi
] = 0;
4888 peer_on_policy_change(peer
, afi
, safi
, 0);
4890 /* Skip peer-group mechanics for regular peers. */
4891 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4895 * Remove flag and configuration from all peer-group members, unless
4896 * they are explicitely overriding peer-group configuration.
4898 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4899 /* Skip peers with overridden configuration. */
4900 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
4904 /* Skip peers where flag is already disabled. */
4905 if (!CHECK_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
))
4908 /* Remove flag and configuration on peer-group member. */
4909 UNSET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_WEIGHT
);
4910 member
->weight
[afi
][safi
] = 0;
4911 peer_on_policy_change(member
, afi
, safi
, 0);
4917 int peer_timers_set(struct peer
*peer
, uint32_t keepalive
, uint32_t holdtime
)
4919 struct peer
*member
;
4920 struct listnode
*node
, *nnode
;
4922 if (keepalive
> 65535)
4923 return BGP_ERR_INVALID_VALUE
;
4925 if (holdtime
> 65535)
4926 return BGP_ERR_INVALID_VALUE
;
4928 if (holdtime
< 3 && holdtime
!= 0)
4929 return BGP_ERR_INVALID_VALUE
;
4931 /* Set flag and configuration on peer. */
4932 peer_flag_set(peer
, PEER_FLAG_TIMER
);
4933 peer
->holdtime
= holdtime
;
4934 peer
->keepalive
= (keepalive
< holdtime
/ 3 ? keepalive
: holdtime
/ 3);
4936 /* Skip peer-group mechanics for regular peers. */
4937 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4941 * Set flag and configuration on all peer-group members, unless they are
4942 * explicitely overriding peer-group configuration.
4944 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4945 /* Skip peers with overridden configuration. */
4946 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER
))
4949 /* Set flag and configuration on peer-group member. */
4950 SET_FLAG(member
->flags
, PEER_FLAG_TIMER
);
4951 PEER_ATTR_INHERIT(peer
, peer
->group
, holdtime
);
4952 PEER_ATTR_INHERIT(peer
, peer
->group
, keepalive
);
4958 int peer_timers_unset(struct peer
*peer
)
4960 struct peer
*member
;
4961 struct listnode
*node
, *nnode
;
4963 /* Inherit configuration from peer-group if peer is member. */
4964 if (peer_group_active(peer
)) {
4965 peer_flag_inherit(peer
, PEER_FLAG_TIMER
);
4966 PEER_ATTR_INHERIT(peer
, peer
->group
, holdtime
);
4967 PEER_ATTR_INHERIT(peer
, peer
->group
, keepalive
);
4969 /* Otherwise remove flag and configuration from peer. */
4970 peer_flag_unset(peer
, PEER_FLAG_TIMER
);
4972 peer
->keepalive
= 0;
4975 /* Skip peer-group mechanics for regular peers. */
4976 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
4980 * Remove flag and configuration from all peer-group members, unless
4981 * they are explicitely overriding peer-group configuration.
4983 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
4984 /* Skip peers with overridden configuration. */
4985 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER
))
4988 /* Remove flag and configuration on peer-group member. */
4989 UNSET_FLAG(member
->flags
, PEER_FLAG_TIMER
);
4990 member
->holdtime
= 0;
4991 member
->keepalive
= 0;
4997 int peer_timers_connect_set(struct peer
*peer
, uint32_t connect
)
4999 struct peer
*member
;
5000 struct listnode
*node
, *nnode
;
5002 if (connect
> 65535)
5003 return BGP_ERR_INVALID_VALUE
;
5005 /* Set flag and configuration on peer. */
5006 peer_flag_set(peer
, PEER_FLAG_TIMER_CONNECT
);
5007 peer
->connect
= connect
;
5008 peer
->v_connect
= connect
;
5010 /* Skip peer-group mechanics for regular peers. */
5011 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
5015 * Set flag and configuration on all peer-group members, unless they are
5016 * explicitely overriding peer-group configuration.
5018 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5019 /* Skip peers with overridden configuration. */
5020 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER_CONNECT
))
5023 /* Set flag and configuration on peer-group member. */
5024 SET_FLAG(member
->flags
, PEER_FLAG_TIMER_CONNECT
);
5025 member
->connect
= connect
;
5026 member
->v_connect
= connect
;
5032 int peer_timers_connect_unset(struct peer
*peer
)
5034 struct peer
*member
;
5035 struct listnode
*node
, *nnode
;
5037 /* Inherit configuration from peer-group if peer is member. */
5038 if (peer_group_active(peer
)) {
5039 peer_flag_inherit(peer
, PEER_FLAG_TIMER_CONNECT
);
5040 PEER_ATTR_INHERIT(peer
, peer
->group
, connect
);
5042 /* Otherwise remove flag and configuration from peer. */
5043 peer_flag_unset(peer
, PEER_FLAG_TIMER_CONNECT
);
5047 /* Set timer with fallback to default value. */
5049 peer
->v_connect
= peer
->connect
;
5051 peer
->v_connect
= peer
->bgp
->default_connect_retry
;
5053 /* Skip peer-group mechanics for regular peers. */
5054 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
5058 * Remove flag and configuration from all peer-group members, unless
5059 * they are explicitely overriding peer-group configuration.
5061 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5062 /* Skip peers with overridden configuration. */
5063 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_TIMER_CONNECT
))
5066 /* Remove flag and configuration on peer-group member. */
5067 UNSET_FLAG(member
->flags
, PEER_FLAG_TIMER_CONNECT
);
5068 member
->connect
= 0;
5069 member
->v_connect
= peer
->bgp
->default_connect_retry
;
5075 int peer_advertise_interval_set(struct peer
*peer
, uint32_t routeadv
)
5077 struct peer
*member
;
5078 struct listnode
*node
, *nnode
;
5081 return BGP_ERR_INVALID_VALUE
;
5083 /* Set flag and configuration on peer. */
5084 peer_flag_set(peer
, PEER_FLAG_ROUTEADV
);
5085 peer
->routeadv
= routeadv
;
5086 peer
->v_routeadv
= routeadv
;
5088 /* Check if handling a regular peer. */
5089 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5090 /* Update peer route announcements. */
5091 update_group_adjust_peer_afs(peer
);
5092 if (peer
->status
== Established
)
5093 bgp_announce_route_all(peer
);
5095 /* Skip peer-group mechanics for regular peers. */
5100 * Set flag and configuration on all peer-group members, unless they are
5101 * explicitely overriding peer-group configuration.
5103 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5104 /* Skip peers with overridden configuration. */
5105 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_ROUTEADV
))
5108 /* Set flag and configuration on peer-group member. */
5109 SET_FLAG(member
->flags
, PEER_FLAG_ROUTEADV
);
5110 member
->routeadv
= routeadv
;
5111 member
->v_routeadv
= routeadv
;
5113 /* Update peer route announcements. */
5114 update_group_adjust_peer_afs(member
);
5115 if (member
->status
== Established
)
5116 bgp_announce_route_all(member
);
5122 int peer_advertise_interval_unset(struct peer
*peer
)
5124 struct peer
*member
;
5125 struct listnode
*node
, *nnode
;
5127 /* Inherit configuration from peer-group if peer is member. */
5128 if (peer_group_active(peer
)) {
5129 peer_flag_inherit(peer
, PEER_FLAG_ROUTEADV
);
5130 PEER_ATTR_INHERIT(peer
, peer
->group
, routeadv
);
5132 /* Otherwise remove flag and configuration from peer. */
5133 peer_flag_unset(peer
, PEER_FLAG_ROUTEADV
);
5137 /* Set timer with fallback to default value. */
5139 peer
->v_routeadv
= peer
->routeadv
;
5141 peer
->v_routeadv
= (peer
->sort
== BGP_PEER_IBGP
)
5142 ? BGP_DEFAULT_IBGP_ROUTEADV
5143 : BGP_DEFAULT_EBGP_ROUTEADV
;
5145 /* Check if handling a regular peer. */
5146 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5147 /* Update peer route announcements. */
5148 update_group_adjust_peer_afs(peer
);
5149 if (peer
->status
== Established
)
5150 bgp_announce_route_all(peer
);
5152 /* Skip peer-group mechanics for regular peers. */
5157 * Remove flag and configuration from all peer-group members, unless
5158 * they are explicitely overriding peer-group configuration.
5160 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5161 /* Skip peers with overridden configuration. */
5162 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_ROUTEADV
))
5165 /* Remove flag and configuration on peer-group member. */
5166 UNSET_FLAG(member
->flags
, PEER_FLAG_ROUTEADV
);
5167 member
->routeadv
= 0;
5168 member
->v_routeadv
= (member
->sort
== BGP_PEER_IBGP
)
5169 ? BGP_DEFAULT_IBGP_ROUTEADV
5170 : BGP_DEFAULT_EBGP_ROUTEADV
;
5172 /* Update peer route announcements. */
5173 update_group_adjust_peer_afs(member
);
5174 if (member
->status
== Established
)
5175 bgp_announce_route_all(member
);
5181 /* neighbor interface */
5182 void peer_interface_set(struct peer
*peer
, const char *str
)
5184 XFREE(MTYPE_BGP_PEER_IFNAME
, peer
->ifname
);
5185 peer
->ifname
= XSTRDUP(MTYPE_BGP_PEER_IFNAME
, str
);
5188 void peer_interface_unset(struct peer
*peer
)
5190 XFREE(MTYPE_BGP_PEER_IFNAME
, peer
->ifname
);
5194 int peer_allowas_in_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
5195 int allow_num
, int origin
)
5197 struct peer
*member
;
5198 struct listnode
*node
, *nnode
;
5200 if (!origin
&& (allow_num
< 1 || allow_num
> 10))
5201 return BGP_ERR_INVALID_VALUE
;
5203 /* Set flag and configuration on peer. */
5204 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN
);
5206 if (peer
->allowas_in
[afi
][safi
] != 0
5207 || !CHECK_FLAG(peer
->af_flags
[afi
][safi
],
5208 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5209 peer_af_flag_set(peer
, afi
, safi
,
5210 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5211 peer
->allowas_in
[afi
][safi
] = 0;
5212 peer_on_policy_change(peer
, afi
, safi
, 0);
5215 if (peer
->allowas_in
[afi
][safi
] != allow_num
5216 || CHECK_FLAG(peer
->af_flags
[afi
][safi
],
5217 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5219 peer_af_flag_unset(peer
, afi
, safi
,
5220 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5221 peer
->allowas_in
[afi
][safi
] = allow_num
;
5222 peer_on_policy_change(peer
, afi
, safi
, 0);
5226 /* Skip peer-group mechanics for regular peers. */
5227 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
5231 * Set flag and configuration on all peer-group members, unless
5232 * they are explicitely overriding peer-group configuration.
5234 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5235 /* Skip peers with overridden configuration. */
5236 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
5237 PEER_FLAG_ALLOWAS_IN
))
5240 /* Set flag and configuration on peer-group member. */
5241 SET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_ALLOWAS_IN
);
5243 if (member
->allowas_in
[afi
][safi
] != 0
5244 || !CHECK_FLAG(member
->af_flags
[afi
][safi
],
5245 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5246 SET_FLAG(member
->af_flags
[afi
][safi
],
5247 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5248 member
->allowas_in
[afi
][safi
] = 0;
5249 peer_on_policy_change(peer
, afi
, safi
, 0);
5252 if (member
->allowas_in
[afi
][safi
] != allow_num
5253 || CHECK_FLAG(member
->af_flags
[afi
][safi
],
5254 PEER_FLAG_ALLOWAS_IN_ORIGIN
)) {
5255 UNSET_FLAG(member
->af_flags
[afi
][safi
],
5256 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5257 member
->allowas_in
[afi
][safi
] = allow_num
;
5258 peer_on_policy_change(peer
, afi
, safi
, 0);
5266 int peer_allowas_in_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
5268 struct peer
*member
;
5269 struct listnode
*node
, *nnode
;
5271 /* Skip peer if flag is already disabled. */
5272 if (!CHECK_FLAG(peer
->af_flags
[afi
][safi
], PEER_FLAG_ALLOWAS_IN
))
5275 /* Inherit configuration from peer-group if peer is member. */
5276 if (peer_group_active(peer
)) {
5277 peer_af_flag_inherit(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN
);
5278 peer_af_flag_inherit(peer
, afi
, safi
,
5279 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5280 PEER_ATTR_INHERIT(peer
, peer
->group
, allowas_in
[afi
][safi
]);
5281 peer_on_policy_change(peer
, afi
, safi
, 0);
5286 /* Remove flag and configuration from peer. */
5287 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN
);
5288 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5289 peer
->allowas_in
[afi
][safi
] = 0;
5290 peer_on_policy_change(peer
, afi
, safi
, 0);
5292 /* Skip peer-group mechanics if handling a regular peer. */
5293 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
))
5297 * Remove flags and configuration from all peer-group members, unless
5298 * they are explicitely overriding peer-group configuration.
5300 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5301 /* Skip peers with overridden configuration. */
5302 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
5303 PEER_FLAG_ALLOWAS_IN
))
5306 /* Skip peers where flag is already disabled. */
5307 if (!CHECK_FLAG(member
->af_flags
[afi
][safi
],
5308 PEER_FLAG_ALLOWAS_IN
))
5311 /* Remove flags and configuration on peer-group member. */
5312 UNSET_FLAG(member
->af_flags
[afi
][safi
], PEER_FLAG_ALLOWAS_IN
);
5313 UNSET_FLAG(member
->af_flags
[afi
][safi
],
5314 PEER_FLAG_ALLOWAS_IN_ORIGIN
);
5315 member
->allowas_in
[afi
][safi
] = 0;
5316 peer_on_policy_change(member
, afi
, safi
, 0);
5322 int peer_local_as_set(struct peer
*peer
, as_t as
, int no_prepend
,
5325 bool old_no_prepend
, old_replace_as
;
5326 struct bgp
*bgp
= peer
->bgp
;
5327 struct peer
*member
;
5328 struct listnode
*node
, *nnode
;
5329 bgp_peer_sort_t ptype
= peer_sort(peer
);
5331 if (ptype
!= BGP_PEER_EBGP
&& ptype
!= BGP_PEER_INTERNAL
)
5332 return BGP_ERR_LOCAL_AS_ALLOWED_ONLY_FOR_EBGP
;
5335 return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS
;
5338 return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS_REMOTE_AS
;
5340 /* Save previous flag states. */
5342 !!CHECK_FLAG(peer
->flags
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5344 !!CHECK_FLAG(peer
->flags
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5346 /* Set flag and configuration on peer. */
5347 peer_flag_set(peer
, PEER_FLAG_LOCAL_AS
);
5348 peer_flag_modify(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
, no_prepend
);
5349 peer_flag_modify(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
, replace_as
);
5351 if (peer
->change_local_as
== as
&& old_no_prepend
== no_prepend
5352 && old_replace_as
== replace_as
)
5354 peer
->change_local_as
= as
;
5356 /* Check if handling a regular peer. */
5357 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5358 /* Send notification or reset peer depending on state. */
5359 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
5360 peer
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5361 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5362 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5364 bgp_session_reset(peer
);
5366 /* Skip peer-group mechanics for regular peers. */
5371 * Set flag and configuration on all peer-group members, unless they are
5372 * explicitely overriding peer-group configuration.
5374 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5375 /* Skip peers with overridden configuration. */
5376 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_LOCAL_AS
))
5379 /* Skip peers with the same configuration. */
5380 old_no_prepend
= CHECK_FLAG(member
->flags
,
5381 PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5382 old_replace_as
= CHECK_FLAG(member
->flags
,
5383 PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5384 if (member
->change_local_as
== as
5385 && CHECK_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS
)
5386 && old_no_prepend
== no_prepend
5387 && old_replace_as
== replace_as
)
5390 /* Set flag and configuration on peer-group member. */
5391 SET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS
);
5392 COND_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_NO_PREPEND
,
5394 COND_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_REPLACE_AS
,
5396 member
->change_local_as
= as
;
5398 /* Send notification or stop peer depending on state. */
5399 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
5400 member
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5401 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5402 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5404 BGP_EVENT_ADD(member
, BGP_Stop
);
5410 int peer_local_as_unset(struct peer
*peer
)
5412 struct peer
*member
;
5413 struct listnode
*node
, *nnode
;
5415 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_LOCAL_AS
))
5418 /* Inherit configuration from peer-group if peer is member. */
5419 if (peer_group_active(peer
)) {
5420 peer_flag_inherit(peer
, PEER_FLAG_LOCAL_AS
);
5421 peer_flag_inherit(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5422 peer_flag_inherit(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5423 PEER_ATTR_INHERIT(peer
, peer
->group
, change_local_as
);
5425 /* Otherwise remove flag and configuration from peer. */
5426 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS
);
5427 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5428 peer_flag_unset(peer
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5429 peer
->change_local_as
= 0;
5432 /* Check if handling a regular peer. */
5433 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5434 /* Send notification or stop peer depending on state. */
5435 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
)) {
5436 peer
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5437 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5438 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5440 BGP_EVENT_ADD(peer
, BGP_Stop
);
5442 /* Skip peer-group mechanics for regular peers. */
5447 * Remove flag and configuration from all peer-group members, unless
5448 * they are explicitely overriding peer-group configuration.
5450 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5451 /* Skip peers with overridden configuration. */
5452 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_LOCAL_AS
))
5455 /* Remove flag and configuration on peer-group member. */
5456 UNSET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS
);
5457 UNSET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_NO_PREPEND
);
5458 UNSET_FLAG(member
->flags
, PEER_FLAG_LOCAL_AS_REPLACE_AS
);
5459 member
->change_local_as
= 0;
5461 /* Send notification or stop peer depending on state. */
5462 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
)) {
5463 member
->last_reset
= PEER_DOWN_LOCAL_AS_CHANGE
;
5464 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5465 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5467 bgp_session_reset(member
);
5473 /* Set password for authenticating with the peer. */
5474 int peer_password_set(struct peer
*peer
, const char *password
)
5476 struct peer
*member
;
5477 struct listnode
*node
, *nnode
;
5478 int len
= password
? strlen(password
) : 0;
5479 int ret
= BGP_SUCCESS
;
5481 if ((len
< PEER_PASSWORD_MINLEN
) || (len
> PEER_PASSWORD_MAXLEN
))
5482 return BGP_ERR_INVALID_VALUE
;
5484 /* Set flag and configuration on peer. */
5485 peer_flag_set(peer
, PEER_FLAG_PASSWORD
);
5486 if (peer
->password
&& strcmp(peer
->password
, password
) == 0)
5488 XFREE(MTYPE_PEER_PASSWORD
, peer
->password
);
5489 peer
->password
= XSTRDUP(MTYPE_PEER_PASSWORD
, password
);
5491 /* Check if handling a regular peer. */
5492 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5493 /* Send notification or reset peer depending on state. */
5494 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
5495 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5496 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5498 bgp_session_reset(peer
);
5501 * Attempt to install password on socket and skip peer-group
5504 if (BGP_PEER_SU_UNSPEC(peer
))
5506 return (bgp_md5_set(peer
) >= 0) ? BGP_SUCCESS
5507 : BGP_ERR_TCPSIG_FAILED
;
5511 * Set flag and configuration on all peer-group members, unless they are
5512 * explicitely overriding peer-group configuration.
5514 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5515 /* Skip peers with overridden configuration. */
5516 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_PASSWORD
))
5519 /* Skip peers with the same password. */
5520 if (member
->password
&& strcmp(member
->password
, password
) == 0)
5523 /* Set flag and configuration on peer-group member. */
5524 SET_FLAG(member
->flags
, PEER_FLAG_PASSWORD
);
5525 if (member
->password
)
5526 XFREE(MTYPE_PEER_PASSWORD
, member
->password
);
5527 member
->password
= XSTRDUP(MTYPE_PEER_PASSWORD
, password
);
5529 /* Send notification or reset peer depending on state. */
5530 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
))
5531 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5532 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5534 bgp_session_reset(member
);
5536 /* Attempt to install password on socket. */
5537 if (!BGP_PEER_SU_UNSPEC(member
) && bgp_md5_set(member
) < 0)
5538 ret
= BGP_ERR_TCPSIG_FAILED
;
5541 /* Set flag and configuration on all peer-group listen ranges */
5542 struct listnode
*ln
;
5545 for (ALL_LIST_ELEMENTS_RO(peer
->group
->listen_range
[AFI_IP
], ln
, lr
))
5546 bgp_md5_set_prefix(lr
, password
);
5547 for (ALL_LIST_ELEMENTS_RO(peer
->group
->listen_range
[AFI_IP6
], ln
, lr
))
5548 bgp_md5_set_prefix(lr
, password
);
5553 int peer_password_unset(struct peer
*peer
)
5555 struct peer
*member
;
5556 struct listnode
*node
, *nnode
;
5558 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_PASSWORD
))
5561 /* Inherit configuration from peer-group if peer is member. */
5562 if (peer_group_active(peer
)) {
5563 peer_flag_inherit(peer
, PEER_FLAG_PASSWORD
);
5564 PEER_STR_ATTR_INHERIT(peer
, peer
->group
, password
,
5565 MTYPE_PEER_PASSWORD
);
5567 /* Otherwise remove flag and configuration from peer. */
5568 peer_flag_unset(peer
, PEER_FLAG_PASSWORD
);
5569 XFREE(MTYPE_PEER_PASSWORD
, peer
->password
);
5572 /* Check if handling a regular peer. */
5573 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5574 /* Send notification or reset peer depending on state. */
5575 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
5576 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
5577 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5579 bgp_session_reset(peer
);
5581 /* Attempt to uninstall password on socket. */
5582 if (!BGP_PEER_SU_UNSPEC(peer
))
5583 bgp_md5_unset(peer
);
5585 /* Skip peer-group mechanics for regular peers. */
5590 * Remove flag and configuration from all peer-group members, unless
5591 * they are explicitely overriding peer-group configuration.
5593 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5594 /* Skip peers with overridden configuration. */
5595 if (CHECK_FLAG(member
->flags_override
, PEER_FLAG_PASSWORD
))
5598 /* Remove flag and configuration on peer-group member. */
5599 UNSET_FLAG(member
->flags
, PEER_FLAG_PASSWORD
);
5600 XFREE(MTYPE_PEER_PASSWORD
, member
->password
);
5602 /* Send notification or reset peer depending on state. */
5603 if (BGP_IS_VALID_STATE_FOR_NOTIF(member
->status
))
5604 bgp_notify_send(member
, BGP_NOTIFY_CEASE
,
5605 BGP_NOTIFY_CEASE_CONFIG_CHANGE
);
5607 bgp_session_reset(member
);
5609 /* Attempt to uninstall password on socket. */
5610 if (!BGP_PEER_SU_UNSPEC(member
))
5611 bgp_md5_unset(member
);
5614 /* Set flag and configuration on all peer-group listen ranges */
5615 struct listnode
*ln
;
5618 for (ALL_LIST_ELEMENTS_RO(peer
->group
->listen_range
[AFI_IP
], ln
, lr
))
5619 bgp_md5_unset_prefix(lr
);
5620 for (ALL_LIST_ELEMENTS_RO(peer
->group
->listen_range
[AFI_IP6
], ln
, lr
))
5621 bgp_md5_unset_prefix(lr
);
5627 /* Set distribute list to the peer. */
5628 int peer_distribute_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
5631 struct peer
*member
;
5632 struct bgp_filter
*filter
;
5633 struct listnode
*node
, *nnode
;
5635 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5636 return BGP_ERR_INVALID_VALUE
;
5638 /* Set configuration on peer. */
5639 filter
= &peer
->filter
[afi
][safi
];
5640 if (filter
->plist
[direct
].name
)
5641 return BGP_ERR_PEER_FILTER_CONFLICT
;
5642 if (filter
->dlist
[direct
].name
)
5643 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->dlist
[direct
].name
);
5644 filter
->dlist
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5645 filter
->dlist
[direct
].alist
= access_list_lookup(afi
, name
);
5647 /* Check if handling a regular peer. */
5648 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5649 /* Set override-flag and process peer route updates. */
5650 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5651 PEER_FT_DISTRIBUTE_LIST
);
5652 peer_on_policy_change(peer
, afi
, safi
,
5653 (direct
== FILTER_OUT
) ? 1 : 0);
5655 /* Skip peer-group mechanics for regular peers. */
5660 * Set configuration on all peer-group members, un less they are
5661 * explicitely overriding peer-group configuration.
5663 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5664 /* Skip peers with overridden configuration. */
5665 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5666 PEER_FT_DISTRIBUTE_LIST
))
5669 /* Set configuration on peer-group member. */
5670 filter
= &member
->filter
[afi
][safi
];
5671 if (filter
->dlist
[direct
].name
)
5672 XFREE(MTYPE_BGP_FILTER_NAME
,
5673 filter
->dlist
[direct
].name
);
5674 filter
->dlist
[direct
].name
=
5675 XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5676 filter
->dlist
[direct
].alist
= access_list_lookup(afi
, name
);
5678 /* Process peer route updates. */
5679 peer_on_policy_change(member
, afi
, safi
,
5680 (direct
== FILTER_OUT
) ? 1 : 0);
5686 int peer_distribute_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
)
5688 struct peer
*member
;
5689 struct bgp_filter
*filter
;
5690 struct listnode
*node
, *nnode
;
5692 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5693 return BGP_ERR_INVALID_VALUE
;
5695 /* Unset override-flag unconditionally. */
5696 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5697 PEER_FT_DISTRIBUTE_LIST
);
5699 /* Inherit configuration from peer-group if peer is member. */
5700 if (peer_group_active(peer
)) {
5701 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
5702 filter
[afi
][safi
].dlist
[direct
].name
,
5703 MTYPE_BGP_FILTER_NAME
);
5704 PEER_ATTR_INHERIT(peer
, peer
->group
,
5705 filter
[afi
][safi
].dlist
[direct
].alist
);
5707 /* Otherwise remove configuration from peer. */
5708 filter
= &peer
->filter
[afi
][safi
];
5709 if (filter
->dlist
[direct
].name
)
5710 XFREE(MTYPE_BGP_FILTER_NAME
,
5711 filter
->dlist
[direct
].name
);
5712 filter
->dlist
[direct
].name
= NULL
;
5713 filter
->dlist
[direct
].alist
= NULL
;
5716 /* Check if handling a regular peer. */
5717 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5718 /* Process peer route updates. */
5719 peer_on_policy_change(peer
, afi
, safi
,
5720 (direct
== FILTER_OUT
) ? 1 : 0);
5722 /* Skip peer-group mechanics for regular peers. */
5727 * Remove configuration on all peer-group members, unless they are
5728 * explicitely overriding peer-group configuration.
5730 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5731 /* Skip peers with overridden configuration. */
5732 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5733 PEER_FT_DISTRIBUTE_LIST
))
5736 /* Remove configuration on peer-group member. */
5737 filter
= &member
->filter
[afi
][safi
];
5738 if (filter
->dlist
[direct
].name
)
5739 XFREE(MTYPE_BGP_FILTER_NAME
,
5740 filter
->dlist
[direct
].name
);
5741 filter
->dlist
[direct
].name
= NULL
;
5742 filter
->dlist
[direct
].alist
= NULL
;
5744 /* Process peer route updates. */
5745 peer_on_policy_change(member
, afi
, safi
,
5746 (direct
== FILTER_OUT
) ? 1 : 0);
5752 /* Update distribute list. */
5753 static void peer_distribute_update(struct access_list
*access
)
5758 struct listnode
*mnode
, *mnnode
;
5759 struct listnode
*node
, *nnode
;
5762 struct peer_group
*group
;
5763 struct bgp_filter
*filter
;
5765 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
)) {
5767 update_group_policy_update(bgp
, BGP_POLICY_FILTER_LIST
,
5768 access
->name
, 0, 0);
5769 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
5770 FOREACH_AFI_SAFI (afi
, safi
) {
5771 filter
= &peer
->filter
[afi
][safi
];
5773 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5775 if (filter
->dlist
[direct
].name
)
5776 filter
->dlist
[direct
]
5777 .alist
= access_list_lookup(
5779 filter
->dlist
[direct
]
5782 filter
->dlist
[direct
].alist
=
5787 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
5788 FOREACH_AFI_SAFI (afi
, safi
) {
5789 filter
= &group
->conf
->filter
[afi
][safi
];
5791 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5793 if (filter
->dlist
[direct
].name
)
5794 filter
->dlist
[direct
]
5795 .alist
= access_list_lookup(
5797 filter
->dlist
[direct
]
5800 filter
->dlist
[direct
].alist
=
5806 vnc_prefix_list_update(bgp
);
5811 /* Set prefix list to the peer. */
5812 int peer_prefix_list_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
5815 struct peer
*member
;
5816 struct bgp_filter
*filter
;
5817 struct listnode
*node
, *nnode
;
5819 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5820 return BGP_ERR_INVALID_VALUE
;
5822 /* Set configuration on peer. */
5823 filter
= &peer
->filter
[afi
][safi
];
5824 if (filter
->dlist
[direct
].name
)
5825 return BGP_ERR_PEER_FILTER_CONFLICT
;
5826 if (filter
->plist
[direct
].name
)
5827 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->plist
[direct
].name
);
5828 filter
->plist
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5829 filter
->plist
[direct
].plist
= prefix_list_lookup(afi
, name
);
5831 /* Check if handling a regular peer. */
5832 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5833 /* Set override-flag and process peer route updates. */
5834 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5835 PEER_FT_PREFIX_LIST
);
5836 peer_on_policy_change(peer
, afi
, safi
,
5837 (direct
== FILTER_OUT
) ? 1 : 0);
5839 /* Skip peer-group mechanics for regular peers. */
5844 * Set configuration on all peer-group members, unless they are
5845 * explicitely overriding peer-group configuration.
5847 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5848 /* Skip peers with overridden configuration. */
5849 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5850 PEER_FT_PREFIX_LIST
))
5853 /* Set configuration on peer-group member. */
5854 filter
= &member
->filter
[afi
][safi
];
5855 if (filter
->plist
[direct
].name
)
5856 XFREE(MTYPE_BGP_FILTER_NAME
,
5857 filter
->plist
[direct
].name
);
5858 filter
->plist
[direct
].name
=
5859 XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
5860 filter
->plist
[direct
].plist
= prefix_list_lookup(afi
, name
);
5862 /* Process peer route updates. */
5863 peer_on_policy_change(member
, afi
, safi
,
5864 (direct
== FILTER_OUT
) ? 1 : 0);
5870 int peer_prefix_list_unset(struct peer
*peer
, afi_t afi
, safi_t safi
,
5873 struct peer
*member
;
5874 struct bgp_filter
*filter
;
5875 struct listnode
*node
, *nnode
;
5877 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
5878 return BGP_ERR_INVALID_VALUE
;
5880 /* Unset override-flag unconditionally. */
5881 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
5882 PEER_FT_PREFIX_LIST
);
5884 /* Inherit configuration from peer-group if peer is member. */
5885 if (peer_group_active(peer
)) {
5886 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
5887 filter
[afi
][safi
].plist
[direct
].name
,
5888 MTYPE_BGP_FILTER_NAME
);
5889 PEER_ATTR_INHERIT(peer
, peer
->group
,
5890 filter
[afi
][safi
].plist
[direct
].plist
);
5892 /* Otherwise remove configuration from peer. */
5893 filter
= &peer
->filter
[afi
][safi
];
5894 if (filter
->plist
[direct
].name
)
5895 XFREE(MTYPE_BGP_FILTER_NAME
,
5896 filter
->plist
[direct
].name
);
5897 filter
->plist
[direct
].name
= NULL
;
5898 filter
->plist
[direct
].plist
= NULL
;
5901 /* Check if handling a regular peer. */
5902 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
5903 /* Process peer route updates. */
5904 peer_on_policy_change(peer
, afi
, safi
,
5905 (direct
== FILTER_OUT
) ? 1 : 0);
5907 /* Skip peer-group mechanics for regular peers. */
5912 * Remove configuration on all peer-group members, unless they are
5913 * explicitely overriding peer-group configuration.
5915 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
5916 /* Skip peers with overridden configuration. */
5917 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
5918 PEER_FT_PREFIX_LIST
))
5921 /* Remove configuration on peer-group member. */
5922 filter
= &member
->filter
[afi
][safi
];
5923 if (filter
->plist
[direct
].name
)
5924 XFREE(MTYPE_BGP_FILTER_NAME
,
5925 filter
->plist
[direct
].name
);
5926 filter
->plist
[direct
].name
= NULL
;
5927 filter
->plist
[direct
].plist
= NULL
;
5929 /* Process peer route updates. */
5930 peer_on_policy_change(member
, afi
, safi
,
5931 (direct
== FILTER_OUT
) ? 1 : 0);
5937 /* Update prefix-list list. */
5938 static void peer_prefix_list_update(struct prefix_list
*plist
)
5940 struct listnode
*mnode
, *mnnode
;
5941 struct listnode
*node
, *nnode
;
5944 struct peer_group
*group
;
5945 struct bgp_filter
*filter
;
5950 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
)) {
5953 * Update the prefix-list on update groups.
5955 update_group_policy_update(
5956 bgp
, BGP_POLICY_PREFIX_LIST
,
5957 plist
? prefix_list_name(plist
) : NULL
, 0, 0);
5959 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
5960 FOREACH_AFI_SAFI (afi
, safi
) {
5961 filter
= &peer
->filter
[afi
][safi
];
5963 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5965 if (filter
->plist
[direct
].name
)
5966 filter
->plist
[direct
]
5967 .plist
= prefix_list_lookup(
5969 filter
->plist
[direct
]
5972 filter
->plist
[direct
].plist
=
5977 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
5978 FOREACH_AFI_SAFI (afi
, safi
) {
5979 filter
= &group
->conf
->filter
[afi
][safi
];
5981 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
5983 if (filter
->plist
[direct
].name
)
5984 filter
->plist
[direct
]
5985 .plist
= prefix_list_lookup(
5987 filter
->plist
[direct
]
5990 filter
->plist
[direct
].plist
=
5998 int peer_aslist_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
6001 struct peer
*member
;
6002 struct bgp_filter
*filter
;
6003 struct listnode
*node
, *nnode
;
6005 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
6006 return BGP_ERR_INVALID_VALUE
;
6008 /* Set configuration on peer. */
6009 filter
= &peer
->filter
[afi
][safi
];
6010 if (filter
->aslist
[direct
].name
)
6011 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->aslist
[direct
].name
);
6012 filter
->aslist
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6013 filter
->aslist
[direct
].aslist
= as_list_lookup(name
);
6015 /* Check if handling a regular peer. */
6016 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6017 /* Set override-flag and process peer route updates. */
6018 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
6019 PEER_FT_FILTER_LIST
);
6020 peer_on_policy_change(peer
, afi
, safi
,
6021 (direct
== FILTER_OUT
) ? 1 : 0);
6023 /* Skip peer-group mechanics for regular peers. */
6028 * Set configuration on all peer-group members, unless they are
6029 * explicitely overriding peer-group configuration.
6031 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6032 /* Skip peers with overridden configuration. */
6033 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
6034 PEER_FT_FILTER_LIST
))
6037 /* Set configuration on peer-group member. */
6038 filter
= &member
->filter
[afi
][safi
];
6039 if (filter
->aslist
[direct
].name
)
6040 XFREE(MTYPE_BGP_FILTER_NAME
,
6041 filter
->aslist
[direct
].name
);
6042 filter
->aslist
[direct
].name
=
6043 XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6044 filter
->aslist
[direct
].aslist
= as_list_lookup(name
);
6046 /* Process peer route updates. */
6047 peer_on_policy_change(member
, afi
, safi
,
6048 (direct
== FILTER_OUT
) ? 1 : 0);
6054 int peer_aslist_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
)
6056 struct peer
*member
;
6057 struct bgp_filter
*filter
;
6058 struct listnode
*node
, *nnode
;
6060 if (direct
!= FILTER_IN
&& direct
!= FILTER_OUT
)
6061 return BGP_ERR_INVALID_VALUE
;
6063 /* Unset override-flag unconditionally. */
6064 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
6065 PEER_FT_FILTER_LIST
);
6067 /* Inherit configuration from peer-group if peer is member. */
6068 if (peer_group_active(peer
)) {
6069 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
6070 filter
[afi
][safi
].aslist
[direct
].name
,
6071 MTYPE_BGP_FILTER_NAME
);
6072 PEER_ATTR_INHERIT(peer
, peer
->group
,
6073 filter
[afi
][safi
].aslist
[direct
].aslist
);
6075 /* Otherwise remove configuration from peer. */
6076 filter
= &peer
->filter
[afi
][safi
];
6077 if (filter
->aslist
[direct
].name
)
6078 XFREE(MTYPE_BGP_FILTER_NAME
,
6079 filter
->aslist
[direct
].name
);
6080 filter
->aslist
[direct
].name
= NULL
;
6081 filter
->aslist
[direct
].aslist
= NULL
;
6084 /* Check if handling a regular peer. */
6085 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6086 /* Process peer route updates. */
6087 peer_on_policy_change(peer
, afi
, safi
,
6088 (direct
== FILTER_OUT
) ? 1 : 0);
6090 /* Skip peer-group mechanics for regular peers. */
6095 * Remove configuration on all peer-group members, unless they are
6096 * explicitely overriding peer-group configuration.
6098 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6099 /* Skip peers with overridden configuration. */
6100 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
6101 PEER_FT_FILTER_LIST
))
6104 /* Remove configuration on peer-group member. */
6105 filter
= &member
->filter
[afi
][safi
];
6106 if (filter
->aslist
[direct
].name
)
6107 XFREE(MTYPE_BGP_FILTER_NAME
,
6108 filter
->aslist
[direct
].name
);
6109 filter
->aslist
[direct
].name
= NULL
;
6110 filter
->aslist
[direct
].aslist
= NULL
;
6112 /* Process peer route updates. */
6113 peer_on_policy_change(member
, afi
, safi
,
6114 (direct
== FILTER_OUT
) ? 1 : 0);
6120 static void peer_aslist_update(const char *aslist_name
)
6125 struct listnode
*mnode
, *mnnode
;
6126 struct listnode
*node
, *nnode
;
6129 struct peer_group
*group
;
6130 struct bgp_filter
*filter
;
6132 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
)) {
6133 update_group_policy_update(bgp
, BGP_POLICY_FILTER_LIST
,
6136 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
6137 FOREACH_AFI_SAFI (afi
, safi
) {
6138 filter
= &peer
->filter
[afi
][safi
];
6140 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
6142 if (filter
->aslist
[direct
].name
)
6143 filter
->aslist
[direct
]
6144 .aslist
= as_list_lookup(
6145 filter
->aslist
[direct
]
6148 filter
->aslist
[direct
].aslist
=
6153 for (ALL_LIST_ELEMENTS(bgp
->group
, node
, nnode
, group
)) {
6154 FOREACH_AFI_SAFI (afi
, safi
) {
6155 filter
= &group
->conf
->filter
[afi
][safi
];
6157 for (direct
= FILTER_IN
; direct
< FILTER_MAX
;
6159 if (filter
->aslist
[direct
].name
)
6160 filter
->aslist
[direct
]
6161 .aslist
= as_list_lookup(
6162 filter
->aslist
[direct
]
6165 filter
->aslist
[direct
].aslist
=
6173 static void peer_aslist_add(char *aslist_name
)
6175 peer_aslist_update(aslist_name
);
6176 route_map_notify_dependencies((char *)aslist_name
,
6177 RMAP_EVENT_ASLIST_ADDED
);
6180 static void peer_aslist_del(const char *aslist_name
)
6182 peer_aslist_update(aslist_name
);
6183 route_map_notify_dependencies(aslist_name
, RMAP_EVENT_ASLIST_DELETED
);
6187 int peer_route_map_set(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
,
6188 const char *name
, struct route_map
*route_map
)
6190 struct peer
*member
;
6191 struct bgp_filter
*filter
;
6192 struct listnode
*node
, *nnode
;
6194 if (direct
!= RMAP_IN
&& direct
!= RMAP_OUT
)
6195 return BGP_ERR_INVALID_VALUE
;
6197 /* Set configuration on peer. */
6198 filter
= &peer
->filter
[afi
][safi
];
6199 if (filter
->map
[direct
].name
) {
6200 /* If the neighbor is configured with the same route-map
6201 * again then, ignore the duplicate configuration.
6203 if (strcmp(filter
->map
[direct
].name
, name
) == 0)
6206 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6208 route_map_counter_decrement(filter
->map
[direct
].map
);
6209 filter
->map
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6210 filter
->map
[direct
].map
= route_map
;
6211 route_map_counter_increment(route_map
);
6213 /* Check if handling a regular peer. */
6214 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6215 /* Set override-flag and process peer route updates. */
6216 SET_FLAG(peer
->filter_override
[afi
][safi
][direct
],
6218 peer_on_policy_change(peer
, afi
, safi
,
6219 (direct
== RMAP_OUT
) ? 1 : 0);
6221 /* Skip peer-group mechanics for regular peers. */
6226 * Set configuration on all peer-group members, unless they are
6227 * explicitely overriding peer-group configuration.
6229 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6230 /* Skip peers with overridden configuration. */
6231 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
6235 /* Set configuration on peer-group member. */
6236 filter
= &member
->filter
[afi
][safi
];
6237 if (filter
->map
[direct
].name
)
6238 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6239 route_map_counter_decrement(filter
->map
[direct
].map
);
6240 filter
->map
[direct
].name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6241 filter
->map
[direct
].map
= route_map
;
6242 route_map_counter_increment(route_map
);
6244 /* Process peer route updates. */
6245 peer_on_policy_change(member
, afi
, safi
,
6246 (direct
== RMAP_OUT
) ? 1 : 0);
6251 /* Unset route-map from the peer. */
6252 int peer_route_map_unset(struct peer
*peer
, afi_t afi
, safi_t safi
, int direct
)
6254 struct peer
*member
;
6255 struct bgp_filter
*filter
;
6256 struct listnode
*node
, *nnode
;
6258 if (direct
!= RMAP_IN
&& direct
!= RMAP_OUT
)
6259 return BGP_ERR_INVALID_VALUE
;
6261 /* Unset override-flag unconditionally. */
6262 UNSET_FLAG(peer
->filter_override
[afi
][safi
][direct
], PEER_FT_ROUTE_MAP
);
6264 /* Inherit configuration from peer-group if peer is member. */
6265 if (peer_group_active(peer
)) {
6266 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
6267 filter
[afi
][safi
].map
[direct
].name
,
6268 MTYPE_BGP_FILTER_NAME
);
6269 PEER_ATTR_INHERIT(peer
, peer
->group
,
6270 filter
[afi
][safi
].map
[direct
].map
);
6272 /* Otherwise remove configuration from peer. */
6273 filter
= &peer
->filter
[afi
][safi
];
6274 if (filter
->map
[direct
].name
)
6275 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6276 route_map_counter_decrement(filter
->map
[direct
].map
);
6277 filter
->map
[direct
].name
= NULL
;
6278 filter
->map
[direct
].map
= NULL
;
6281 /* Check if handling a regular peer. */
6282 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6283 /* Process peer route updates. */
6284 peer_on_policy_change(peer
, afi
, safi
,
6285 (direct
== RMAP_OUT
) ? 1 : 0);
6287 /* Skip peer-group mechanics for regular peers. */
6292 * Remove configuration on all peer-group members, unless they are
6293 * explicitely overriding peer-group configuration.
6295 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6296 /* Skip peers with overridden configuration. */
6297 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][direct
],
6301 /* Remove configuration on peer-group member. */
6302 filter
= &member
->filter
[afi
][safi
];
6303 if (filter
->map
[direct
].name
)
6304 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->map
[direct
].name
);
6305 route_map_counter_decrement(filter
->map
[direct
].map
);
6306 filter
->map
[direct
].name
= NULL
;
6307 filter
->map
[direct
].map
= NULL
;
6309 /* Process peer route updates. */
6310 peer_on_policy_change(member
, afi
, safi
,
6311 (direct
== RMAP_OUT
) ? 1 : 0);
6317 /* Set unsuppress-map to the peer. */
6318 int peer_unsuppress_map_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
6319 const char *name
, struct route_map
*route_map
)
6321 struct peer
*member
;
6322 struct bgp_filter
*filter
;
6323 struct listnode
*node
, *nnode
;
6325 /* Set configuration on peer. */
6326 filter
= &peer
->filter
[afi
][safi
];
6327 if (filter
->usmap
.name
)
6328 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6329 route_map_counter_decrement(filter
->usmap
.map
);
6330 filter
->usmap
.name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6331 filter
->usmap
.map
= route_map
;
6332 route_map_counter_increment(route_map
);
6334 /* Check if handling a regular peer. */
6335 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6336 /* Set override-flag and process peer route updates. */
6337 SET_FLAG(peer
->filter_override
[afi
][safi
][0],
6338 PEER_FT_UNSUPPRESS_MAP
);
6339 peer_on_policy_change(peer
, afi
, safi
, 1);
6341 /* Skip peer-group mechanics for regular peers. */
6346 * Set configuration on all peer-group members, unless they are
6347 * explicitely overriding peer-group configuration.
6349 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6350 /* Skip peers with overridden configuration. */
6351 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][0],
6352 PEER_FT_UNSUPPRESS_MAP
))
6355 /* Set configuration on peer-group member. */
6356 filter
= &member
->filter
[afi
][safi
];
6357 if (filter
->usmap
.name
)
6358 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6359 route_map_counter_decrement(filter
->usmap
.map
);
6360 filter
->usmap
.name
= XSTRDUP(MTYPE_BGP_FILTER_NAME
, name
);
6361 filter
->usmap
.map
= route_map
;
6362 route_map_counter_increment(route_map
);
6364 /* Process peer route updates. */
6365 peer_on_policy_change(member
, afi
, safi
, 1);
6371 /* Unset route-map from the peer. */
6372 int peer_unsuppress_map_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
6374 struct peer
*member
;
6375 struct bgp_filter
*filter
;
6376 struct listnode
*node
, *nnode
;
6378 /* Unset override-flag unconditionally. */
6379 UNSET_FLAG(peer
->filter_override
[afi
][safi
][0], PEER_FT_UNSUPPRESS_MAP
);
6381 /* Inherit configuration from peer-group if peer is member. */
6382 if (peer_group_active(peer
)) {
6383 PEER_STR_ATTR_INHERIT(peer
, peer
->group
,
6384 filter
[afi
][safi
].usmap
.name
,
6385 MTYPE_BGP_FILTER_NAME
);
6386 PEER_ATTR_INHERIT(peer
, peer
->group
,
6387 filter
[afi
][safi
].usmap
.map
);
6389 /* Otherwise remove configuration from peer. */
6390 filter
= &peer
->filter
[afi
][safi
];
6391 if (filter
->usmap
.name
)
6392 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6393 route_map_counter_decrement(filter
->usmap
.map
);
6394 filter
->usmap
.name
= NULL
;
6395 filter
->usmap
.map
= NULL
;
6398 /* Check if handling a regular peer. */
6399 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6400 /* Process peer route updates. */
6401 peer_on_policy_change(peer
, afi
, safi
, 1);
6403 /* Skip peer-group mechanics for regular peers. */
6408 * Remove configuration on all peer-group members, unless they are
6409 * explicitely overriding peer-group configuration.
6411 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6412 /* Skip peers with overridden configuration. */
6413 if (CHECK_FLAG(member
->filter_override
[afi
][safi
][0],
6414 PEER_FT_UNSUPPRESS_MAP
))
6417 /* Remove configuration on peer-group member. */
6418 filter
= &member
->filter
[afi
][safi
];
6419 if (filter
->usmap
.name
)
6420 XFREE(MTYPE_BGP_FILTER_NAME
, filter
->usmap
.name
);
6421 route_map_counter_decrement(filter
->usmap
.map
);
6422 filter
->usmap
.name
= NULL
;
6423 filter
->usmap
.map
= NULL
;
6425 /* Process peer route updates. */
6426 peer_on_policy_change(member
, afi
, safi
, 1);
6432 int peer_maximum_prefix_set(struct peer
*peer
, afi_t afi
, safi_t safi
,
6433 uint32_t max
, uint8_t threshold
, int warning
,
6436 struct peer
*member
;
6437 struct listnode
*node
, *nnode
;
6439 /* Set flags and configuration on peer. */
6440 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX
);
6442 peer_af_flag_set(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX_WARNING
);
6444 peer_af_flag_unset(peer
, afi
, safi
,
6445 PEER_FLAG_MAX_PREFIX_WARNING
);
6447 peer
->pmax
[afi
][safi
] = max
;
6448 peer
->pmax_threshold
[afi
][safi
] = threshold
;
6449 peer
->pmax_restart
[afi
][safi
] = restart
;
6451 /* Check if handling a regular peer. */
6452 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6453 /* Re-check if peer violates maximum-prefix. */
6454 if ((peer
->status
== Established
) && (peer
->afc
[afi
][safi
]))
6455 bgp_maximum_prefix_overflow(peer
, afi
, safi
, 1);
6457 /* Skip peer-group mechanics for regular peers. */
6462 * Set flags and configuration on all peer-group members, unless they
6463 * are explicitely overriding peer-group configuration.
6465 for (ALL_LIST_ELEMENTS(peer
->group
->peer
, node
, nnode
, member
)) {
6466 /* Skip peers with overridden configuration. */
6467 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
6468 PEER_FLAG_MAX_PREFIX
))
6471 /* Set flag and configuration on peer-group member. */
6472 member
->pmax
[afi
][safi
] = max
;
6473 member
->pmax_threshold
[afi
][safi
] = threshold
;
6474 member
->pmax_restart
[afi
][safi
] = restart
;
6476 SET_FLAG(member
->af_flags
[afi
][safi
],
6477 PEER_FLAG_MAX_PREFIX_WARNING
);
6479 UNSET_FLAG(member
->af_flags
[afi
][safi
],
6480 PEER_FLAG_MAX_PREFIX_WARNING
);
6482 /* Re-check if peer violates maximum-prefix. */
6483 if ((member
->status
== Established
) && (member
->afc
[afi
][safi
]))
6484 bgp_maximum_prefix_overflow(member
, afi
, safi
, 1);
6490 int peer_maximum_prefix_unset(struct peer
*peer
, afi_t afi
, safi_t safi
)
6492 /* Inherit configuration from peer-group if peer is member. */
6493 if (peer_group_active(peer
)) {
6494 peer_af_flag_inherit(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX
);
6495 peer_af_flag_inherit(peer
, afi
, safi
,
6496 PEER_FLAG_MAX_PREFIX_WARNING
);
6497 PEER_ATTR_INHERIT(peer
, peer
->group
, pmax
[afi
][safi
]);
6498 PEER_ATTR_INHERIT(peer
, peer
->group
, pmax_threshold
[afi
][safi
]);
6499 PEER_ATTR_INHERIT(peer
, peer
->group
, pmax_restart
[afi
][safi
]);
6504 /* Remove flags and configuration from peer. */
6505 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX
);
6506 peer_af_flag_unset(peer
, afi
, safi
, PEER_FLAG_MAX_PREFIX_WARNING
);
6507 peer
->pmax
[afi
][safi
] = 0;
6508 peer
->pmax_threshold
[afi
][safi
] = 0;
6509 peer
->pmax_restart
[afi
][safi
] = 0;
6512 * Remove flags and configuration from all peer-group members, unless
6513 * they are explicitely overriding peer-group configuration.
6515 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6516 struct peer
*member
;
6517 struct listnode
*node
;
6519 for (ALL_LIST_ELEMENTS_RO(peer
->group
->peer
, node
, member
)) {
6520 /* Skip peers with overridden configuration. */
6521 if (CHECK_FLAG(member
->af_flags_override
[afi
][safi
],
6522 PEER_FLAG_MAX_PREFIX
))
6525 /* Remove flag and configuration on peer-group member.
6527 UNSET_FLAG(member
->af_flags
[afi
][safi
],
6528 PEER_FLAG_MAX_PREFIX
);
6529 UNSET_FLAG(member
->af_flags
[afi
][safi
],
6530 PEER_FLAG_MAX_PREFIX_WARNING
);
6531 member
->pmax
[afi
][safi
] = 0;
6532 member
->pmax_threshold
[afi
][safi
] = 0;
6533 member
->pmax_restart
[afi
][safi
] = 0;
6540 int is_ebgp_multihop_configured(struct peer
*peer
)
6542 struct peer_group
*group
;
6543 struct listnode
*node
, *nnode
;
6546 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6547 group
= peer
->group
;
6548 if ((peer_sort(peer
) != BGP_PEER_IBGP
)
6549 && (group
->conf
->ttl
!= BGP_DEFAULT_TTL
))
6552 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer1
)) {
6553 if ((peer_sort(peer1
) != BGP_PEER_IBGP
)
6554 && (peer1
->ttl
!= BGP_DEFAULT_TTL
))
6558 if ((peer_sort(peer
) != BGP_PEER_IBGP
)
6559 && (peer
->ttl
!= BGP_DEFAULT_TTL
))
6565 /* Set # of hops between us and BGP peer. */
6566 int peer_ttl_security_hops_set(struct peer
*peer
, int gtsm_hops
)
6568 struct peer_group
*group
;
6569 struct listnode
*node
, *nnode
;
6572 zlog_debug("peer_ttl_security_hops_set: set gtsm_hops to %d for %s",
6573 gtsm_hops
, peer
->host
);
6575 /* We cannot configure ttl-security hops when ebgp-multihop is already
6576 set. For non peer-groups, the check is simple. For peer-groups,
6578 slightly messy, because we need to check both the peer-group
6580 and all peer-group members for any trace of ebgp-multihop
6582 before actually applying the ttl-security rules. Cisco really made a
6583 mess of this configuration parameter, and OpenBGPD got it right.
6586 if ((peer
->gtsm_hops
== BGP_GTSM_HOPS_DISABLED
)
6587 && (peer
->sort
!= BGP_PEER_IBGP
)) {
6588 if (is_ebgp_multihop_configured(peer
))
6589 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK
;
6591 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6592 peer
->gtsm_hops
= gtsm_hops
;
6594 /* Calling ebgp multihop also resets the session.
6595 * On restart, NHT will get setup correctly as will the
6596 * min & max ttls on the socket. The return value is
6599 ret
= peer_ebgp_multihop_set(peer
, MAXTTL
);
6604 group
= peer
->group
;
6605 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
,
6607 peer
->gtsm_hops
= group
->conf
->gtsm_hops
;
6609 /* Calling ebgp multihop also resets the
6611 * On restart, NHT will get setup correctly as
6613 * min & max ttls on the socket. The return
6617 peer_ebgp_multihop_set(peer
, MAXTTL
);
6621 /* Post the first gtsm setup or if its ibgp, maxttl setting
6623 * necessary, just set the minttl.
6625 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6626 peer
->gtsm_hops
= gtsm_hops
;
6629 sockopt_minttl(peer
->su
.sa
.sa_family
, peer
->fd
,
6630 MAXTTL
+ 1 - gtsm_hops
);
6631 if ((peer
->status
< Established
) && peer
->doppelganger
6632 && (peer
->doppelganger
->fd
>= 0))
6633 sockopt_minttl(peer
->su
.sa
.sa_family
,
6634 peer
->doppelganger
->fd
,
6635 MAXTTL
+ 1 - gtsm_hops
);
6637 group
= peer
->group
;
6638 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
,
6640 peer
->gtsm_hops
= group
->conf
->gtsm_hops
;
6642 /* Change setting of existing peer
6643 * established then change value (may break
6645 * not established yet (teardown session and
6647 * no session then do nothing (will get
6648 * handled by next connection)
6652 != BGP_GTSM_HOPS_DISABLED
)
6654 peer
->su
.sa
.sa_family
, peer
->fd
,
6655 MAXTTL
+ 1 - peer
->gtsm_hops
);
6656 if ((peer
->status
< Established
)
6657 && peer
->doppelganger
6658 && (peer
->doppelganger
->fd
>= 0))
6659 sockopt_minttl(peer
->su
.sa
.sa_family
,
6660 peer
->doppelganger
->fd
,
6661 MAXTTL
+ 1 - gtsm_hops
);
6669 int peer_ttl_security_hops_unset(struct peer
*peer
)
6671 struct peer_group
*group
;
6672 struct listnode
*node
, *nnode
;
6675 zlog_debug("peer_ttl_security_hops_unset: set gtsm_hops to zero for %s",
6678 /* if a peer-group member, then reset to peer-group default rather than
6680 if (peer_group_active(peer
))
6681 peer
->gtsm_hops
= peer
->group
->conf
->gtsm_hops
;
6683 peer
->gtsm_hops
= BGP_GTSM_HOPS_DISABLED
;
6685 if (!CHECK_FLAG(peer
->sflags
, PEER_STATUS_GROUP
)) {
6686 /* Invoking ebgp_multihop_set will set the TTL back to the
6688 * value as well as restting the NHT and such. The session is
6691 if (peer
->sort
== BGP_PEER_EBGP
)
6692 ret
= peer_ebgp_multihop_unset(peer
);
6695 sockopt_minttl(peer
->su
.sa
.sa_family
, peer
->fd
,
6698 if ((peer
->status
< Established
) && peer
->doppelganger
6699 && (peer
->doppelganger
->fd
>= 0))
6700 sockopt_minttl(peer
->su
.sa
.sa_family
,
6701 peer
->doppelganger
->fd
, 0);
6704 group
= peer
->group
;
6705 for (ALL_LIST_ELEMENTS(group
->peer
, node
, nnode
, peer
)) {
6706 peer
->gtsm_hops
= BGP_GTSM_HOPS_DISABLED
;
6707 if (peer
->sort
== BGP_PEER_EBGP
)
6708 ret
= peer_ebgp_multihop_unset(peer
);
6711 sockopt_minttl(peer
->su
.sa
.sa_family
,
6714 if ((peer
->status
< Established
)
6715 && peer
->doppelganger
6716 && (peer
->doppelganger
->fd
>= 0))
6717 sockopt_minttl(peer
->su
.sa
.sa_family
,
6718 peer
->doppelganger
->fd
,
6728 * If peer clear is invoked in a loop for all peers on the BGP instance,
6729 * it may end up freeing the doppelganger, and if this was the next node
6730 * to the current node, we would end up accessing the freed next node.
6731 * Pass along additional parameter which can be updated if next node
6732 * is freed; only required when walking the peer list on BGP instance.
6734 int peer_clear(struct peer
*peer
, struct listnode
**nnode
)
6736 if (!CHECK_FLAG(peer
->flags
, PEER_FLAG_SHUTDOWN
)) {
6737 if (CHECK_FLAG(peer
->sflags
, PEER_STATUS_PREFIX_OVERFLOW
)) {
6738 UNSET_FLAG(peer
->sflags
, PEER_STATUS_PREFIX_OVERFLOW
);
6739 if (peer
->t_pmax_restart
) {
6740 BGP_TIMER_OFF(peer
->t_pmax_restart
);
6741 if (bgp_debug_neighbor_events(peer
))
6743 "%s Maximum-prefix restart timer canceled",
6746 BGP_EVENT_ADD(peer
, BGP_Start
);
6750 peer
->v_start
= BGP_INIT_START_TIMER
;
6751 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer
->status
))
6752 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
6753 BGP_NOTIFY_CEASE_ADMIN_RESET
);
6755 bgp_session_reset_safe(peer
, nnode
);
6760 int peer_clear_soft(struct peer
*peer
, afi_t afi
, safi_t safi
,
6761 enum bgp_clear_type stype
)
6763 struct peer_af
*paf
;
6765 if (peer
->status
!= Established
)
6768 if (!peer
->afc
[afi
][safi
])
6769 return BGP_ERR_AF_UNCONFIGURED
;
6771 peer
->rtt
= sockopt_tcp_rtt(peer
->fd
);
6773 if (stype
== BGP_CLEAR_SOFT_OUT
|| stype
== BGP_CLEAR_SOFT_BOTH
) {
6774 /* Clear the "neighbor x.x.x.x default-originate" flag */
6775 paf
= peer_af_find(peer
, afi
, safi
);
6776 if (paf
&& paf
->subgroup
6777 && CHECK_FLAG(paf
->subgroup
->sflags
,
6778 SUBGRP_STATUS_DEFAULT_ORIGINATE
))
6779 UNSET_FLAG(paf
->subgroup
->sflags
,
6780 SUBGRP_STATUS_DEFAULT_ORIGINATE
);
6782 bgp_announce_route(peer
, afi
, safi
);
6785 if (stype
== BGP_CLEAR_SOFT_IN_ORF_PREFIX
) {
6786 if (CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6787 PEER_CAP_ORF_PREFIX_SM_ADV
)
6788 && (CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6789 PEER_CAP_ORF_PREFIX_RM_RCV
)
6790 || CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6791 PEER_CAP_ORF_PREFIX_RM_OLD_RCV
))) {
6792 struct bgp_filter
*filter
= &peer
->filter
[afi
][safi
];
6793 uint8_t prefix_type
;
6795 if (CHECK_FLAG(peer
->af_cap
[afi
][safi
],
6796 PEER_CAP_ORF_PREFIX_RM_RCV
))
6797 prefix_type
= ORF_TYPE_PREFIX
;
6799 prefix_type
= ORF_TYPE_PREFIX_OLD
;
6801 if (filter
->plist
[FILTER_IN
].plist
) {
6802 if (CHECK_FLAG(peer
->af_sflags
[afi
][safi
],
6803 PEER_STATUS_ORF_PREFIX_SEND
))
6804 bgp_route_refresh_send(
6805 peer
, afi
, safi
, prefix_type
,
6807 bgp_route_refresh_send(peer
, afi
, safi
,
6809 REFRESH_IMMEDIATE
, 0);
6811 if (CHECK_FLAG(peer
->af_sflags
[afi
][safi
],
6812 PEER_STATUS_ORF_PREFIX_SEND
))
6813 bgp_route_refresh_send(
6814 peer
, afi
, safi
, prefix_type
,
6815 REFRESH_IMMEDIATE
, 1);
6817 bgp_route_refresh_send(peer
, afi
, safi
,
6824 if (stype
== BGP_CLEAR_SOFT_IN
|| stype
== BGP_CLEAR_SOFT_BOTH
6825 || stype
== BGP_CLEAR_SOFT_IN_ORF_PREFIX
) {
6826 /* If neighbor has soft reconfiguration inbound flag.
6827 Use Adj-RIB-In database. */
6828 if (CHECK_FLAG(peer
->af_flags
[afi
][safi
],
6829 PEER_FLAG_SOFT_RECONFIG
))
6830 bgp_soft_reconfig_in(peer
, afi
, safi
);
6832 /* If neighbor has route refresh capability, send route
6834 message to the peer. */
6835 if (CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_OLD_RCV
)
6836 || CHECK_FLAG(peer
->cap
, PEER_CAP_REFRESH_NEW_RCV
))
6837 bgp_route_refresh_send(peer
, afi
, safi
, 0, 0,
6840 return BGP_ERR_SOFT_RECONFIG_UNCONFIGURED
;
6846 /* Display peer uptime.*/
6847 char *peer_uptime(time_t uptime2
, char *buf
, size_t len
, bool use_json
,
6850 time_t uptime1
, epoch_tbuf
;
6853 /* If there is no connection has been done before print `never'. */
6856 json_object_string_add(json
, "peerUptime", "never");
6857 json_object_int_add(json
, "peerUptimeMsec", 0);
6859 snprintf(buf
, len
, "never");
6863 /* Get current time. */
6864 uptime1
= bgp_clock();
6866 gmtime_r(&uptime1
, &tm
);
6868 if (uptime1
< ONE_DAY_SECOND
)
6869 snprintf(buf
, len
, "%02d:%02d:%02d", tm
.tm_hour
, tm
.tm_min
,
6871 else if (uptime1
< ONE_WEEK_SECOND
)
6872 snprintf(buf
, len
, "%dd%02dh%02dm", tm
.tm_yday
, tm
.tm_hour
,
6874 else if (uptime1
< ONE_YEAR_SECOND
)
6875 snprintf(buf
, len
, "%02dw%dd%02dh", tm
.tm_yday
/ 7,
6876 tm
.tm_yday
- ((tm
.tm_yday
/ 7) * 7), tm
.tm_hour
);
6878 snprintf(buf
, len
, "%02dy%02dw%dd", tm
.tm_year
- 70,
6880 tm
.tm_yday
- ((tm
.tm_yday
/ 7) * 7));
6883 epoch_tbuf
= time(NULL
) - uptime1
;
6884 json_object_string_add(json
, "peerUptime", buf
);
6885 json_object_int_add(json
, "peerUptimeMsec", uptime1
* 1000);
6886 json_object_int_add(json
, "peerUptimeEstablishedEpoch",
6893 void bgp_master_init(struct thread_master
*master
, const int buffer_size
)
6897 memset(&bgp_master
, 0, sizeof(struct bgp_master
));
6900 bm
->bgp
= list_new();
6901 bm
->listen_sockets
= list_new();
6902 bm
->port
= BGP_PORT_DEFAULT
;
6903 bm
->master
= master
;
6904 bm
->start_time
= bgp_clock();
6905 bm
->t_rmap_update
= NULL
;
6906 bm
->rmap_update_timer
= RMAP_DEFAULT_UPDATE_TIMER
;
6907 bm
->terminating
= false;
6908 bm
->socket_buffer
= buffer_size
;
6910 bgp_process_queue_init();
6913 /* init the rd id space.
6914 assign 0th index in the bitfield,
6915 so that we start with id 1
6917 bf_init(bm
->rd_idspace
, UINT16_MAX
);
6918 bf_assign_zero_index(bm
->rd_idspace
);
6920 /* mpls label dynamic allocation pool */
6921 bgp_lp_init(bm
->master
, &bm
->labelpool
);
6923 QOBJ_REG(bm
, bgp_master
);
6927 * Free up connected routes and interfaces for a BGP instance. Invoked upon
6928 * instance delete (non-default only) or BGP exit.
6930 static void bgp_if_finish(struct bgp
*bgp
)
6933 struct interface
*ifp
;
6935 vrf
= bgp_vrf_lookup_by_instance_type(bgp
);
6937 if (bgp
->inst_type
== BGP_INSTANCE_TYPE_VIEW
|| !vrf
)
6940 FOR_ALL_INTERFACES (vrf
, ifp
) {
6941 struct listnode
*c_node
, *c_nnode
;
6942 struct connected
*c
;
6944 for (ALL_LIST_ELEMENTS(ifp
->connected
, c_node
, c_nnode
, c
))
6945 bgp_connected_delete(bgp
, c
);
6949 static void bgp_viewvrf_autocomplete(vector comps
, struct cmd_token
*token
)
6951 struct vrf
*vrf
= NULL
;
6952 struct listnode
*next
;
6955 RB_FOREACH (vrf
, vrf_name_head
, &vrfs_by_name
)
6956 vector_set(comps
, XSTRDUP(MTYPE_COMPLETION
, vrf
->name
));
6958 for (ALL_LIST_ELEMENTS_RO(bm
->bgp
, next
, bgp
)) {
6959 if (bgp
->inst_type
!= BGP_INSTANCE_TYPE_VIEW
)
6962 vector_set(comps
, XSTRDUP(MTYPE_COMPLETION
, bgp
->name
));
6966 static void bgp_instasn_autocomplete(vector comps
, struct cmd_token
*token
)
6968 struct listnode
*next
, *next2
;
6969 struct bgp
*bgp
, *bgp2
;
6972 for (ALL_LIST_ELEMENTS_RO(bm
->bgp
, next
, bgp
)) {
6974 for (ALL_LIST_ELEMENTS_RO(bm
->bgp
, next2
, bgp2
)) {
6975 if (bgp2
->as
== bgp
->as
)
6983 snprintf(buf
, sizeof(buf
), "%u", bgp
->as
);
6984 vector_set(comps
, XSTRDUP(MTYPE_COMPLETION
, buf
));
6988 static const struct cmd_variable_handler bgp_viewvrf_var_handlers
[] = {
6989 {.tokenname
= "VIEWVRFNAME", .completions
= bgp_viewvrf_autocomplete
},
6990 {.varname
= "instasn", .completions
= bgp_instasn_autocomplete
},
6991 {.completions
= NULL
},
6994 struct frr_pthread
*bgp_pth_io
;
6995 struct frr_pthread
*bgp_pth_ka
;
6997 static void bgp_pthreads_init(void)
6999 assert(!bgp_pth_io
);
7000 assert(!bgp_pth_ka
);
7002 struct frr_pthread_attr io
= {
7003 .start
= frr_pthread_attr_default
.start
,
7004 .stop
= frr_pthread_attr_default
.stop
,
7006 struct frr_pthread_attr ka
= {
7007 .start
= bgp_keepalives_start
,
7008 .stop
= bgp_keepalives_stop
,
7010 bgp_pth_io
= frr_pthread_new(&io
, "BGP I/O thread", "bgpd_io");
7011 bgp_pth_ka
= frr_pthread_new(&ka
, "BGP Keepalives thread", "bgpd_ka");
7014 void bgp_pthreads_run(void)
7016 frr_pthread_run(bgp_pth_io
, NULL
);
7017 frr_pthread_run(bgp_pth_ka
, NULL
);
7019 /* Wait until threads are ready. */
7020 frr_pthread_wait_running(bgp_pth_io
);
7021 frr_pthread_wait_running(bgp_pth_ka
);
7024 void bgp_pthreads_finish(void)
7026 frr_pthread_stop_all();
7029 void bgp_init(unsigned short instance
)
7032 /* allocates some vital data structures used by peer commands in
7035 /* pre-init pthreads */
7036 bgp_pthreads_init();
7039 bgp_zebra_init(bm
->master
, instance
);
7042 vnc_zebra_init(bm
->master
);
7045 /* BGP VTY commands installation. */
7053 bgp_route_map_init();
7054 bgp_scan_vty_init();
7059 bgp_ethernetvpn_init();
7060 bgp_flowspec_vty_init();
7062 /* Access list initialize. */
7064 access_list_add_hook(peer_distribute_update
);
7065 access_list_delete_hook(peer_distribute_update
);
7067 /* Filter list initialize. */
7069 as_list_add_hook(peer_aslist_add
);
7070 as_list_delete_hook(peer_aslist_del
);
7072 /* Prefix list initialize.*/
7074 prefix_list_add_hook(peer_prefix_list_update
);
7075 prefix_list_delete_hook(peer_prefix_list_update
);
7077 /* Community list initialize. */
7078 bgp_clist
= community_list_init();
7083 cmd_variable_handler_register(bgp_viewvrf_var_handlers
);
7086 void bgp_terminate(void)
7090 struct listnode
*node
, *nnode
;
7091 struct listnode
*mnode
, *mnnode
;
7095 /* Close the listener sockets first as this prevents peers from
7097 * to reconnect on receiving the peer unconfig message. In the presence
7098 * of a large number of peers this will ensure that no peer is left with
7099 * a dangling connection
7101 /* reverse bgp_master_init */
7104 if (bm
->listen_sockets
)
7105 list_delete(&bm
->listen_sockets
);
7107 for (ALL_LIST_ELEMENTS(bm
->bgp
, mnode
, mnnode
, bgp
))
7108 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
))
7109 if (peer
->status
== Established
7110 || peer
->status
== OpenSent
7111 || peer
->status
== OpenConfirm
)
7112 bgp_notify_send(peer
, BGP_NOTIFY_CEASE
,
7113 BGP_NOTIFY_CEASE_PEER_UNCONFIG
);
7115 if (bm
->process_main_queue
)
7116 work_queue_free_and_null(&bm
->process_main_queue
);
7118 if (bm
->t_rmap_update
)
7119 BGP_TIMER_OFF(bm
->t_rmap_update
);
7124 struct peer
*peer_lookup_in_view(struct vty
*vty
, struct bgp
*bgp
,
7125 const char *ip_str
, bool use_json
)
7131 /* Get peer sockunion. */
7132 ret
= str2sockunion(ip_str
, &su
);
7134 peer
= peer_lookup_by_conf_if(bgp
, ip_str
);
7136 peer
= peer_lookup_by_hostname(bgp
, ip_str
);
7140 json_object
*json_no
= NULL
;
7141 json_no
= json_object_new_object();
7142 json_object_string_add(
7144 "malformedAddressOrName",
7146 vty_out(vty
, "%s\n",
7147 json_object_to_json_string_ext(
7149 JSON_C_TO_STRING_PRETTY
));
7150 json_object_free(json_no
);
7153 "%% Malformed address or name: %s\n",
7161 /* Peer structure lookup. */
7162 peer
= peer_lookup(bgp
, &su
);
7165 json_object
*json_no
= NULL
;
7166 json_no
= json_object_new_object();
7167 json_object_string_add(json_no
, "warning",
7168 "No such neighbor in this view/vrf");
7169 vty_out(vty
, "%s\n",
7170 json_object_to_json_string_ext(
7171 json_no
, JSON_C_TO_STRING_PRETTY
));
7172 json_object_free(json_no
);
7174 vty_out(vty
, "No such neighbor in this view/vrf\n");
7181 void bgp_gr_apply_running_config(void)
7183 struct peer
*peer
= NULL
;
7184 struct bgp
*bgp
= NULL
;
7185 struct listnode
*node
, *nnode
;
7186 bool gr_router_detected
= false;
7188 if (BGP_DEBUG(graceful_restart
, GRACEFUL_RESTART
))
7189 zlog_debug("[BGP_GR] %s called !", __func__
);
7191 for (ALL_LIST_ELEMENTS(bm
->bgp
, node
, nnode
, bgp
)) {
7192 for (ALL_LIST_ELEMENTS(bgp
->peer
, node
, nnode
, peer
)) {
7193 bgp_peer_gr_flags_update(peer
);
7194 if (CHECK_FLAG(peer
->flags
, PEER_FLAG_GRACEFUL_RESTART
))
7195 gr_router_detected
= true;
7198 if (gr_router_detected
7199 && bgp
->present_zebra_gr_state
== ZEBRA_GR_DISABLE
) {
7200 bgp_zebra_send_capabilities(bgp
, true);
7201 } else if (!gr_router_detected
7202 && bgp
->present_zebra_gr_state
== ZEBRA_GR_ENABLE
) {
7203 bgp_zebra_send_capabilities(bgp
, false);
7206 gr_router_detected
= false;