]> git.proxmox.com Git - mirror_frr.git/blob - bgpd/bgpd.c
bgpd: Replace bgp_flag_* to [UN]SET/CHECK_FLAG macros
[mirror_frr.git] / bgpd / bgpd.c
1 /* BGP-4, BGP-4+ daemon program
2 * Copyright (C) 1996, 97, 98, 99, 2000 Kunihiro Ishiguro
3 *
4 * This file is part of GNU Zebra.
5 *
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
9 * later version.
10 *
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.
15 *
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
19 */
20
21 #include <zebra.h>
22
23 #include "prefix.h"
24 #include "thread.h"
25 #include "buffer.h"
26 #include "stream.h"
27 #include "ringbuf.h"
28 #include "command.h"
29 #include "sockunion.h"
30 #include "sockopt.h"
31 #include "network.h"
32 #include "memory.h"
33 #include "filter.h"
34 #include "routemap.h"
35 #include "log.h"
36 #include "plist.h"
37 #include "linklist.h"
38 #include "workqueue.h"
39 #include "queue.h"
40 #include "zclient.h"
41 #include "bfd.h"
42 #include "hash.h"
43 #include "jhash.h"
44 #include "table.h"
45 #include "lib/json.h"
46 #include "frr_pthread.h"
47 #include "bitfield.h"
48
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"
68 #if ENABLE_BGP_VNC
69 #include "bgpd/rfapi/bgp_rfapi_cfg.h"
70 #include "bgpd/rfapi/rfapi_backend.h"
71 #endif
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"
91
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)
95 DEFINE_QOBJ_TYPE(bgp)
96 DEFINE_QOBJ_TYPE(peer)
97 DEFINE_HOOK(bgp_inst_delete, (struct bgp *bgp), (bgp))
98
99 /* BGP process wide configuration. */
100 static struct bgp_master bgp_master;
101
102 /* BGP process wide configuration pointer to export. */
103 struct bgp_master *bm;
104
105 /* BGP community-list. */
106 struct community_list_handler *bgp_clist;
107
108 unsigned int multipath_num = MULTIPATH_NUM;
109
110 static void bgp_if_finish(struct bgp *bgp);
111 static void peer_drop_dynamic_neighbor(struct peer *peer);
112
113 extern struct zclient *zclient;
114
115 /* handle main socket creation or deletion */
116 static int bgp_check_main_socket(bool create, struct bgp *bgp)
117 {
118 static int bgp_server_main_created;
119
120 if (create) {
121 if (bgp_server_main_created)
122 return 0;
123 if (bgp_socket(bgp, bm->port, bm->address) < 0)
124 return BGP_ERR_INVALID_VALUE;
125 bgp_server_main_created = 1;
126 return 0;
127 }
128 if (!bgp_server_main_created)
129 return 0;
130 bgp_close();
131 bgp_server_main_created = 0;
132 return 0;
133 }
134
135 void bgp_session_reset(struct peer *peer)
136 {
137 if (peer->doppelganger && (peer->doppelganger->status != Deleted)
138 && !(CHECK_FLAG(peer->doppelganger->flags, PEER_FLAG_CONFIG_NODE)))
139 peer_delete(peer->doppelganger);
140
141 BGP_EVENT_ADD(peer, BGP_Stop);
142 }
143
144 /*
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.
149 */
150 static void bgp_session_reset_safe(struct peer *peer, struct listnode **nnode)
151 {
152 struct listnode *n;
153 struct peer *npeer;
154
155 n = (nnode) ? *nnode : NULL;
156 npeer = (n) ? listgetdata(n) : NULL;
157
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);
165 }
166
167 BGP_EVENT_ADD(peer, BGP_Stop);
168 }
169
170 /* BGP global flag manipulation. */
171 int bgp_option_set(int flag)
172 {
173 switch (flag) {
174 case BGP_OPT_NO_FIB:
175 case BGP_OPT_NO_LISTEN:
176 case BGP_OPT_NO_ZEBRA:
177 SET_FLAG(bm->options, flag);
178 break;
179 default:
180 return BGP_ERR_INVALID_FLAG;
181 }
182 return 0;
183 }
184
185 int bgp_option_unset(int flag)
186 {
187 switch (flag) {
188 /* Fall through. */
189 case BGP_OPT_NO_ZEBRA:
190 case BGP_OPT_NO_FIB:
191 UNSET_FLAG(bm->options, flag);
192 break;
193 default:
194 return BGP_ERR_INVALID_FLAG;
195 }
196 return 0;
197 }
198
199 int bgp_option_check(int flag)
200 {
201 return CHECK_FLAG(bm->options, flag);
202 }
203
204 /* Internal function to set BGP structure configureation flag. */
205 static void bgp_config_set(struct bgp *bgp, int config)
206 {
207 SET_FLAG(bgp->config, config);
208 }
209
210 static void bgp_config_unset(struct bgp *bgp, int config)
211 {
212 UNSET_FLAG(bgp->config, config);
213 }
214
215 static int bgp_config_check(struct bgp *bgp, int config)
216 {
217 return CHECK_FLAG(bgp->config, config);
218 }
219
220 /* Set BGP router identifier; distinguish between explicit config and other
221 * cases.
222 */
223 static int bgp_router_id_set(struct bgp *bgp, const struct in_addr *id,
224 bool is_config)
225 {
226 struct peer *peer;
227 struct listnode *node, *nnode;
228
229 if (IPV4_ADDR_SAME(&bgp->router_id, id))
230 return 0;
231
232 /* EVPN uses router id in RD, withdraw them */
233 if (is_evpn_enabled())
234 bgp_evpn_handle_router_id_update(bgp, true);
235
236 vpn_handle_router_id_update(bgp, true, is_config);
237
238 IPV4_ADDR_COPY(&bgp->router_id, id);
239
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);
243
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);
248 }
249 }
250
251 /* EVPN uses router id in RD, update them */
252 if (is_evpn_enabled())
253 bgp_evpn_handle_router_id_update(bgp, false);
254
255 vpn_handle_router_id_update(bgp, false, is_config);
256
257 return 0;
258 }
259
260 void bgp_router_id_zebra_bump(vrf_id_t vrf_id, const struct prefix *router_id)
261 {
262 struct listnode *node, *nnode;
263 struct bgp *bgp;
264 struct in_addr *addr = NULL;
265
266 if (router_id != NULL)
267 addr = (struct in_addr *)&(router_id->u.prefix4);
268
269 if (vrf_id == VRF_DEFAULT) {
270 /* Router-id change for default VRF has to also update all
271 * views. */
272 for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp)) {
273 if (bgp->inst_type == BGP_INSTANCE_TYPE_VRF)
274 continue;
275
276 if (addr)
277 bgp->router_id_zebra = *addr;
278 else
279 addr = &bgp->router_id_zebra;
280
281 if (!bgp->router_id_static.s_addr) {
282 /* Router ID is updated if there are no active
283 * peer sessions
284 */
285 if (bgp->established_peers == 0) {
286 if (BGP_DEBUG(zebra, ZEBRA))
287 zlog_debug("RID change : vrf %u, RTR ID %s",
288 bgp->vrf_id, inet_ntoa(*addr));
289 bgp_router_id_set(bgp, addr, false);
290 }
291 }
292 }
293 } else {
294 bgp = bgp_lookup_by_vrf_id(vrf_id);
295 if (bgp) {
296 if (addr)
297 bgp->router_id_zebra = *addr;
298 else
299 addr = &bgp->router_id_zebra;
300
301 if (!bgp->router_id_static.s_addr) {
302 /* Router ID is updated if there are no active
303 * peer sessions
304 */
305 if (bgp->established_peers == 0) {
306 if (BGP_DEBUG(zebra, ZEBRA))
307 zlog_debug("RID change : vrf %u, RTR ID %s",
308 bgp->vrf_id, inet_ntoa(*addr));
309 bgp_router_id_set(bgp, addr, false);
310 }
311 }
312
313 }
314 }
315 }
316
317 int bgp_router_id_static_set(struct bgp *bgp, struct in_addr id)
318 {
319 bgp->router_id_static = id;
320 bgp_router_id_set(bgp,
321 id.s_addr != INADDR_ANY ? &id : &bgp->router_id_zebra,
322 true /* is config */);
323 return 0;
324 }
325
326 /* BGP's cluster-id control. */
327 int bgp_cluster_id_set(struct bgp *bgp, struct in_addr *cluster_id)
328 {
329 struct peer *peer;
330 struct listnode *node, *nnode;
331
332 if (bgp_config_check(bgp, BGP_CONFIG_CLUSTER_ID)
333 && IPV4_ADDR_SAME(&bgp->cluster_id, cluster_id))
334 return 0;
335
336 IPV4_ADDR_COPY(&bgp->cluster_id, cluster_id);
337 bgp_config_set(bgp, BGP_CONFIG_CLUSTER_ID);
338
339 /* Clear all IBGP peer. */
340 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
341 if (peer->sort != BGP_PEER_IBGP)
342 continue;
343
344 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
345 peer->last_reset = PEER_DOWN_CLID_CHANGE;
346 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
347 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
348 }
349 }
350 return 0;
351 }
352
353 int bgp_cluster_id_unset(struct bgp *bgp)
354 {
355 struct peer *peer;
356 struct listnode *node, *nnode;
357
358 if (!bgp_config_check(bgp, BGP_CONFIG_CLUSTER_ID))
359 return 0;
360
361 bgp->cluster_id.s_addr = 0;
362 bgp_config_unset(bgp, BGP_CONFIG_CLUSTER_ID);
363
364 /* Clear all IBGP peer. */
365 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
366 if (peer->sort != BGP_PEER_IBGP)
367 continue;
368
369 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
370 peer->last_reset = PEER_DOWN_CLID_CHANGE;
371 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
372 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
373 }
374 }
375 return 0;
376 }
377
378 /* time_t value that is monotonicly increasing
379 * and uneffected by adjustments to system clock
380 */
381 time_t bgp_clock(void)
382 {
383 struct timeval tv;
384
385 monotime(&tv);
386 return tv.tv_sec;
387 }
388
389 /* BGP timer configuration. */
390 int bgp_timers_set(struct bgp *bgp, uint32_t keepalive, uint32_t holdtime,
391 uint32_t connect_retry)
392 {
393 bgp->default_keepalive =
394 (keepalive < holdtime / 3 ? keepalive : holdtime / 3);
395 bgp->default_holdtime = holdtime;
396 bgp->default_connect_retry = connect_retry;
397
398 return 0;
399 }
400
401 /* mostly for completeness - CLI uses its own defaults */
402 int bgp_timers_unset(struct bgp *bgp)
403 {
404 bgp->default_keepalive = BGP_DEFAULT_KEEPALIVE;
405 bgp->default_holdtime = BGP_DEFAULT_HOLDTIME;
406 bgp->default_connect_retry = BGP_DEFAULT_CONNECT_RETRY;
407
408 return 0;
409 }
410
411 /* BGP confederation configuration. */
412 int bgp_confederation_id_set(struct bgp *bgp, as_t as)
413 {
414 struct peer *peer;
415 struct listnode *node, *nnode;
416 int already_confed;
417
418 if (as == 0)
419 return BGP_ERR_INVALID_AS;
420
421 /* Remember - were we doing confederation before? */
422 already_confed = bgp_config_check(bgp, BGP_CONFIG_CONFEDERATION);
423 bgp->confed_id = as;
424 bgp_config_set(bgp, BGP_CONFIG_CONFEDERATION);
425
426 /* If we were doing confederation already, this is just an external
427 AS change. Just Reset EBGP sessions, not CONFED sessions. If we
428 were not doing confederation before, reset all EBGP sessions. */
429 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
430 /* We're looking for peers who's AS is not local or part of our
431 confederation. */
432 if (already_confed) {
433 if (peer_sort(peer) == BGP_PEER_EBGP) {
434 peer->local_as = as;
435 if (BGP_IS_VALID_STATE_FOR_NOTIF(
436 peer->status)) {
437 peer->last_reset =
438 PEER_DOWN_CONFED_ID_CHANGE;
439 bgp_notify_send(
440 peer, BGP_NOTIFY_CEASE,
441 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
442 } else
443 bgp_session_reset_safe(peer, &nnode);
444 }
445 } else {
446 /* Not doign confederation before, so reset every
447 non-local
448 session */
449 if (peer_sort(peer) != BGP_PEER_IBGP) {
450 /* Reset the local_as to be our EBGP one */
451 if (peer_sort(peer) == BGP_PEER_EBGP)
452 peer->local_as = as;
453 if (BGP_IS_VALID_STATE_FOR_NOTIF(
454 peer->status)) {
455 peer->last_reset =
456 PEER_DOWN_CONFED_ID_CHANGE;
457 bgp_notify_send(
458 peer, BGP_NOTIFY_CEASE,
459 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
460 } else
461 bgp_session_reset_safe(peer, &nnode);
462 }
463 }
464 }
465 return 0;
466 }
467
468 int bgp_confederation_id_unset(struct bgp *bgp)
469 {
470 struct peer *peer;
471 struct listnode *node, *nnode;
472
473 bgp->confed_id = 0;
474 bgp_config_unset(bgp, BGP_CONFIG_CONFEDERATION);
475
476 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
477 /* We're looking for peers who's AS is not local */
478 if (peer_sort(peer) != BGP_PEER_IBGP) {
479 peer->local_as = bgp->as;
480 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
481 peer->last_reset = PEER_DOWN_CONFED_ID_CHANGE;
482 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
483 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
484 }
485
486 else
487 bgp_session_reset_safe(peer, &nnode);
488 }
489 }
490 return 0;
491 }
492
493 /* Is an AS part of the confed or not? */
494 int bgp_confederation_peers_check(struct bgp *bgp, as_t as)
495 {
496 int i;
497
498 if (!bgp)
499 return 0;
500
501 for (i = 0; i < bgp->confed_peers_cnt; i++)
502 if (bgp->confed_peers[i] == as)
503 return 1;
504
505 return 0;
506 }
507
508 /* Add an AS to the confederation set. */
509 int bgp_confederation_peers_add(struct bgp *bgp, as_t as)
510 {
511 struct peer *peer;
512 struct listnode *node, *nnode;
513
514 if (!bgp)
515 return BGP_ERR_INVALID_BGP;
516
517 if (bgp->as == as)
518 return BGP_ERR_INVALID_AS;
519
520 if (bgp_confederation_peers_check(bgp, as))
521 return -1;
522
523 if (bgp->confed_peers)
524 bgp->confed_peers =
525 XREALLOC(MTYPE_BGP_CONFED_LIST, bgp->confed_peers,
526 (bgp->confed_peers_cnt + 1) * sizeof(as_t));
527 else
528 bgp->confed_peers =
529 XMALLOC(MTYPE_BGP_CONFED_LIST,
530 (bgp->confed_peers_cnt + 1) * sizeof(as_t));
531
532 bgp->confed_peers[bgp->confed_peers_cnt] = as;
533 bgp->confed_peers_cnt++;
534
535 if (bgp_config_check(bgp, BGP_CONFIG_CONFEDERATION)) {
536 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
537 if (peer->as == as) {
538 peer->local_as = bgp->as;
539 if (BGP_IS_VALID_STATE_FOR_NOTIF(
540 peer->status)) {
541 peer->last_reset =
542 PEER_DOWN_CONFED_PEER_CHANGE;
543 bgp_notify_send(
544 peer, BGP_NOTIFY_CEASE,
545 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
546 } else
547 bgp_session_reset_safe(peer, &nnode);
548 }
549 }
550 }
551 return 0;
552 }
553
554 /* Delete an AS from the confederation set. */
555 int bgp_confederation_peers_remove(struct bgp *bgp, as_t as)
556 {
557 int i;
558 int j;
559 struct peer *peer;
560 struct listnode *node, *nnode;
561
562 if (!bgp)
563 return -1;
564
565 if (!bgp_confederation_peers_check(bgp, as))
566 return -1;
567
568 for (i = 0; i < bgp->confed_peers_cnt; i++)
569 if (bgp->confed_peers[i] == as)
570 for (j = i + 1; j < bgp->confed_peers_cnt; j++)
571 bgp->confed_peers[j - 1] = bgp->confed_peers[j];
572
573 bgp->confed_peers_cnt--;
574
575 if (bgp->confed_peers_cnt == 0) {
576 if (bgp->confed_peers)
577 XFREE(MTYPE_BGP_CONFED_LIST, bgp->confed_peers);
578 bgp->confed_peers = NULL;
579 } else
580 bgp->confed_peers =
581 XREALLOC(MTYPE_BGP_CONFED_LIST, bgp->confed_peers,
582 bgp->confed_peers_cnt * sizeof(as_t));
583
584 /* Now reset any peer who's remote AS has just been removed from the
585 CONFED */
586 if (bgp_config_check(bgp, BGP_CONFIG_CONFEDERATION)) {
587 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
588 if (peer->as == as) {
589 peer->local_as = bgp->confed_id;
590 if (BGP_IS_VALID_STATE_FOR_NOTIF(
591 peer->status)) {
592 peer->last_reset =
593 PEER_DOWN_CONFED_PEER_CHANGE;
594 bgp_notify_send(
595 peer, BGP_NOTIFY_CEASE,
596 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
597 } else
598 bgp_session_reset_safe(peer, &nnode);
599 }
600 }
601 }
602
603 return 0;
604 }
605
606 /* Local preference configuration. */
607 int bgp_default_local_preference_set(struct bgp *bgp, uint32_t local_pref)
608 {
609 if (!bgp)
610 return -1;
611
612 bgp->default_local_pref = local_pref;
613
614 return 0;
615 }
616
617 int bgp_default_local_preference_unset(struct bgp *bgp)
618 {
619 if (!bgp)
620 return -1;
621
622 bgp->default_local_pref = BGP_DEFAULT_LOCAL_PREF;
623
624 return 0;
625 }
626
627 /* Local preference configuration. */
628 int bgp_default_subgroup_pkt_queue_max_set(struct bgp *bgp, uint32_t queue_size)
629 {
630 if (!bgp)
631 return -1;
632
633 bgp->default_subgroup_pkt_queue_max = queue_size;
634
635 return 0;
636 }
637
638 int bgp_default_subgroup_pkt_queue_max_unset(struct bgp *bgp)
639 {
640 if (!bgp)
641 return -1;
642 bgp->default_subgroup_pkt_queue_max =
643 BGP_DEFAULT_SUBGROUP_PKT_QUEUE_MAX;
644
645 return 0;
646 }
647
648 /* Listen limit configuration. */
649 int bgp_listen_limit_set(struct bgp *bgp, int listen_limit)
650 {
651 if (!bgp)
652 return -1;
653
654 bgp->dynamic_neighbors_limit = listen_limit;
655
656 return 0;
657 }
658
659 int bgp_listen_limit_unset(struct bgp *bgp)
660 {
661 if (!bgp)
662 return -1;
663
664 bgp->dynamic_neighbors_limit = BGP_DYNAMIC_NEIGHBORS_LIMIT_DEFAULT;
665
666 return 0;
667 }
668
669 int bgp_map_afi_safi_iana2int(iana_afi_t pkt_afi, iana_safi_t pkt_safi,
670 afi_t *afi, safi_t *safi)
671 {
672 /* Map from IANA values to internal values, return error if
673 * values are unrecognized.
674 */
675 *afi = afi_iana2int(pkt_afi);
676 *safi = safi_iana2int(pkt_safi);
677 if (*afi == AFI_MAX || *safi == SAFI_MAX)
678 return -1;
679
680 return 0;
681 }
682
683 int bgp_map_afi_safi_int2iana(afi_t afi, safi_t safi, iana_afi_t *pkt_afi,
684 iana_safi_t *pkt_safi)
685 {
686 /* Map from internal values to IANA values, return error if
687 * internal values are bad (unexpected).
688 */
689 if (afi == AFI_MAX || safi == SAFI_MAX)
690 return -1;
691 *pkt_afi = afi_int2iana(afi);
692 *pkt_safi = safi_int2iana(safi);
693 return 0;
694 }
695
696 struct peer_af *peer_af_create(struct peer *peer, afi_t afi, safi_t safi)
697 {
698 struct peer_af *af;
699 int afid;
700 struct bgp *bgp;
701
702 if (!peer)
703 return NULL;
704
705 afid = afindex(afi, safi);
706 if (afid >= BGP_AF_MAX)
707 return NULL;
708
709 bgp = peer->bgp;
710 assert(peer->peer_af_array[afid] == NULL);
711
712 /* Allocate new peer af */
713 af = XCALLOC(MTYPE_BGP_PEER_AF, sizeof(struct peer_af));
714
715 peer->peer_af_array[afid] = af;
716 af->afi = afi;
717 af->safi = safi;
718 af->afid = afid;
719 af->peer = peer;
720 bgp->af_peer_count[afi][safi]++;
721
722 return af;
723 }
724
725 struct peer_af *peer_af_find(struct peer *peer, afi_t afi, safi_t safi)
726 {
727 int afid;
728
729 if (!peer)
730 return NULL;
731
732 afid = afindex(afi, safi);
733 if (afid >= BGP_AF_MAX)
734 return NULL;
735
736 return peer->peer_af_array[afid];
737 }
738
739 int peer_af_delete(struct peer *peer, afi_t afi, safi_t safi)
740 {
741 struct peer_af *af;
742 int afid;
743 struct bgp *bgp;
744
745 if (!peer)
746 return -1;
747
748 afid = afindex(afi, safi);
749 if (afid >= BGP_AF_MAX)
750 return -1;
751
752 af = peer->peer_af_array[afid];
753 if (!af)
754 return -1;
755
756 bgp = peer->bgp;
757 bgp_stop_announce_route_timer(af);
758
759 if (PAF_SUBGRP(af)) {
760 if (BGP_DEBUG(update_groups, UPDATE_GROUPS))
761 zlog_debug("u%" PRIu64 ":s%" PRIu64 " remove peer %s",
762 af->subgroup->update_group->id,
763 af->subgroup->id, peer->host);
764 }
765
766
767 update_subgroup_remove_peer(af->subgroup, af);
768
769 if (bgp->af_peer_count[afi][safi])
770 bgp->af_peer_count[afi][safi]--;
771
772 peer->peer_af_array[afid] = NULL;
773 XFREE(MTYPE_BGP_PEER_AF, af);
774 return 0;
775 }
776
777 /* Peer comparison function for sorting. */
778 int peer_cmp(struct peer *p1, struct peer *p2)
779 {
780 if (p1->group && !p2->group)
781 return -1;
782
783 if (!p1->group && p2->group)
784 return 1;
785
786 if (p1->group == p2->group) {
787 if (p1->conf_if && !p2->conf_if)
788 return -1;
789
790 if (!p1->conf_if && p2->conf_if)
791 return 1;
792
793 if (p1->conf_if && p2->conf_if)
794 return if_cmp_name_func(p1->conf_if, p2->conf_if);
795 } else
796 return strcmp(p1->group->name, p2->group->name);
797
798 return sockunion_cmp(&p1->su, &p2->su);
799 }
800
801 static unsigned int peer_hash_key_make(const void *p)
802 {
803 const struct peer *peer = p;
804 return sockunion_hash(&peer->su);
805 }
806
807 static bool peer_hash_same(const void *p1, const void *p2)
808 {
809 const struct peer *peer1 = p1;
810 const struct peer *peer2 = p2;
811 return (sockunion_same(&peer1->su, &peer2->su)
812 && CHECK_FLAG(peer1->flags, PEER_FLAG_CONFIG_NODE)
813 == CHECK_FLAG(peer2->flags, PEER_FLAG_CONFIG_NODE));
814 }
815
816 void peer_flag_inherit(struct peer *peer, uint32_t flag)
817 {
818 bool group_val;
819
820 /* Skip if peer is not a peer-group member. */
821 if (!peer_group_active(peer))
822 return;
823
824 /* Unset override flag to signal inheritance from peer-group. */
825 UNSET_FLAG(peer->flags_override, flag);
826
827 /*
828 * Inherit flag state from peer-group. If the flag of the peer-group is
829 * not being inverted, the peer must inherit the inverse of the current
830 * peer-group flag state.
831 */
832 group_val = CHECK_FLAG(peer->group->conf->flags, flag);
833 if (!CHECK_FLAG(peer->group->conf->flags_invert, flag)
834 && CHECK_FLAG(peer->flags_invert, flag))
835 COND_FLAG(peer->flags, flag, !group_val);
836 else
837 COND_FLAG(peer->flags, flag, group_val);
838 }
839
840 int peer_af_flag_check(struct peer *peer, afi_t afi, safi_t safi, uint32_t flag)
841 {
842 return CHECK_FLAG(peer->af_flags[afi][safi], flag);
843 }
844
845 void peer_af_flag_inherit(struct peer *peer, afi_t afi, safi_t safi,
846 uint32_t flag)
847 {
848 bool group_val;
849
850 /* Skip if peer is not a peer-group member. */
851 if (!peer_group_active(peer))
852 return;
853
854 /* Unset override flag to signal inheritance from peer-group. */
855 UNSET_FLAG(peer->af_flags_override[afi][safi], flag);
856
857 /*
858 * Inherit flag state from peer-group. If the flag of the peer-group is
859 * not being inverted, the peer must inherit the inverse of the current
860 * peer-group flag state.
861 */
862 group_val = CHECK_FLAG(peer->group->conf->af_flags[afi][safi], flag);
863 if (!CHECK_FLAG(peer->group->conf->af_flags_invert[afi][safi], flag)
864 && CHECK_FLAG(peer->af_flags_invert[afi][safi], flag))
865 COND_FLAG(peer->af_flags[afi][safi], flag, !group_val);
866 else
867 COND_FLAG(peer->af_flags[afi][safi], flag, group_val);
868 }
869
870 /* Check peer's AS number and determines if this peer is IBGP or EBGP */
871 static inline bgp_peer_sort_t peer_calc_sort(struct peer *peer)
872 {
873 struct bgp *bgp;
874
875 bgp = peer->bgp;
876
877 /* Peer-group */
878 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
879 if (peer->as_type == AS_INTERNAL)
880 return BGP_PEER_IBGP;
881
882 else if (peer->as_type == AS_EXTERNAL)
883 return BGP_PEER_EBGP;
884
885 else if (peer->as_type == AS_SPECIFIED && peer->as) {
886 assert(bgp);
887 return (bgp->as == peer->as ? BGP_PEER_IBGP
888 : BGP_PEER_EBGP);
889 }
890
891 else {
892 struct peer *peer1;
893
894 assert(peer->group);
895 peer1 = listnode_head(peer->group->peer);
896
897 if (peer1)
898 return peer1->sort;
899 }
900 return BGP_PEER_INTERNAL;
901 }
902
903 /* Normal peer */
904 if (bgp && CHECK_FLAG(bgp->config, BGP_CONFIG_CONFEDERATION)) {
905 if (peer->local_as == 0)
906 return BGP_PEER_INTERNAL;
907
908 if (peer->local_as == peer->as) {
909 if (bgp->as == bgp->confed_id) {
910 if (peer->local_as == bgp->as)
911 return BGP_PEER_IBGP;
912 else
913 return BGP_PEER_EBGP;
914 } else {
915 if (peer->local_as == bgp->confed_id)
916 return BGP_PEER_EBGP;
917 else
918 return BGP_PEER_IBGP;
919 }
920 }
921
922 if (bgp_confederation_peers_check(bgp, peer->as))
923 return BGP_PEER_CONFED;
924
925 return BGP_PEER_EBGP;
926 } else {
927 if (peer->as_type == AS_UNSPECIFIED) {
928 /* check if in peer-group with AS information */
929 if (peer->group
930 && (peer->group->conf->as_type != AS_UNSPECIFIED)) {
931 if (peer->group->conf->as_type
932 == AS_SPECIFIED) {
933 if (peer->local_as
934 == peer->group->conf->as)
935 return BGP_PEER_IBGP;
936 else
937 return BGP_PEER_EBGP;
938 } else if (peer->group->conf->as_type
939 == AS_INTERNAL)
940 return BGP_PEER_IBGP;
941 else
942 return BGP_PEER_EBGP;
943 }
944 /* no AS information anywhere, let caller know */
945 return BGP_PEER_UNSPECIFIED;
946 } else if (peer->as_type != AS_SPECIFIED)
947 return (peer->as_type == AS_INTERNAL ? BGP_PEER_IBGP
948 : BGP_PEER_EBGP);
949
950 return (peer->local_as == 0
951 ? BGP_PEER_INTERNAL
952 : peer->local_as == peer->as ? BGP_PEER_IBGP
953 : BGP_PEER_EBGP);
954 }
955 }
956
957 /* Calculate and cache the peer "sort" */
958 bgp_peer_sort_t peer_sort(struct peer *peer)
959 {
960 peer->sort = peer_calc_sort(peer);
961 return peer->sort;
962 }
963
964 static void peer_free(struct peer *peer)
965 {
966 afi_t afi;
967 safi_t safi;
968
969 assert(peer->status == Deleted);
970
971 QOBJ_UNREG(peer);
972
973 /* this /ought/ to have been done already through bgp_stop earlier,
974 * but just to be sure..
975 */
976 bgp_timer_set(peer);
977 bgp_reads_off(peer);
978 bgp_writes_off(peer);
979 assert(!peer->t_write);
980 assert(!peer->t_read);
981 BGP_EVENT_FLUSH(peer);
982
983 pthread_mutex_destroy(&peer->io_mtx);
984
985 /* Free connected nexthop, if present */
986 if (CHECK_FLAG(peer->flags, PEER_FLAG_CONFIG_NODE)
987 && !peer_dynamic_neighbor(peer))
988 bgp_delete_connected_nexthop(family2afi(peer->su.sa.sa_family),
989 peer);
990
991 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG, peer->tx_shutdown_message);
992
993 XFREE(MTYPE_PEER_DESC, peer->desc);
994 XFREE(MTYPE_BGP_PEER_HOST, peer->host);
995 XFREE(MTYPE_BGP_PEER_HOST, peer->domainname);
996 XFREE(MTYPE_BGP_PEER_IFNAME, peer->ifname);
997
998 /* Update source configuration. */
999 if (peer->update_source) {
1000 sockunion_free(peer->update_source);
1001 peer->update_source = NULL;
1002 }
1003
1004 XFREE(MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
1005
1006 XFREE(MTYPE_TMP, peer->notify.data);
1007 memset(&peer->notify, 0, sizeof(struct bgp_notify));
1008
1009 if (peer->clear_node_queue)
1010 work_queue_free_and_null(&peer->clear_node_queue);
1011
1012 bgp_sync_delete(peer);
1013
1014 XFREE(MTYPE_PEER_CONF_IF, peer->conf_if);
1015
1016 bfd_info_free(&(peer->bfd_info));
1017
1018 for (afi = AFI_IP; afi < AFI_MAX; afi++) {
1019 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++) {
1020 bgp_addpath_set_peer_type(peer, afi, safi,
1021 BGP_ADDPATH_NONE);
1022 }
1023 }
1024
1025 bgp_unlock(peer->bgp);
1026
1027 memset(peer, 0, sizeof(struct peer));
1028
1029 XFREE(MTYPE_BGP_PEER, peer);
1030 }
1031
1032 /* increase reference count on a struct peer */
1033 struct peer *peer_lock_with_caller(const char *name, struct peer *peer)
1034 {
1035 assert(peer && (peer->lock >= 0));
1036
1037 #if 0
1038 zlog_debug("%s peer_lock %p %d", name, peer, peer->lock);
1039 #endif
1040
1041 peer->lock++;
1042
1043 return peer;
1044 }
1045
1046 /* decrease reference count on a struct peer
1047 * struct peer is freed and NULL returned if last reference
1048 */
1049 struct peer *peer_unlock_with_caller(const char *name, struct peer *peer)
1050 {
1051 assert(peer && (peer->lock > 0));
1052
1053 #if 0
1054 zlog_debug("%s peer_unlock %p %d", name, peer, peer->lock);
1055 #endif
1056
1057 peer->lock--;
1058
1059 if (peer->lock == 0) {
1060 peer_free(peer);
1061 return NULL;
1062 }
1063
1064 return peer;
1065 }
1066 /* BGP GR changes */
1067
1068 int bgp_global_gr_init(struct bgp *bgp)
1069 {
1070 if (BGP_DEBUG(graceful_restart, GRACEFUL_RESTART))
1071 zlog_debug("%s called ..", __func__);
1072
1073 int local_GLOBAL_GR_FSM[BGP_GLOBAL_GR_MODE][BGP_GLOBAL_GR_EVENT_CMD] = {
1074 /* GLOBAL_HELPER Mode */
1075 {
1076 /*Event -> */
1077 /*GLOBAL_GR_cmd*/ /*no_Global_GR_cmd*/
1078 GLOBAL_GR, GLOBAL_INVALID,
1079 /*GLOBAL_DISABLE_cmd*/ /*no_Global_Disable_cmd*/
1080 GLOBAL_DISABLE, GLOBAL_INVALID
1081 },
1082 /* GLOBAL_GR Mode */
1083 {
1084 /*Event -> */
1085 /*GLOBAL_GR_cmd*/ /*no_Global_GR_cmd*/
1086 GLOBAL_INVALID, GLOBAL_HELPER,
1087 /*GLOBAL_DISABLE_cmd*/ /*no_Global_Disable_cmd*/
1088 GLOBAL_DISABLE, GLOBAL_INVALID
1089 },
1090 /* GLOBAL_DISABLE Mode */
1091 {
1092 /*Event -> */
1093 /*GLOBAL_GR_cmd */ /*no_Global_GR_cmd*/
1094 GLOBAL_GR, GLOBAL_INVALID,
1095 /*GLOBAL_DISABLE_cmd*//*no_Global_Disable_cmd*/
1096 GLOBAL_INVALID, GLOBAL_HELPER
1097 },
1098 /* GLOBAL_INVALID Mode */
1099 {
1100 /*Event -> */
1101 /*GLOBAL_GR_cmd*/ /*no_Global_GR_cmd*/
1102 GLOBAL_INVALID, GLOBAL_INVALID,
1103 /*GLOBAL_DISABLE_cmd*/ /*no_Global_Disable_cmd*/
1104 GLOBAL_INVALID, GLOBAL_INVALID
1105 }
1106 };
1107 memcpy(bgp->GLOBAL_GR_FSM, local_GLOBAL_GR_FSM,
1108 sizeof(local_GLOBAL_GR_FSM));
1109
1110 bgp->global_gr_present_state = GLOBAL_HELPER;
1111 bgp->present_zebra_gr_state = ZEBRA_GR_DISABLE;
1112
1113 return BGP_GR_SUCCESS;
1114 }
1115
1116 int bgp_peer_gr_init(struct peer *peer)
1117 {
1118 if (BGP_DEBUG(graceful_restart, GRACEFUL_RESTART))
1119 zlog_debug("%s called ..", __func__);
1120
1121 struct bgp_peer_gr local_Peer_GR_FSM[BGP_PEER_GR_MODE]
1122 [BGP_PEER_GR_EVENT_CMD] = {
1123 {
1124 /* PEER_HELPER Mode */
1125 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1126 { PEER_GR, bgp_peer_gr_action }, {PEER_INVALID, NULL },
1127 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1128 {PEER_DISABLE, bgp_peer_gr_action }, {PEER_INVALID, NULL },
1129 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1130 { PEER_INVALID, NULL }, {PEER_GLOBAL_INHERIT,
1131 bgp_peer_gr_action }
1132 },
1133 {
1134 /* PEER_GR Mode */
1135 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1136 { PEER_INVALID, NULL }, { PEER_GLOBAL_INHERIT,
1137 bgp_peer_gr_action },
1138 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1139 {PEER_DISABLE, bgp_peer_gr_action }, { PEER_INVALID, NULL },
1140 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1141 { PEER_HELPER, bgp_peer_gr_action }, { PEER_INVALID, NULL }
1142 },
1143 {
1144 /* PEER_DISABLE Mode */
1145 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1146 { PEER_GR, bgp_peer_gr_action }, { PEER_INVALID, NULL },
1147 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1148 { PEER_INVALID, NULL }, { PEER_GLOBAL_INHERIT,
1149 bgp_peer_gr_action },
1150 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1151 { PEER_HELPER, bgp_peer_gr_action }, { PEER_INVALID, NULL }
1152 },
1153 {
1154 /* PEER_INVALID Mode */
1155 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1156 { PEER_INVALID, NULL }, { PEER_INVALID, NULL },
1157 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1158 { PEER_INVALID, NULL }, { PEER_INVALID, NULL },
1159 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1160 { PEER_INVALID, NULL }, { PEER_INVALID, NULL },
1161 },
1162 {
1163 /* PEER_GLOBAL_INHERIT Mode */
1164 /* Event-> */ /* PEER_GR_CMD */ /* NO_PEER_GR_CMD */
1165 { PEER_GR, bgp_peer_gr_action }, { PEER_INVALID, NULL },
1166 /* Event-> */ /* PEER_DISABLE_CMD */ /* NO_PEER_DISABLE_CMD */
1167 { PEER_DISABLE, bgp_peer_gr_action}, { PEER_INVALID, NULL },
1168 /* Event-> */ /* PEER_HELPER_cmd */ /* NO_PEER_HELPER_CMD */
1169 { PEER_HELPER, bgp_peer_gr_action }, { PEER_INVALID, NULL }
1170 }
1171 };
1172 memcpy(&peer->PEER_GR_FSM, local_Peer_GR_FSM,
1173 sizeof(local_Peer_GR_FSM));
1174 peer->peer_gr_present_state = PEER_GLOBAL_INHERIT;
1175 bgp_peer_move_to_gr_mode(peer, PEER_GLOBAL_INHERIT);
1176
1177 return BGP_GR_SUCCESS;
1178 }
1179
1180 /* Allocate new peer object, implicitely locked. */
1181 struct peer *peer_new(struct bgp *bgp)
1182 {
1183 afi_t afi;
1184 safi_t safi;
1185 struct peer *peer;
1186 struct servent *sp;
1187
1188 /* bgp argument is absolutely required */
1189 assert(bgp);
1190 if (!bgp)
1191 return NULL;
1192
1193 /* Allocate new peer. */
1194 peer = XCALLOC(MTYPE_BGP_PEER, sizeof(struct peer));
1195
1196 /* Set default value. */
1197 peer->fd = -1;
1198 peer->v_start = BGP_INIT_START_TIMER;
1199 peer->v_connect = bgp->default_connect_retry;
1200 peer->status = Idle;
1201 peer->ostatus = Idle;
1202 peer->cur_event = peer->last_event = peer->last_major_event = 0;
1203 peer->bgp = bgp_lock(bgp);
1204 peer = peer_lock(peer); /* initial reference */
1205 peer->password = NULL;
1206
1207 /* Set default flags. */
1208 FOREACH_AFI_SAFI (afi, safi) {
1209 SET_FLAG(peer->af_flags[afi][safi], PEER_FLAG_SEND_COMMUNITY);
1210 SET_FLAG(peer->af_flags[afi][safi],
1211 PEER_FLAG_SEND_EXT_COMMUNITY);
1212 SET_FLAG(peer->af_flags[afi][safi],
1213 PEER_FLAG_SEND_LARGE_COMMUNITY);
1214
1215 SET_FLAG(peer->af_flags_invert[afi][safi],
1216 PEER_FLAG_SEND_COMMUNITY);
1217 SET_FLAG(peer->af_flags_invert[afi][safi],
1218 PEER_FLAG_SEND_EXT_COMMUNITY);
1219 SET_FLAG(peer->af_flags_invert[afi][safi],
1220 PEER_FLAG_SEND_LARGE_COMMUNITY);
1221 peer->addpath_type[afi][safi] = BGP_ADDPATH_NONE;
1222 }
1223
1224 /* set nexthop-unchanged for l2vpn evpn by default */
1225 SET_FLAG(peer->af_flags[AFI_L2VPN][SAFI_EVPN],
1226 PEER_FLAG_NEXTHOP_UNCHANGED);
1227
1228 SET_FLAG(peer->sflags, PEER_STATUS_CAPABILITY_OPEN);
1229
1230 /* Initialize per peer bgp GR FSM */
1231 bgp_peer_gr_init(peer);
1232
1233 /* Create buffers. */
1234 peer->ibuf = stream_fifo_new();
1235 peer->obuf = stream_fifo_new();
1236 pthread_mutex_init(&peer->io_mtx, NULL);
1237
1238 /* We use a larger buffer for peer->obuf_work in the event that:
1239 * - We RX a BGP_UPDATE where the attributes alone are just
1240 * under BGP_MAX_PACKET_SIZE
1241 * - The user configures an outbound route-map that does many as-path
1242 * prepends or adds many communities. At most they can have
1243 * CMD_ARGC_MAX args in a route-map so there is a finite limit on how
1244 * large they can make the attributes.
1245 *
1246 * Having a buffer with BGP_MAX_PACKET_SIZE_OVERFLOW allows us to avoid
1247 * bounds checking for every single attribute as we construct an
1248 * UPDATE.
1249 */
1250 peer->obuf_work =
1251 stream_new(BGP_MAX_PACKET_SIZE + BGP_MAX_PACKET_SIZE_OVERFLOW);
1252 peer->ibuf_work =
1253 ringbuf_new(BGP_MAX_PACKET_SIZE * BGP_READ_PACKET_MAX);
1254
1255 peer->scratch = stream_new(BGP_MAX_PACKET_SIZE);
1256
1257 bgp_sync_init(peer);
1258
1259 /* Get service port number. */
1260 sp = getservbyname("bgp", "tcp");
1261 peer->port = (sp == NULL) ? BGP_PORT_DEFAULT : ntohs(sp->s_port);
1262
1263 QOBJ_REG(peer, peer);
1264 return peer;
1265 }
1266
1267 /*
1268 * This function is invoked when a duplicate peer structure associated with
1269 * a neighbor is being deleted. If this about-to-be-deleted structure is
1270 * the one with all the config, then we have to copy over the info.
1271 */
1272 void peer_xfer_config(struct peer *peer_dst, struct peer *peer_src)
1273 {
1274 struct peer_af *paf;
1275 afi_t afi;
1276 safi_t safi;
1277 int afidx;
1278
1279 assert(peer_src);
1280 assert(peer_dst);
1281
1282 /* The following function is used by both peer group config copy to
1283 * individual peer and when we transfer config
1284 */
1285 if (peer_src->change_local_as)
1286 peer_dst->change_local_as = peer_src->change_local_as;
1287
1288 /* peer flags apply */
1289 peer_dst->flags = peer_src->flags;
1290 peer_dst->cap = peer_src->cap;
1291
1292 peer_dst->peer_gr_present_state = peer_src->peer_gr_present_state;
1293 peer_dst->peer_gr_new_status_flag = peer_src->peer_gr_new_status_flag;
1294
1295 peer_dst->local_as = peer_src->local_as;
1296 peer_dst->port = peer_src->port;
1297 (void)peer_sort(peer_dst);
1298 peer_dst->rmap_type = peer_src->rmap_type;
1299
1300 /* Timers */
1301 peer_dst->holdtime = peer_src->holdtime;
1302 peer_dst->keepalive = peer_src->keepalive;
1303 peer_dst->connect = peer_src->connect;
1304 peer_dst->v_holdtime = peer_src->v_holdtime;
1305 peer_dst->v_keepalive = peer_src->v_keepalive;
1306 peer_dst->routeadv = peer_src->routeadv;
1307 peer_dst->v_routeadv = peer_src->v_routeadv;
1308
1309 /* password apply */
1310 if (peer_src->password && !peer_dst->password)
1311 peer_dst->password =
1312 XSTRDUP(MTYPE_PEER_PASSWORD, peer_src->password);
1313
1314 FOREACH_AFI_SAFI (afi, safi) {
1315 peer_dst->afc[afi][safi] = peer_src->afc[afi][safi];
1316 peer_dst->af_flags[afi][safi] = peer_src->af_flags[afi][safi];
1317 peer_dst->allowas_in[afi][safi] =
1318 peer_src->allowas_in[afi][safi];
1319 peer_dst->weight[afi][safi] = peer_src->weight[afi][safi];
1320 peer_dst->addpath_type[afi][safi] =
1321 peer_src->addpath_type[afi][safi];
1322 }
1323
1324 for (afidx = BGP_AF_START; afidx < BGP_AF_MAX; afidx++) {
1325 paf = peer_src->peer_af_array[afidx];
1326 if (paf != NULL)
1327 peer_af_create(peer_dst, paf->afi, paf->safi);
1328 }
1329
1330 /* update-source apply */
1331 if (peer_src->update_source) {
1332 if (peer_dst->update_source)
1333 sockunion_free(peer_dst->update_source);
1334 XFREE(MTYPE_PEER_UPDATE_SOURCE, peer_dst->update_if);
1335 peer_dst->update_source =
1336 sockunion_dup(peer_src->update_source);
1337 } else if (peer_src->update_if) {
1338 XFREE(MTYPE_PEER_UPDATE_SOURCE, peer_dst->update_if);
1339 if (peer_dst->update_source) {
1340 sockunion_free(peer_dst->update_source);
1341 peer_dst->update_source = NULL;
1342 }
1343 peer_dst->update_if =
1344 XSTRDUP(MTYPE_PEER_UPDATE_SOURCE, peer_src->update_if);
1345 }
1346
1347 if (peer_src->ifname) {
1348 XFREE(MTYPE_BGP_PEER_IFNAME, peer_dst->ifname);
1349
1350 peer_dst->ifname =
1351 XSTRDUP(MTYPE_BGP_PEER_IFNAME, peer_src->ifname);
1352 }
1353 }
1354
1355 static int bgp_peer_conf_if_to_su_update_v4(struct peer *peer,
1356 struct interface *ifp)
1357 {
1358 struct connected *ifc;
1359 struct prefix p;
1360 uint32_t addr;
1361 struct listnode *node;
1362
1363 /* If our IPv4 address on the interface is /30 or /31, we can derive the
1364 * IPv4 address of the other end.
1365 */
1366 for (ALL_LIST_ELEMENTS_RO(ifp->connected, node, ifc)) {
1367 if (ifc->address && (ifc->address->family == AF_INET)) {
1368 PREFIX_COPY_IPV4(&p, CONNECTED_PREFIX(ifc));
1369 if (p.prefixlen == 30) {
1370 peer->su.sa.sa_family = AF_INET;
1371 addr = ntohl(p.u.prefix4.s_addr);
1372 if (addr % 4 == 1)
1373 peer->su.sin.sin_addr.s_addr =
1374 htonl(addr + 1);
1375 else if (addr % 4 == 2)
1376 peer->su.sin.sin_addr.s_addr =
1377 htonl(addr - 1);
1378 #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
1379 peer->su.sin.sin_len =
1380 sizeof(struct sockaddr_in);
1381 #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
1382 return 1;
1383 } else if (p.prefixlen == 31) {
1384 peer->su.sa.sa_family = AF_INET;
1385 addr = ntohl(p.u.prefix4.s_addr);
1386 if (addr % 2 == 0)
1387 peer->su.sin.sin_addr.s_addr =
1388 htonl(addr + 1);
1389 else
1390 peer->su.sin.sin_addr.s_addr =
1391 htonl(addr - 1);
1392 #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
1393 peer->su.sin.sin_len =
1394 sizeof(struct sockaddr_in);
1395 #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
1396 return 1;
1397 } else if (bgp_debug_neighbor_events(peer))
1398 zlog_debug(
1399 "%s: IPv4 interface address is not /30 or /31, v4 session not started",
1400 peer->conf_if);
1401 }
1402 }
1403
1404 return 0;
1405 }
1406
1407 static int bgp_peer_conf_if_to_su_update_v6(struct peer *peer,
1408 struct interface *ifp)
1409 {
1410 struct nbr_connected *ifc_nbr;
1411
1412 /* Have we learnt the peer's IPv6 link-local address? */
1413 if (ifp->nbr_connected
1414 && (ifc_nbr = listnode_head(ifp->nbr_connected))) {
1415 peer->su.sa.sa_family = AF_INET6;
1416 memcpy(&peer->su.sin6.sin6_addr, &ifc_nbr->address->u.prefix,
1417 sizeof(struct in6_addr));
1418 #ifdef SIN6_LEN
1419 peer->su.sin6.sin6_len = sizeof(struct sockaddr_in6);
1420 #endif
1421 peer->su.sin6.sin6_scope_id = ifp->ifindex;
1422 return 1;
1423 }
1424
1425 return 0;
1426 }
1427
1428 /*
1429 * Set or reset the peer address socketunion structure based on the
1430 * learnt/derived peer address. If the address has changed, update the
1431 * password on the listen socket, if needed.
1432 */
1433 void bgp_peer_conf_if_to_su_update(struct peer *peer)
1434 {
1435 struct interface *ifp;
1436 int prev_family;
1437 int peer_addr_updated = 0;
1438
1439 if (!peer->conf_if)
1440 return;
1441
1442 /*
1443 * Our peer structure is stored in the bgp->peerhash
1444 * release it before we modify anything.
1445 */
1446 hash_release(peer->bgp->peerhash, peer);
1447
1448 prev_family = peer->su.sa.sa_family;
1449 if ((ifp = if_lookup_by_name(peer->conf_if, peer->bgp->vrf_id))) {
1450 peer->ifp = ifp;
1451 /* If BGP unnumbered is not "v6only", we first see if we can
1452 * derive the
1453 * peer's IPv4 address.
1454 */
1455 if (!CHECK_FLAG(peer->flags, PEER_FLAG_IFPEER_V6ONLY))
1456 peer_addr_updated =
1457 bgp_peer_conf_if_to_su_update_v4(peer, ifp);
1458
1459 /* If "v6only" or we can't derive peer's IPv4 address, see if
1460 * we've
1461 * learnt the peer's IPv6 link-local address. This is from the
1462 * source
1463 * IPv6 address in router advertisement.
1464 */
1465 if (!peer_addr_updated)
1466 peer_addr_updated =
1467 bgp_peer_conf_if_to_su_update_v6(peer, ifp);
1468 }
1469 /* If we could derive the peer address, we may need to install the
1470 * password
1471 * configured for the peer, if any, on the listen socket. Otherwise,
1472 * mark
1473 * that peer's address is not available and uninstall the password, if
1474 * needed.
1475 */
1476 if (peer_addr_updated) {
1477 if (CHECK_FLAG(peer->flags, PEER_FLAG_PASSWORD)
1478 && prev_family == AF_UNSPEC)
1479 bgp_md5_set(peer);
1480 } else {
1481 if (CHECK_FLAG(peer->flags, PEER_FLAG_PASSWORD)
1482 && prev_family != AF_UNSPEC)
1483 bgp_md5_unset(peer);
1484 peer->su.sa.sa_family = AF_UNSPEC;
1485 memset(&peer->su.sin6.sin6_addr, 0, sizeof(struct in6_addr));
1486 }
1487
1488 /*
1489 * Since our su changed we need to del/add peer to the peerhash
1490 */
1491 hash_get(peer->bgp->peerhash, peer, hash_alloc_intern);
1492 }
1493
1494 static void bgp_recalculate_afi_safi_bestpaths(struct bgp *bgp, afi_t afi,
1495 safi_t safi)
1496 {
1497 struct bgp_node *rn, *nrn;
1498 struct bgp_table *table;
1499
1500 for (rn = bgp_table_top(bgp->rib[afi][safi]); rn;
1501 rn = bgp_route_next(rn)) {
1502 table = bgp_node_get_bgp_table_info(rn);
1503 if (table != NULL) {
1504 /* Special handling for 2-level routing
1505 * tables. */
1506 if (safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP
1507 || safi == SAFI_EVPN) {
1508 for (nrn = bgp_table_top(table);
1509 nrn; nrn = bgp_route_next(nrn))
1510 bgp_process(bgp, nrn, afi, safi);
1511 } else
1512 bgp_process(bgp, rn, afi, safi);
1513 }
1514 }
1515 }
1516
1517 /* Force a bestpath recalculation for all prefixes. This is used
1518 * when 'bgp bestpath' commands are entered.
1519 */
1520 void bgp_recalculate_all_bestpaths(struct bgp *bgp)
1521 {
1522 afi_t afi;
1523 safi_t safi;
1524
1525 FOREACH_AFI_SAFI (afi, safi) {
1526 bgp_recalculate_afi_safi_bestpaths(bgp, afi, safi);
1527 }
1528 }
1529
1530 /*
1531 * Create new BGP peer.
1532 *
1533 * conf_if and su are mutually exclusive if configuring from the cli.
1534 * If we are handing a doppelganger, then we *must* pass in both
1535 * the original peer's su and conf_if, so that we can appropriately
1536 * track the bgp->peerhash( ie we don't want to remove the current
1537 * one from the config ).
1538 */
1539 struct peer *peer_create(union sockunion *su, const char *conf_if,
1540 struct bgp *bgp, as_t local_as, as_t remote_as,
1541 int as_type, afi_t afi, safi_t safi,
1542 struct peer_group *group)
1543 {
1544 int active;
1545 struct peer *peer;
1546 char buf[SU_ADDRSTRLEN];
1547
1548 peer = peer_new(bgp);
1549 if (conf_if) {
1550 peer->conf_if = XSTRDUP(MTYPE_PEER_CONF_IF, conf_if);
1551 if (su)
1552 peer->su = *su;
1553 else
1554 bgp_peer_conf_if_to_su_update(peer);
1555 XFREE(MTYPE_BGP_PEER_HOST, peer->host);
1556 peer->host = XSTRDUP(MTYPE_BGP_PEER_HOST, conf_if);
1557 } else if (su) {
1558 peer->su = *su;
1559 sockunion2str(su, buf, SU_ADDRSTRLEN);
1560 XFREE(MTYPE_BGP_PEER_HOST, peer->host);
1561 peer->host = XSTRDUP(MTYPE_BGP_PEER_HOST, buf);
1562 }
1563 peer->local_as = local_as;
1564 peer->as = remote_as;
1565 peer->as_type = as_type;
1566 peer->local_id = bgp->router_id;
1567 peer->v_holdtime = bgp->default_holdtime;
1568 peer->v_keepalive = bgp->default_keepalive;
1569 peer->v_routeadv = (peer_sort(peer) == BGP_PEER_IBGP)
1570 ? BGP_DEFAULT_IBGP_ROUTEADV
1571 : BGP_DEFAULT_EBGP_ROUTEADV;
1572
1573 peer = peer_lock(peer); /* bgp peer list reference */
1574 peer->group = group;
1575 listnode_add_sort(bgp->peer, peer);
1576 hash_get(bgp->peerhash, peer, hash_alloc_intern);
1577
1578 /* Adjust update-group coalesce timer heuristics for # peers. */
1579 if (bgp->heuristic_coalesce) {
1580 long ct = BGP_DEFAULT_SUBGROUP_COALESCE_TIME
1581 + (bgp->peer->count
1582 * BGP_PEER_ADJUST_SUBGROUP_COALESCE_TIME);
1583 bgp->coalesce_time = MIN(BGP_MAX_SUBGROUP_COALESCE_TIME, ct);
1584 }
1585
1586 active = peer_active(peer);
1587 if (!active) {
1588 if (peer->su.sa.sa_family == AF_UNSPEC)
1589 peer->last_reset = PEER_DOWN_NBR_ADDR;
1590 else
1591 peer->last_reset = PEER_DOWN_NOAFI_ACTIVATED;
1592 }
1593
1594 /* Last read and reset time set */
1595 peer->readtime = peer->resettime = bgp_clock();
1596
1597 /* Default TTL set. */
1598 peer->ttl = (peer->sort == BGP_PEER_IBGP) ? MAXTTL : BGP_DEFAULT_TTL;
1599
1600 SET_FLAG(peer->flags, PEER_FLAG_CONFIG_NODE);
1601
1602 if (afi && safi) {
1603 peer->afc[afi][safi] = 1;
1604 peer_af_create(peer, afi, safi);
1605 }
1606
1607 /* auto shutdown if configured */
1608 if (bgp->autoshutdown)
1609 peer_flag_set(peer, PEER_FLAG_SHUTDOWN);
1610 /* Set up peer's events and timers. */
1611 else if (!active && peer_active(peer))
1612 bgp_timer_set(peer);
1613
1614 bgp_peer_gr_flags_update(peer);
1615 BGP_GR_ROUTER_DETECT_AND_SEND_CAPABILITY_TO_ZEBRA(bgp, bgp->peer);
1616
1617 return peer;
1618 }
1619
1620 /* Make accept BGP peer. This function is only called from the test code */
1621 struct peer *peer_create_accept(struct bgp *bgp)
1622 {
1623 struct peer *peer;
1624
1625 peer = peer_new(bgp);
1626
1627 peer = peer_lock(peer); /* bgp peer list reference */
1628 listnode_add_sort(bgp->peer, peer);
1629
1630 return peer;
1631 }
1632
1633 /*
1634 * Return true if we have a peer configured to use this afi/safi
1635 */
1636 int bgp_afi_safi_peer_exists(struct bgp *bgp, afi_t afi, safi_t safi)
1637 {
1638 struct listnode *node;
1639 struct peer *peer;
1640
1641 for (ALL_LIST_ELEMENTS_RO(bgp->peer, node, peer)) {
1642 if (!CHECK_FLAG(peer->flags, PEER_FLAG_CONFIG_NODE))
1643 continue;
1644
1645 if (peer->afc[afi][safi])
1646 return 1;
1647 }
1648
1649 return 0;
1650 }
1651
1652 /* Change peer's AS number. */
1653 void peer_as_change(struct peer *peer, as_t as, int as_specified)
1654 {
1655 bgp_peer_sort_t type;
1656
1657 /* Stop peer. */
1658 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
1659 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
1660 peer->last_reset = PEER_DOWN_REMOTE_AS_CHANGE;
1661 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
1662 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
1663 } else
1664 bgp_session_reset(peer);
1665 }
1666 type = peer_sort(peer);
1667 peer->as = as;
1668 peer->as_type = as_specified;
1669
1670 if (bgp_config_check(peer->bgp, BGP_CONFIG_CONFEDERATION)
1671 && !bgp_confederation_peers_check(peer->bgp, as)
1672 && peer->bgp->as != as)
1673 peer->local_as = peer->bgp->confed_id;
1674 else
1675 peer->local_as = peer->bgp->as;
1676
1677 /* Advertisement-interval reset */
1678 if (!CHECK_FLAG(peer->flags, PEER_FLAG_ROUTEADV)) {
1679 peer->v_routeadv = (peer_sort(peer) == BGP_PEER_IBGP)
1680 ? BGP_DEFAULT_IBGP_ROUTEADV
1681 : BGP_DEFAULT_EBGP_ROUTEADV;
1682 }
1683
1684 /* TTL reset */
1685 if (peer_sort(peer) == BGP_PEER_IBGP)
1686 peer->ttl = MAXTTL;
1687 else if (type == BGP_PEER_IBGP)
1688 peer->ttl = BGP_DEFAULT_TTL;
1689
1690 /* reflector-client reset */
1691 if (peer_sort(peer) != BGP_PEER_IBGP) {
1692 UNSET_FLAG(peer->af_flags[AFI_IP][SAFI_UNICAST],
1693 PEER_FLAG_REFLECTOR_CLIENT);
1694 UNSET_FLAG(peer->af_flags[AFI_IP][SAFI_MULTICAST],
1695 PEER_FLAG_REFLECTOR_CLIENT);
1696 UNSET_FLAG(peer->af_flags[AFI_IP][SAFI_LABELED_UNICAST],
1697 PEER_FLAG_REFLECTOR_CLIENT);
1698 UNSET_FLAG(peer->af_flags[AFI_IP][SAFI_MPLS_VPN],
1699 PEER_FLAG_REFLECTOR_CLIENT);
1700 UNSET_FLAG(peer->af_flags[AFI_IP][SAFI_ENCAP],
1701 PEER_FLAG_REFLECTOR_CLIENT);
1702 UNSET_FLAG(peer->af_flags[AFI_IP][SAFI_FLOWSPEC],
1703 PEER_FLAG_REFLECTOR_CLIENT);
1704 UNSET_FLAG(peer->af_flags[AFI_IP6][SAFI_UNICAST],
1705 PEER_FLAG_REFLECTOR_CLIENT);
1706 UNSET_FLAG(peer->af_flags[AFI_IP6][SAFI_MULTICAST],
1707 PEER_FLAG_REFLECTOR_CLIENT);
1708 UNSET_FLAG(peer->af_flags[AFI_IP6][SAFI_LABELED_UNICAST],
1709 PEER_FLAG_REFLECTOR_CLIENT);
1710 UNSET_FLAG(peer->af_flags[AFI_IP6][SAFI_MPLS_VPN],
1711 PEER_FLAG_REFLECTOR_CLIENT);
1712 UNSET_FLAG(peer->af_flags[AFI_IP6][SAFI_ENCAP],
1713 PEER_FLAG_REFLECTOR_CLIENT);
1714 UNSET_FLAG(peer->af_flags[AFI_IP6][SAFI_FLOWSPEC],
1715 PEER_FLAG_REFLECTOR_CLIENT);
1716 UNSET_FLAG(peer->af_flags[AFI_L2VPN][SAFI_EVPN],
1717 PEER_FLAG_REFLECTOR_CLIENT);
1718 }
1719
1720 /* local-as reset */
1721 if (peer_sort(peer) != BGP_PEER_EBGP) {
1722 peer->change_local_as = 0;
1723 peer_flag_unset(peer, PEER_FLAG_LOCAL_AS);
1724 peer_flag_unset(peer, PEER_FLAG_LOCAL_AS_NO_PREPEND);
1725 peer_flag_unset(peer, PEER_FLAG_LOCAL_AS_REPLACE_AS);
1726 }
1727 }
1728
1729 /* If peer does not exist, create new one. If peer already exists,
1730 set AS number to the peer. */
1731 int peer_remote_as(struct bgp *bgp, union sockunion *su, const char *conf_if,
1732 as_t *as, int as_type, afi_t afi, safi_t safi)
1733 {
1734 struct peer *peer;
1735 as_t local_as;
1736
1737 if (conf_if)
1738 peer = peer_lookup_by_conf_if(bgp, conf_if);
1739 else
1740 peer = peer_lookup(bgp, su);
1741
1742 if (peer) {
1743 /* Not allowed for a dynamic peer. */
1744 if (peer_dynamic_neighbor(peer)) {
1745 *as = peer->as;
1746 return BGP_ERR_INVALID_FOR_DYNAMIC_PEER;
1747 }
1748
1749 /* When this peer is a member of peer-group. */
1750 if (peer->group) {
1751 /* peer-group already has AS number/internal/external */
1752 if (peer->group->conf->as
1753 || peer->group->conf->as_type) {
1754 /* Return peer group's AS number. */
1755 *as = peer->group->conf->as;
1756 return BGP_ERR_PEER_GROUP_MEMBER;
1757 }
1758
1759 bgp_peer_sort_t peer_sort_type =
1760 peer_sort(peer->group->conf);
1761
1762 /* Explicit AS numbers used, compare AS numbers */
1763 if (as_type == AS_SPECIFIED) {
1764 if (((peer_sort_type == BGP_PEER_IBGP)
1765 && (bgp->as != *as))
1766 || ((peer_sort_type == BGP_PEER_EBGP)
1767 && (bgp->as == *as))) {
1768 *as = peer->as;
1769 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT;
1770 }
1771 } else {
1772 /* internal/external used, compare as-types */
1773 if (((peer_sort_type == BGP_PEER_IBGP)
1774 && (as_type != AS_INTERNAL))
1775 || ((peer_sort_type == BGP_PEER_EBGP)
1776 && (as_type != AS_EXTERNAL))) {
1777 *as = peer->as;
1778 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT;
1779 }
1780 }
1781 }
1782
1783 /* Existing peer's AS number change. */
1784 if (((peer->as_type == AS_SPECIFIED) && peer->as != *as)
1785 || (peer->as_type != as_type))
1786 peer_as_change(peer, *as, as_type);
1787 } else {
1788 if (conf_if)
1789 return BGP_ERR_NO_INTERFACE_CONFIG;
1790
1791 /* If the peer is not part of our confederation, and its not an
1792 iBGP peer then spoof the source AS */
1793 if (bgp_config_check(bgp, BGP_CONFIG_CONFEDERATION)
1794 && !bgp_confederation_peers_check(bgp, *as)
1795 && bgp->as != *as)
1796 local_as = bgp->confed_id;
1797 else
1798 local_as = bgp->as;
1799
1800 /* If this is IPv4 unicast configuration and "no bgp default
1801 ipv4-unicast" is specified. */
1802
1803 if (CHECK_FLAG(bgp->flags, BGP_FLAG_NO_DEFAULT_IPV4)
1804 && afi == AFI_IP && safi == SAFI_UNICAST)
1805 peer_create(su, conf_if, bgp, local_as, *as, as_type, 0,
1806 0, NULL);
1807 else
1808 peer_create(su, conf_if, bgp, local_as, *as, as_type,
1809 afi, safi, NULL);
1810 }
1811
1812 return 0;
1813 }
1814
1815 static void peer_group2peer_config_copy_af(struct peer_group *group,
1816 struct peer *peer, afi_t afi,
1817 safi_t safi)
1818 {
1819 int in = FILTER_IN;
1820 int out = FILTER_OUT;
1821 uint32_t flags_tmp;
1822 uint32_t pflags_ovrd;
1823 uint8_t *pfilter_ovrd;
1824 struct peer *conf;
1825
1826 conf = group->conf;
1827 pflags_ovrd = peer->af_flags_override[afi][safi];
1828 pfilter_ovrd = &peer->filter_override[afi][safi][in];
1829
1830 /* peer af_flags apply */
1831 flags_tmp = conf->af_flags[afi][safi] & ~pflags_ovrd;
1832 flags_tmp ^= conf->af_flags_invert[afi][safi]
1833 ^ peer->af_flags_invert[afi][safi];
1834 flags_tmp &= ~pflags_ovrd;
1835
1836 UNSET_FLAG(peer->af_flags[afi][safi], ~pflags_ovrd);
1837 SET_FLAG(peer->af_flags[afi][safi], flags_tmp);
1838 SET_FLAG(peer->af_flags_invert[afi][safi],
1839 conf->af_flags_invert[afi][safi]);
1840
1841 /* maximum-prefix */
1842 if (!CHECK_FLAG(pflags_ovrd, PEER_FLAG_MAX_PREFIX)) {
1843 PEER_ATTR_INHERIT(peer, group, pmax[afi][safi]);
1844 PEER_ATTR_INHERIT(peer, group, pmax_threshold[afi][safi]);
1845 PEER_ATTR_INHERIT(peer, group, pmax_restart[afi][safi]);
1846 }
1847
1848 /* allowas-in */
1849 if (!CHECK_FLAG(pflags_ovrd, PEER_FLAG_ALLOWAS_IN))
1850 PEER_ATTR_INHERIT(peer, group, allowas_in[afi][safi]);
1851
1852 /* weight */
1853 if (!CHECK_FLAG(pflags_ovrd, PEER_FLAG_WEIGHT))
1854 PEER_ATTR_INHERIT(peer, group, weight[afi][safi]);
1855
1856 /* default-originate route-map */
1857 if (!CHECK_FLAG(pflags_ovrd, PEER_FLAG_DEFAULT_ORIGINATE)) {
1858 PEER_STR_ATTR_INHERIT(peer, group, default_rmap[afi][safi].name,
1859 MTYPE_ROUTE_MAP_NAME);
1860 PEER_ATTR_INHERIT(peer, group, default_rmap[afi][safi].map);
1861 }
1862
1863 /* inbound filter apply */
1864 if (!CHECK_FLAG(pfilter_ovrd[in], PEER_FT_DISTRIBUTE_LIST)) {
1865 PEER_STR_ATTR_INHERIT(peer, group,
1866 filter[afi][safi].dlist[in].name,
1867 MTYPE_BGP_FILTER_NAME);
1868 PEER_ATTR_INHERIT(peer, group,
1869 filter[afi][safi].dlist[in].alist);
1870 }
1871
1872 if (!CHECK_FLAG(pfilter_ovrd[in], PEER_FT_PREFIX_LIST)) {
1873 PEER_STR_ATTR_INHERIT(peer, group,
1874 filter[afi][safi].plist[in].name,
1875 MTYPE_BGP_FILTER_NAME);
1876 PEER_ATTR_INHERIT(peer, group,
1877 filter[afi][safi].plist[in].plist);
1878 }
1879
1880 if (!CHECK_FLAG(pfilter_ovrd[in], PEER_FT_FILTER_LIST)) {
1881 PEER_STR_ATTR_INHERIT(peer, group,
1882 filter[afi][safi].aslist[in].name,
1883 MTYPE_BGP_FILTER_NAME);
1884 PEER_ATTR_INHERIT(peer, group,
1885 filter[afi][safi].aslist[in].aslist);
1886 }
1887
1888 if (!CHECK_FLAG(pfilter_ovrd[RMAP_IN], PEER_FT_ROUTE_MAP)) {
1889 PEER_STR_ATTR_INHERIT(peer, group,
1890 filter[afi][safi].map[in].name,
1891 MTYPE_BGP_FILTER_NAME);
1892 PEER_ATTR_INHERIT(peer, group,
1893 filter[afi][safi].map[RMAP_IN].map);
1894 }
1895
1896 /* outbound filter apply */
1897 if (!CHECK_FLAG(pfilter_ovrd[out], PEER_FT_DISTRIBUTE_LIST)) {
1898 PEER_STR_ATTR_INHERIT(peer, group,
1899 filter[afi][safi].dlist[out].name,
1900 MTYPE_BGP_FILTER_NAME);
1901 PEER_ATTR_INHERIT(peer, group,
1902 filter[afi][safi].dlist[out].alist);
1903 }
1904
1905 if (!CHECK_FLAG(pfilter_ovrd[out], PEER_FT_PREFIX_LIST)) {
1906 PEER_STR_ATTR_INHERIT(peer, group,
1907 filter[afi][safi].plist[out].name,
1908 MTYPE_BGP_FILTER_NAME);
1909 PEER_ATTR_INHERIT(peer, group,
1910 filter[afi][safi].plist[out].plist);
1911 }
1912
1913 if (!CHECK_FLAG(pfilter_ovrd[out], PEER_FT_FILTER_LIST)) {
1914 PEER_STR_ATTR_INHERIT(peer, group,
1915 filter[afi][safi].aslist[out].name,
1916 MTYPE_BGP_FILTER_NAME);
1917 PEER_ATTR_INHERIT(peer, group,
1918 filter[afi][safi].aslist[out].aslist);
1919 }
1920
1921 if (!CHECK_FLAG(pfilter_ovrd[RMAP_OUT], PEER_FT_ROUTE_MAP)) {
1922 PEER_STR_ATTR_INHERIT(peer, group,
1923 filter[afi][safi].map[RMAP_OUT].name,
1924 MTYPE_BGP_FILTER_NAME);
1925 PEER_ATTR_INHERIT(peer, group,
1926 filter[afi][safi].map[RMAP_OUT].map);
1927 }
1928
1929 /* nondirectional filter apply */
1930 if (!CHECK_FLAG(pfilter_ovrd[0], PEER_FT_UNSUPPRESS_MAP)) {
1931 PEER_STR_ATTR_INHERIT(peer, group, filter[afi][safi].usmap.name,
1932 MTYPE_BGP_FILTER_NAME);
1933 PEER_ATTR_INHERIT(peer, group, filter[afi][safi].usmap.map);
1934 }
1935
1936 if (peer->addpath_type[afi][safi] == BGP_ADDPATH_NONE) {
1937 peer->addpath_type[afi][safi] = conf->addpath_type[afi][safi];
1938 bgp_addpath_type_changed(conf->bgp);
1939 }
1940 }
1941
1942 static int peer_activate_af(struct peer *peer, afi_t afi, safi_t safi)
1943 {
1944 int active;
1945 struct peer *other;
1946
1947 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
1948 flog_err(EC_BGP_PEER_GROUP, "%s was called for peer-group %s",
1949 __func__, peer->host);
1950 return 1;
1951 }
1952
1953 /* Do not activate a peer for both SAFI_UNICAST and SAFI_LABELED_UNICAST
1954 */
1955 if ((safi == SAFI_UNICAST && peer->afc[afi][SAFI_LABELED_UNICAST])
1956 || (safi == SAFI_LABELED_UNICAST && peer->afc[afi][SAFI_UNICAST]))
1957 return BGP_ERR_PEER_SAFI_CONFLICT;
1958
1959 /* Nothing to do if we've already activated this peer */
1960 if (peer->afc[afi][safi])
1961 return 0;
1962
1963 if (peer_af_create(peer, afi, safi) == NULL)
1964 return 1;
1965
1966 active = peer_active(peer);
1967 peer->afc[afi][safi] = 1;
1968
1969 if (peer->group)
1970 peer_group2peer_config_copy_af(peer->group, peer, afi, safi);
1971
1972 if (!active && peer_active(peer)) {
1973 bgp_timer_set(peer);
1974 } else {
1975 if (peer->status == Established) {
1976 if (CHECK_FLAG(peer->cap, PEER_CAP_DYNAMIC_RCV)) {
1977 peer->afc_adv[afi][safi] = 1;
1978 bgp_capability_send(peer, afi, safi,
1979 CAPABILITY_CODE_MP,
1980 CAPABILITY_ACTION_SET);
1981 if (peer->afc_recv[afi][safi]) {
1982 peer->afc_nego[afi][safi] = 1;
1983 bgp_announce_route(peer, afi, safi);
1984 }
1985 } else {
1986 peer->last_reset = PEER_DOWN_AF_ACTIVATE;
1987 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
1988 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
1989 }
1990 }
1991 if (peer->status == OpenSent || peer->status == OpenConfirm) {
1992 peer->last_reset = PEER_DOWN_AF_ACTIVATE;
1993 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
1994 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
1995 }
1996 /*
1997 * If we are turning on a AFI/SAFI locally and we've
1998 * started bringing a peer up, we need to tell
1999 * the other peer to restart because we might loose
2000 * configuration here because when the doppelganger
2001 * gets to a established state due to how
2002 * we resolve we could just overwrite the afi/safi
2003 * activation.
2004 */
2005 other = peer->doppelganger;
2006 if (other
2007 && (other->status == OpenSent
2008 || other->status == OpenConfirm)) {
2009 other->last_reset = PEER_DOWN_AF_ACTIVATE;
2010 bgp_notify_send(other, BGP_NOTIFY_CEASE,
2011 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2012 }
2013 }
2014
2015 return 0;
2016 }
2017
2018 /* Activate the peer or peer group for specified AFI and SAFI. */
2019 int peer_activate(struct peer *peer, afi_t afi, safi_t safi)
2020 {
2021 int ret = 0;
2022 struct peer_group *group;
2023 struct listnode *node, *nnode;
2024 struct peer *tmp_peer;
2025 struct bgp *bgp;
2026
2027 /* Nothing to do if we've already activated this peer */
2028 if (peer->afc[afi][safi])
2029 return ret;
2030
2031 bgp = peer->bgp;
2032
2033 /* This is a peer-group so activate all of the members of the
2034 * peer-group as well */
2035 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
2036
2037 /* Do not activate a peer for both SAFI_UNICAST and
2038 * SAFI_LABELED_UNICAST */
2039 if ((safi == SAFI_UNICAST
2040 && peer->afc[afi][SAFI_LABELED_UNICAST])
2041 || (safi == SAFI_LABELED_UNICAST
2042 && peer->afc[afi][SAFI_UNICAST]))
2043 return BGP_ERR_PEER_SAFI_CONFLICT;
2044
2045 peer->afc[afi][safi] = 1;
2046 group = peer->group;
2047
2048 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, tmp_peer)) {
2049 ret |= peer_activate_af(tmp_peer, afi, safi);
2050 }
2051 } else {
2052 ret |= peer_activate_af(peer, afi, safi);
2053 }
2054
2055 /* If this is the first peer to be activated for this
2056 * afi/labeled-unicast recalc bestpaths to trigger label allocation */
2057 if (safi == SAFI_LABELED_UNICAST
2058 && !bgp->allocate_mpls_labels[afi][SAFI_UNICAST]) {
2059
2060 if (BGP_DEBUG(zebra, ZEBRA))
2061 zlog_debug(
2062 "peer(s) are now active for labeled-unicast, allocate MPLS labels");
2063
2064 bgp->allocate_mpls_labels[afi][SAFI_UNICAST] = 1;
2065 bgp_recalculate_afi_safi_bestpaths(bgp, afi, SAFI_UNICAST);
2066 }
2067
2068 if (safi == SAFI_FLOWSPEC) {
2069 /* connect to table manager */
2070 bgp_zebra_init_tm_connect(bgp);
2071 }
2072 return ret;
2073 }
2074
2075 static int non_peergroup_deactivate_af(struct peer *peer, afi_t afi,
2076 safi_t safi)
2077 {
2078 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
2079 flog_err(EC_BGP_PEER_GROUP, "%s was called for peer-group %s",
2080 __func__, peer->host);
2081 return 1;
2082 }
2083
2084 /* Nothing to do if we've already deactivated this peer */
2085 if (!peer->afc[afi][safi])
2086 return 0;
2087
2088 /* De-activate the address family configuration. */
2089 peer->afc[afi][safi] = 0;
2090
2091 if (peer_af_delete(peer, afi, safi) != 0) {
2092 flog_err(EC_BGP_PEER_DELETE,
2093 "couldn't delete af structure for peer %s",
2094 peer->host);
2095 return 1;
2096 }
2097
2098 if (peer->status == Established) {
2099 if (CHECK_FLAG(peer->cap, PEER_CAP_DYNAMIC_RCV)) {
2100 peer->afc_adv[afi][safi] = 0;
2101 peer->afc_nego[afi][safi] = 0;
2102
2103 if (peer_active_nego(peer)) {
2104 bgp_capability_send(peer, afi, safi,
2105 CAPABILITY_CODE_MP,
2106 CAPABILITY_ACTION_UNSET);
2107 bgp_clear_route(peer, afi, safi);
2108 peer->pcount[afi][safi] = 0;
2109 } else {
2110 peer->last_reset = PEER_DOWN_NEIGHBOR_DELETE;
2111 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
2112 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2113 }
2114 } else {
2115 peer->last_reset = PEER_DOWN_NEIGHBOR_DELETE;
2116 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
2117 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2118 }
2119 }
2120
2121 return 0;
2122 }
2123
2124 int peer_deactivate(struct peer *peer, afi_t afi, safi_t safi)
2125 {
2126 int ret = 0;
2127 struct peer_group *group;
2128 struct peer *tmp_peer;
2129 struct listnode *node, *nnode;
2130 struct bgp *bgp;
2131
2132 /* Nothing to do if we've already de-activated this peer */
2133 if (!peer->afc[afi][safi])
2134 return ret;
2135
2136 /* This is a peer-group so de-activate all of the members of the
2137 * peer-group as well */
2138 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
2139 peer->afc[afi][safi] = 0;
2140 group = peer->group;
2141
2142 if (peer_af_delete(peer, afi, safi) != 0) {
2143 flog_err(EC_BGP_PEER_DELETE,
2144 "couldn't delete af structure for peer %s",
2145 peer->host);
2146 }
2147
2148 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, tmp_peer)) {
2149 ret |= non_peergroup_deactivate_af(tmp_peer, afi, safi);
2150 }
2151 } else {
2152 ret |= non_peergroup_deactivate_af(peer, afi, safi);
2153 }
2154
2155 bgp = peer->bgp;
2156
2157 /* If this is the last peer to be deactivated for this
2158 * afi/labeled-unicast recalc bestpaths to trigger label deallocation */
2159 if (safi == SAFI_LABELED_UNICAST
2160 && bgp->allocate_mpls_labels[afi][SAFI_UNICAST]
2161 && !bgp_afi_safi_peer_exists(bgp, afi, safi)) {
2162
2163 if (BGP_DEBUG(zebra, ZEBRA))
2164 zlog_debug(
2165 "peer(s) are no longer active for labeled-unicast, deallocate MPLS labels");
2166
2167 bgp->allocate_mpls_labels[afi][SAFI_UNICAST] = 0;
2168 bgp_recalculate_afi_safi_bestpaths(bgp, afi, SAFI_UNICAST);
2169 }
2170 return ret;
2171 }
2172
2173 int peer_afc_set(struct peer *peer, afi_t afi, safi_t safi, int enable)
2174 {
2175 if (enable)
2176 return peer_activate(peer, afi, safi);
2177 else
2178 return peer_deactivate(peer, afi, safi);
2179 }
2180
2181 void peer_nsf_stop(struct peer *peer)
2182 {
2183 afi_t afi;
2184 safi_t safi;
2185
2186 UNSET_FLAG(peer->sflags, PEER_STATUS_NSF_WAIT);
2187 UNSET_FLAG(peer->sflags, PEER_STATUS_NSF_MODE);
2188
2189 for (afi = AFI_IP; afi < AFI_MAX; afi++)
2190 for (safi = SAFI_UNICAST; safi <= SAFI_MPLS_VPN; safi++)
2191 peer->nsf[afi][safi] = 0;
2192
2193 if (peer->t_gr_restart) {
2194 BGP_TIMER_OFF(peer->t_gr_restart);
2195 if (bgp_debug_neighbor_events(peer))
2196 zlog_debug("%s graceful restart timer stopped",
2197 peer->host);
2198 }
2199 if (peer->t_gr_stale) {
2200 BGP_TIMER_OFF(peer->t_gr_stale);
2201 if (bgp_debug_neighbor_events(peer))
2202 zlog_debug(
2203 "%s graceful restart stalepath timer stopped",
2204 peer->host);
2205 }
2206 bgp_clear_route_all(peer);
2207 }
2208
2209 /* Delete peer from confguration.
2210 *
2211 * The peer is moved to a dead-end "Deleted" neighbour-state, to allow
2212 * it to "cool off" and refcounts to hit 0, at which state it is freed.
2213 *
2214 * This function /should/ take care to be idempotent, to guard against
2215 * it being called multiple times through stray events that come in
2216 * that happen to result in this function being called again. That
2217 * said, getting here for a "Deleted" peer is a bug in the neighbour
2218 * FSM.
2219 */
2220 int peer_delete(struct peer *peer)
2221 {
2222 int i;
2223 afi_t afi;
2224 safi_t safi;
2225 struct bgp *bgp;
2226 struct bgp_filter *filter;
2227 struct listnode *pn;
2228 int accept_peer;
2229
2230 assert(peer->status != Deleted);
2231
2232 bgp = peer->bgp;
2233 accept_peer = CHECK_FLAG(peer->sflags, PEER_STATUS_ACCEPT_PEER);
2234
2235 bgp_keepalives_off(peer);
2236 bgp_reads_off(peer);
2237 bgp_writes_off(peer);
2238 assert(!CHECK_FLAG(peer->thread_flags, PEER_THREAD_WRITES_ON));
2239 assert(!CHECK_FLAG(peer->thread_flags, PEER_THREAD_READS_ON));
2240 assert(!CHECK_FLAG(peer->thread_flags, PEER_THREAD_KEEPALIVES_ON));
2241
2242 if (CHECK_FLAG(peer->sflags, PEER_STATUS_NSF_WAIT))
2243 peer_nsf_stop(peer);
2244
2245 SET_FLAG(peer->flags, PEER_FLAG_DELETE);
2246
2247 bgp_bfd_deregister_peer(peer);
2248
2249 /* If this peer belongs to peer group, clear up the
2250 relationship. */
2251 if (peer->group) {
2252 if (peer_dynamic_neighbor(peer))
2253 peer_drop_dynamic_neighbor(peer);
2254
2255 if ((pn = listnode_lookup(peer->group->peer, peer))) {
2256 peer = peer_unlock(
2257 peer); /* group->peer list reference */
2258 list_delete_node(peer->group->peer, pn);
2259 }
2260 peer->group = NULL;
2261 }
2262
2263 /* Withdraw all information from routing table. We can not use
2264 * BGP_EVENT_ADD (peer, BGP_Stop) at here. Because the event is
2265 * executed after peer structure is deleted.
2266 */
2267 peer->last_reset = PEER_DOWN_NEIGHBOR_DELETE;
2268 bgp_stop(peer);
2269 UNSET_FLAG(peer->flags, PEER_FLAG_DELETE);
2270
2271 if (peer->doppelganger) {
2272 peer->doppelganger->doppelganger = NULL;
2273 peer->doppelganger = NULL;
2274 }
2275
2276 UNSET_FLAG(peer->sflags, PEER_STATUS_ACCEPT_PEER);
2277 bgp_fsm_change_status(peer, Deleted);
2278
2279 /* Remove from NHT */
2280 if (CHECK_FLAG(peer->flags, PEER_FLAG_CONFIG_NODE))
2281 bgp_unlink_nexthop_by_peer(peer);
2282
2283 /* Password configuration */
2284 if (CHECK_FLAG(peer->flags, PEER_FLAG_PASSWORD)) {
2285 XFREE(MTYPE_PEER_PASSWORD, peer->password);
2286
2287 if (!accept_peer && !BGP_PEER_SU_UNSPEC(peer)
2288 && !CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
2289 bgp_md5_unset(peer);
2290 }
2291
2292 bgp_timer_set(peer); /* stops all timers for Deleted */
2293
2294 /* Delete from all peer list. */
2295 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)
2296 && (pn = listnode_lookup(bgp->peer, peer))) {
2297 peer_unlock(peer); /* bgp peer list reference */
2298 list_delete_node(bgp->peer, pn);
2299 hash_release(bgp->peerhash, peer);
2300 }
2301
2302 /* Buffers. */
2303 if (peer->ibuf) {
2304 stream_fifo_free(peer->ibuf);
2305 peer->ibuf = NULL;
2306 }
2307
2308 if (peer->obuf) {
2309 stream_fifo_free(peer->obuf);
2310 peer->obuf = NULL;
2311 }
2312
2313 if (peer->ibuf_work) {
2314 ringbuf_del(peer->ibuf_work);
2315 peer->ibuf_work = NULL;
2316 }
2317
2318 if (peer->obuf_work) {
2319 stream_free(peer->obuf_work);
2320 peer->obuf_work = NULL;
2321 }
2322
2323 if (peer->scratch) {
2324 stream_free(peer->scratch);
2325 peer->scratch = NULL;
2326 }
2327
2328 /* Local and remote addresses. */
2329 if (peer->su_local) {
2330 sockunion_free(peer->su_local);
2331 peer->su_local = NULL;
2332 }
2333
2334 if (peer->su_remote) {
2335 sockunion_free(peer->su_remote);
2336 peer->su_remote = NULL;
2337 }
2338
2339 /* Free filter related memory. */
2340 FOREACH_AFI_SAFI (afi, safi) {
2341 filter = &peer->filter[afi][safi];
2342
2343 for (i = FILTER_IN; i < FILTER_MAX; i++) {
2344 XFREE(MTYPE_BGP_FILTER_NAME, filter->dlist[i].name);
2345 XFREE(MTYPE_BGP_FILTER_NAME, filter->plist[i].name);
2346 XFREE(MTYPE_BGP_FILTER_NAME, filter->aslist[i].name);
2347 }
2348
2349 for (i = RMAP_IN; i < RMAP_MAX; i++) {
2350 XFREE(MTYPE_BGP_FILTER_NAME, filter->map[i].name);
2351 }
2352
2353 XFREE(MTYPE_BGP_FILTER_NAME, filter->usmap.name);
2354 XFREE(MTYPE_ROUTE_MAP_NAME, peer->default_rmap[afi][safi].name);
2355 }
2356
2357 FOREACH_AFI_SAFI (afi, safi)
2358 peer_af_delete(peer, afi, safi);
2359
2360 XFREE(MTYPE_BGP_PEER_HOST, peer->hostname);
2361 XFREE(MTYPE_BGP_PEER_HOST, peer->domainname);
2362
2363 peer_unlock(peer); /* initial reference */
2364
2365 return 0;
2366 }
2367
2368 static int peer_group_cmp(struct peer_group *g1, struct peer_group *g2)
2369 {
2370 return strcmp(g1->name, g2->name);
2371 }
2372
2373 /* Peer group cofiguration. */
2374 static struct peer_group *peer_group_new(void)
2375 {
2376 return XCALLOC(MTYPE_PEER_GROUP, sizeof(struct peer_group));
2377 }
2378
2379 static void peer_group_free(struct peer_group *group)
2380 {
2381 XFREE(MTYPE_PEER_GROUP, group);
2382 }
2383
2384 struct peer_group *peer_group_lookup(struct bgp *bgp, const char *name)
2385 {
2386 struct peer_group *group;
2387 struct listnode *node, *nnode;
2388
2389 for (ALL_LIST_ELEMENTS(bgp->group, node, nnode, group)) {
2390 if (strcmp(group->name, name) == 0)
2391 return group;
2392 }
2393 return NULL;
2394 }
2395
2396 struct peer_group *peer_group_get(struct bgp *bgp, const char *name)
2397 {
2398 struct peer_group *group;
2399 afi_t afi;
2400
2401 group = peer_group_lookup(bgp, name);
2402 if (group)
2403 return group;
2404
2405 group = peer_group_new();
2406 group->bgp = bgp;
2407 XFREE(MTYPE_PEER_GROUP_HOST, group->name);
2408 group->name = XSTRDUP(MTYPE_PEER_GROUP_HOST, name);
2409 group->peer = list_new();
2410 for (afi = AFI_IP; afi < AFI_MAX; afi++)
2411 group->listen_range[afi] = list_new();
2412 group->conf = peer_new(bgp);
2413 if (!CHECK_FLAG(bgp->flags, BGP_FLAG_NO_DEFAULT_IPV4))
2414 group->conf->afc[AFI_IP][SAFI_UNICAST] = 1;
2415 XFREE(MTYPE_BGP_PEER_HOST, group->conf->host);
2416 group->conf->host = XSTRDUP(MTYPE_BGP_PEER_HOST, name);
2417 group->conf->group = group;
2418 group->conf->as = 0;
2419 group->conf->ttl = BGP_DEFAULT_TTL;
2420 group->conf->gtsm_hops = 0;
2421 group->conf->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
2422 SET_FLAG(group->conf->sflags, PEER_STATUS_GROUP);
2423 listnode_add_sort(bgp->group, group);
2424
2425 return group;
2426 }
2427
2428 static void peer_group2peer_config_copy(struct peer_group *group,
2429 struct peer *peer)
2430 {
2431 uint32_t flags_tmp;
2432 struct peer *conf;
2433
2434 conf = group->conf;
2435
2436 /* remote-as */
2437 if (conf->as)
2438 peer->as = conf->as;
2439
2440 /* local-as */
2441 if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_LOCAL_AS))
2442 peer->change_local_as = conf->change_local_as;
2443
2444 /* If peer-group has configured TTL then override it */
2445 if (conf->ttl != BGP_DEFAULT_TTL)
2446 peer->ttl = conf->ttl;
2447
2448 /* GTSM hops */
2449 peer->gtsm_hops = conf->gtsm_hops;
2450
2451 /* peer flags apply */
2452 flags_tmp = conf->flags & ~peer->flags_override;
2453 flags_tmp ^= conf->flags_invert ^ peer->flags_invert;
2454 flags_tmp &= ~peer->flags_override;
2455
2456 UNSET_FLAG(peer->flags, ~peer->flags_override);
2457 SET_FLAG(peer->flags, flags_tmp);
2458 SET_FLAG(peer->flags_invert, conf->flags_invert);
2459
2460 /* peer timers apply */
2461 if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_TIMER)) {
2462 PEER_ATTR_INHERIT(peer, group, holdtime);
2463 PEER_ATTR_INHERIT(peer, group, keepalive);
2464 }
2465
2466 if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_TIMER_CONNECT)) {
2467 PEER_ATTR_INHERIT(peer, group, connect);
2468 if (CHECK_FLAG(conf->flags, PEER_FLAG_TIMER_CONNECT))
2469 peer->v_connect = conf->connect;
2470 else
2471 peer->v_connect = peer->bgp->default_connect_retry;
2472 }
2473
2474 /* advertisement-interval apply */
2475 if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_ROUTEADV)) {
2476 PEER_ATTR_INHERIT(peer, group, routeadv);
2477 if (CHECK_FLAG(conf->flags, PEER_FLAG_ROUTEADV))
2478 peer->v_routeadv = conf->routeadv;
2479 else
2480 peer->v_routeadv = (peer_sort(peer) == BGP_PEER_IBGP)
2481 ? BGP_DEFAULT_IBGP_ROUTEADV
2482 : BGP_DEFAULT_EBGP_ROUTEADV;
2483 }
2484
2485 /* password apply */
2486 if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_PASSWORD))
2487 PEER_STR_ATTR_INHERIT(peer, group, password,
2488 MTYPE_PEER_PASSWORD);
2489
2490 if (!BGP_PEER_SU_UNSPEC(peer))
2491 bgp_md5_set(peer);
2492
2493 /* update-source apply */
2494 if (!CHECK_FLAG(peer->flags_override, PEER_FLAG_UPDATE_SOURCE)) {
2495 if (conf->update_source) {
2496 XFREE(MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
2497 PEER_SU_ATTR_INHERIT(peer, group, update_source);
2498 } else if (conf->update_if) {
2499 sockunion_free(peer->update_source);
2500 PEER_STR_ATTR_INHERIT(peer, group, update_if,
2501 MTYPE_PEER_UPDATE_SOURCE);
2502 }
2503 }
2504
2505 bgp_bfd_peer_group2peer_copy(conf, peer);
2506 }
2507
2508 /* Peer group's remote AS configuration. */
2509 int peer_group_remote_as(struct bgp *bgp, const char *group_name, as_t *as,
2510 int as_type)
2511 {
2512 struct peer_group *group;
2513 struct peer *peer;
2514 struct listnode *node, *nnode;
2515
2516 group = peer_group_lookup(bgp, group_name);
2517 if (!group)
2518 return -1;
2519
2520 if ((as_type == group->conf->as_type) && (group->conf->as == *as))
2521 return 0;
2522
2523
2524 /* When we setup peer-group AS number all peer group member's AS
2525 number must be updated to same number. */
2526 peer_as_change(group->conf, *as, as_type);
2527
2528 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
2529 if (((peer->as_type == AS_SPECIFIED) && peer->as != *as)
2530 || (peer->as_type != as_type))
2531 peer_as_change(peer, *as, as_type);
2532 }
2533
2534 return 0;
2535 }
2536
2537 int peer_notify_unconfig(struct peer *peer)
2538 {
2539 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2540 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
2541 BGP_NOTIFY_CEASE_PEER_UNCONFIG);
2542 return 0;
2543 }
2544
2545 int peer_group_notify_unconfig(struct peer_group *group)
2546 {
2547 struct peer *peer, *other;
2548 struct listnode *node, *nnode;
2549
2550 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
2551 other = peer->doppelganger;
2552 if (other && other->status != Deleted) {
2553 other->group = NULL;
2554 peer_notify_unconfig(other);
2555 } else
2556 peer_notify_unconfig(peer);
2557 }
2558 return 0;
2559 }
2560
2561 int peer_group_delete(struct peer_group *group)
2562 {
2563 struct bgp *bgp;
2564 struct peer *peer;
2565 struct prefix *prefix;
2566 struct peer *other;
2567 struct listnode *node, *nnode;
2568 afi_t afi;
2569
2570 bgp = group->bgp;
2571
2572 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
2573 other = peer->doppelganger;
2574 peer_delete(peer);
2575 if (other && other->status != Deleted) {
2576 other->group = NULL;
2577 peer_delete(other);
2578 }
2579 }
2580 list_delete(&group->peer);
2581
2582 for (afi = AFI_IP; afi < AFI_MAX; afi++) {
2583 for (ALL_LIST_ELEMENTS(group->listen_range[afi], node, nnode,
2584 prefix)) {
2585 prefix_free(&prefix);
2586 }
2587 list_delete(&group->listen_range[afi]);
2588 }
2589
2590 XFREE(MTYPE_PEER_GROUP_HOST, group->name);
2591 group->name = NULL;
2592
2593 bfd_info_free(&(group->conf->bfd_info));
2594
2595 group->conf->group = NULL;
2596 peer_delete(group->conf);
2597
2598 /* Delete from all peer_group list. */
2599 listnode_delete(bgp->group, group);
2600
2601 peer_group_free(group);
2602
2603 return 0;
2604 }
2605
2606 int peer_group_remote_as_delete(struct peer_group *group)
2607 {
2608 struct peer *peer, *other;
2609 struct listnode *node, *nnode;
2610
2611 if ((group->conf->as_type == AS_UNSPECIFIED)
2612 || ((!group->conf->as) && (group->conf->as_type == AS_SPECIFIED)))
2613 return 0;
2614
2615 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
2616 other = peer->doppelganger;
2617
2618 peer_delete(peer);
2619
2620 if (other && other->status != Deleted) {
2621 other->group = NULL;
2622 peer_delete(other);
2623 }
2624 }
2625 list_delete_all_node(group->peer);
2626
2627 group->conf->as = 0;
2628 group->conf->as_type = AS_UNSPECIFIED;
2629
2630 return 0;
2631 }
2632
2633 int peer_group_listen_range_add(struct peer_group *group, struct prefix *range)
2634 {
2635 struct prefix *prefix;
2636 struct listnode *node, *nnode;
2637 afi_t afi;
2638
2639 afi = family2afi(range->family);
2640
2641 /* Group needs remote AS configured. */
2642 if (group->conf->as_type == AS_UNSPECIFIED)
2643 return BGP_ERR_PEER_GROUP_NO_REMOTE_AS;
2644
2645 /* Ensure no duplicates. Currently we don't care about overlaps. */
2646 for (ALL_LIST_ELEMENTS(group->listen_range[afi], node, nnode, prefix)) {
2647 if (prefix_same(range, prefix))
2648 return 0;
2649 }
2650
2651 prefix = prefix_new();
2652 prefix_copy(prefix, range);
2653 listnode_add(group->listen_range[afi], prefix);
2654
2655 /* Update passwords for new ranges */
2656 if (group->conf->password)
2657 bgp_md5_set_prefix(prefix, group->conf->password);
2658
2659 return 0;
2660 }
2661
2662 int peer_group_listen_range_del(struct peer_group *group, struct prefix *range)
2663 {
2664 struct prefix *prefix, prefix2;
2665 struct listnode *node, *nnode;
2666 struct peer *peer;
2667 afi_t afi;
2668 char buf[PREFIX2STR_BUFFER];
2669
2670 afi = family2afi(range->family);
2671
2672 /* Identify the listen range. */
2673 for (ALL_LIST_ELEMENTS(group->listen_range[afi], node, nnode, prefix)) {
2674 if (prefix_same(range, prefix))
2675 break;
2676 }
2677
2678 if (!prefix)
2679 return BGP_ERR_DYNAMIC_NEIGHBORS_RANGE_NOT_FOUND;
2680
2681 prefix2str(prefix, buf, sizeof(buf));
2682
2683 /* Dispose off any dynamic neighbors that exist due to this listen range
2684 */
2685 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
2686 if (!peer_dynamic_neighbor(peer))
2687 continue;
2688
2689 sockunion2hostprefix(&peer->su, &prefix2);
2690 if (prefix_match(prefix, &prefix2)) {
2691 if (bgp_debug_neighbor_events(peer))
2692 zlog_debug(
2693 "Deleting dynamic neighbor %s group %s upon "
2694 "delete of listen range %s",
2695 peer->host, group->name, buf);
2696 peer_delete(peer);
2697 }
2698 }
2699
2700 /* Get rid of the listen range */
2701 listnode_delete(group->listen_range[afi], prefix);
2702
2703 /* Remove passwords for deleted ranges */
2704 if (group->conf->password)
2705 bgp_md5_unset_prefix(prefix);
2706
2707 return 0;
2708 }
2709
2710 /* Bind specified peer to peer group. */
2711 int peer_group_bind(struct bgp *bgp, union sockunion *su, struct peer *peer,
2712 struct peer_group *group, as_t *as)
2713 {
2714 int first_member = 0;
2715 afi_t afi;
2716 safi_t safi;
2717
2718 /* Lookup the peer. */
2719 if (!peer)
2720 peer = peer_lookup(bgp, su);
2721
2722 /* The peer exist, bind it to the peer-group */
2723 if (peer) {
2724 /* When the peer already belongs to a peer-group, check the
2725 * consistency. */
2726 if (peer_group_active(peer)) {
2727
2728 /* The peer is already bound to the peer-group,
2729 * nothing to do
2730 */
2731 if (strcmp(peer->group->name, group->name) == 0)
2732 return 0;
2733 else
2734 return BGP_ERR_PEER_GROUP_CANT_CHANGE;
2735 }
2736
2737 /* The peer has not specified a remote-as, inherit it from the
2738 * peer-group */
2739 if (peer->as_type == AS_UNSPECIFIED) {
2740 peer->as_type = group->conf->as_type;
2741 peer->as = group->conf->as;
2742 peer->sort = group->conf->sort;
2743 }
2744
2745 if (!group->conf->as && peer_sort(peer)) {
2746 if (peer_sort(group->conf) != BGP_PEER_INTERNAL
2747 && peer_sort(group->conf) != peer_sort(peer)) {
2748 if (as)
2749 *as = peer->as;
2750 return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT;
2751 }
2752
2753 if (peer_sort(group->conf) == BGP_PEER_INTERNAL)
2754 first_member = 1;
2755 }
2756
2757 peer_group2peer_config_copy(group, peer);
2758
2759 FOREACH_AFI_SAFI (afi, safi) {
2760 if (group->conf->afc[afi][safi]) {
2761 peer->afc[afi][safi] = 1;
2762
2763 if (peer_af_find(peer, afi, safi)
2764 || peer_af_create(peer, afi, safi)) {
2765 peer_group2peer_config_copy_af(
2766 group, peer, afi, safi);
2767 }
2768 } else if (peer->afc[afi][safi])
2769 peer_deactivate(peer, afi, safi);
2770 }
2771
2772 if (peer->group) {
2773 assert(group && peer->group == group);
2774 } else {
2775 listnode_delete(bgp->peer, peer);
2776
2777 peer->group = group;
2778 listnode_add_sort(bgp->peer, peer);
2779
2780 peer = peer_lock(peer); /* group->peer list reference */
2781 listnode_add(group->peer, peer);
2782 }
2783
2784 if (first_member) {
2785 /* Advertisement-interval reset */
2786 if (!CHECK_FLAG(group->conf->flags,
2787 PEER_FLAG_ROUTEADV)) {
2788 group->conf->v_routeadv =
2789 (peer_sort(group->conf)
2790 == BGP_PEER_IBGP)
2791 ? BGP_DEFAULT_IBGP_ROUTEADV
2792 : BGP_DEFAULT_EBGP_ROUTEADV;
2793 }
2794
2795 /* ebgp-multihop reset */
2796 if (peer_sort(group->conf) == BGP_PEER_IBGP)
2797 group->conf->ttl = MAXTTL;
2798
2799 /* local-as reset */
2800 if (peer_sort(group->conf) != BGP_PEER_EBGP) {
2801 group->conf->change_local_as = 0;
2802 peer_flag_unset(group->conf,
2803 PEER_FLAG_LOCAL_AS);
2804 peer_flag_unset(group->conf,
2805 PEER_FLAG_LOCAL_AS_NO_PREPEND);
2806 peer_flag_unset(group->conf,
2807 PEER_FLAG_LOCAL_AS_REPLACE_AS);
2808 }
2809 }
2810
2811 SET_FLAG(peer->flags, PEER_FLAG_CONFIG_NODE);
2812
2813 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
2814 peer->last_reset = PEER_DOWN_RMAP_BIND;
2815 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
2816 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2817 } else {
2818 bgp_session_reset(peer);
2819 }
2820 }
2821
2822 /* Create a new peer. */
2823 else {
2824 if ((group->conf->as_type == AS_SPECIFIED)
2825 && (!group->conf->as)) {
2826 return BGP_ERR_PEER_GROUP_NO_REMOTE_AS;
2827 }
2828
2829 peer = peer_create(su, NULL, bgp, bgp->as, group->conf->as,
2830 group->conf->as_type, 0, 0, group);
2831
2832 peer = peer_lock(peer); /* group->peer list reference */
2833 listnode_add(group->peer, peer);
2834
2835 peer_group2peer_config_copy(group, peer);
2836
2837 /* If the peer-group is active for this afi/safi then activate
2838 * for this peer */
2839 FOREACH_AFI_SAFI (afi, safi) {
2840 if (group->conf->afc[afi][safi]) {
2841 peer->afc[afi][safi] = 1;
2842 peer_af_create(peer, afi, safi);
2843 peer_group2peer_config_copy_af(group, peer, afi,
2844 safi);
2845 } else if (peer->afc[afi][safi])
2846 peer_deactivate(peer, afi, safi);
2847 }
2848
2849 SET_FLAG(peer->flags, PEER_FLAG_CONFIG_NODE);
2850
2851 /* Set up peer's events and timers. */
2852 if (peer_active(peer))
2853 bgp_timer_set(peer);
2854 }
2855
2856 return 0;
2857 }
2858
2859 static int bgp_startup_timer_expire(struct thread *thread)
2860 {
2861 struct bgp *bgp;
2862
2863 bgp = THREAD_ARG(thread);
2864 bgp->t_startup = NULL;
2865
2866 return 0;
2867 }
2868
2869 /*
2870 * On shutdown we call the cleanup function which
2871 * does a free of the link list nodes, free up
2872 * the data we are pointing at too.
2873 */
2874 static void bgp_vrf_string_name_delete(void *data)
2875 {
2876 char *vname = data;
2877
2878 XFREE(MTYPE_TMP, vname);
2879 }
2880
2881 /* BGP instance creation by `router bgp' commands. */
2882 static struct bgp *bgp_create(as_t *as, const char *name,
2883 enum bgp_instance_type inst_type)
2884 {
2885 struct bgp *bgp;
2886 afi_t afi;
2887 safi_t safi;
2888
2889 if ((bgp = XCALLOC(MTYPE_BGP, sizeof(struct bgp))) == NULL)
2890 return NULL;
2891
2892 if (BGP_DEBUG(zebra, ZEBRA)) {
2893 if (inst_type == BGP_INSTANCE_TYPE_DEFAULT)
2894 zlog_debug("Creating Default VRF, AS %u", *as);
2895 else
2896 zlog_debug("Creating %s %s, AS %u",
2897 (inst_type == BGP_INSTANCE_TYPE_VRF)
2898 ? "VRF"
2899 : "VIEW",
2900 name, *as);
2901 }
2902
2903 /* Default the EVPN VRF to the default one */
2904 if (inst_type == BGP_INSTANCE_TYPE_DEFAULT && !bgp_master.bgp_evpn) {
2905 bgp_lock(bgp);
2906 bm->bgp_evpn = bgp;
2907 }
2908
2909 bgp_lock(bgp);
2910 bgp->heuristic_coalesce = true;
2911 bgp->inst_type = inst_type;
2912 bgp->vrf_id = (inst_type == BGP_INSTANCE_TYPE_DEFAULT) ? VRF_DEFAULT
2913 : VRF_UNKNOWN;
2914 bgp->peer_self = peer_new(bgp);
2915 XFREE(MTYPE_BGP_PEER_HOST, bgp->peer_self->host);
2916 bgp->peer_self->host =
2917 XSTRDUP(MTYPE_BGP_PEER_HOST, "Static announcement");
2918 XFREE(MTYPE_BGP_PEER_HOST, bgp->peer_self->hostname);
2919 if (cmd_hostname_get())
2920 bgp->peer_self->hostname =
2921 XSTRDUP(MTYPE_BGP_PEER_HOST, cmd_hostname_get());
2922
2923 XFREE(MTYPE_BGP_PEER_HOST, bgp->peer_self->domainname);
2924 if (cmd_domainname_get())
2925 bgp->peer_self->domainname =
2926 XSTRDUP(MTYPE_BGP_PEER_HOST, cmd_domainname_get());
2927 bgp->peer = list_new();
2928 bgp->peer->cmp = (int (*)(void *, void *))peer_cmp;
2929 bgp->peerhash = hash_create(peer_hash_key_make, peer_hash_same,
2930 "BGP Peer Hash");
2931 bgp->peerhash->max_size = BGP_PEER_MAX_HASH_SIZE;
2932
2933 bgp->group = list_new();
2934 bgp->group->cmp = (int (*)(void *, void *))peer_group_cmp;
2935
2936 FOREACH_AFI_SAFI (afi, safi) {
2937 bgp->route[afi][safi] = bgp_table_init(bgp, afi, safi);
2938 bgp->aggregate[afi][safi] = bgp_table_init(bgp, afi, safi);
2939 bgp->rib[afi][safi] = bgp_table_init(bgp, afi, safi);
2940
2941 /* Enable maximum-paths */
2942 bgp_maximum_paths_set(bgp, afi, safi, BGP_PEER_EBGP,
2943 multipath_num, 0);
2944 bgp_maximum_paths_set(bgp, afi, safi, BGP_PEER_IBGP,
2945 multipath_num, 0);
2946 /* Initialize graceful restart info */
2947 bgp->gr_info[afi][safi].eor_required = 0;
2948 bgp->gr_info[afi][safi].eor_received = 0;
2949 bgp->gr_info[afi][safi].t_select_deferral = NULL;
2950 bgp->gr_info[afi][safi].t_route_select = NULL;
2951 bgp->gr_info[afi][safi].route_list = list_new();
2952 }
2953
2954 bgp->v_update_delay = BGP_UPDATE_DELAY_DEF;
2955 bgp->default_local_pref = BGP_DEFAULT_LOCAL_PREF;
2956 bgp->default_subgroup_pkt_queue_max =
2957 BGP_DEFAULT_SUBGROUP_PKT_QUEUE_MAX;
2958 bgp_timers_unset(bgp);
2959 bgp->restart_time = BGP_DEFAULT_RESTART_TIME;
2960 bgp->stalepath_time = BGP_DEFAULT_STALEPATH_TIME;
2961 bgp->select_defer_time = BGP_DEFAULT_SELECT_DEFERRAL_TIME;
2962 bgp->rib_stale_time = BGP_DEFAULT_RIB_STALE_TIME;
2963 bgp->dynamic_neighbors_limit = BGP_DYNAMIC_NEIGHBORS_LIMIT_DEFAULT;
2964 bgp->dynamic_neighbors_count = 0;
2965 bgp->ebgp_requires_policy = DEFAULT_EBGP_POLICY_DISABLED;
2966 bgp->reject_as_sets = BGP_REJECT_AS_SETS_DISABLED;
2967 bgp_addpath_init_bgp_data(&bgp->tx_addpath);
2968
2969 bgp->as = *as;
2970
2971 #if ENABLE_BGP_VNC
2972 if (inst_type != BGP_INSTANCE_TYPE_VRF) {
2973 bgp->rfapi = bgp_rfapi_new(bgp);
2974 assert(bgp->rfapi);
2975 assert(bgp->rfapi_cfg);
2976 }
2977 #endif /* ENABLE_BGP_VNC */
2978
2979 for (afi = AFI_IP; afi < AFI_MAX; afi++) {
2980 bgp->vpn_policy[afi].bgp = bgp;
2981 bgp->vpn_policy[afi].afi = afi;
2982 bgp->vpn_policy[afi].tovpn_label = MPLS_LABEL_NONE;
2983 bgp->vpn_policy[afi].tovpn_zebra_vrf_label_last_sent =
2984 MPLS_LABEL_NONE;
2985
2986 bgp->vpn_policy[afi].import_vrf = list_new();
2987 bgp->vpn_policy[afi].import_vrf->del =
2988 bgp_vrf_string_name_delete;
2989 bgp->vpn_policy[afi].export_vrf = list_new();
2990 bgp->vpn_policy[afi].export_vrf->del =
2991 bgp_vrf_string_name_delete;
2992 }
2993 if (name)
2994 bgp->name = XSTRDUP(MTYPE_BGP, name);
2995
2996 thread_add_timer(bm->master, bgp_startup_timer_expire, bgp,
2997 bgp->restart_time, &bgp->t_startup);
2998
2999 /* printable name we can use in debug messages */
3000 if (inst_type == BGP_INSTANCE_TYPE_DEFAULT) {
3001 bgp->name_pretty = XSTRDUP(MTYPE_BGP, "VRF default");
3002 } else {
3003 const char *n;
3004 int len;
3005
3006 if (bgp->name)
3007 n = bgp->name;
3008 else
3009 n = "?";
3010
3011 len = 4 + 1 + strlen(n) + 1; /* "view foo\0" */
3012
3013 bgp->name_pretty = XCALLOC(MTYPE_BGP, len);
3014 snprintf(bgp->name_pretty, len, "%s %s",
3015 (bgp->inst_type == BGP_INSTANCE_TYPE_VRF)
3016 ? "VRF"
3017 : "VIEW",
3018 n);
3019 }
3020
3021 atomic_store_explicit(&bgp->wpkt_quanta, BGP_WRITE_PACKET_MAX,
3022 memory_order_relaxed);
3023 atomic_store_explicit(&bgp->rpkt_quanta, BGP_READ_PACKET_MAX,
3024 memory_order_relaxed);
3025 bgp->coalesce_time = BGP_DEFAULT_SUBGROUP_COALESCE_TIME;
3026
3027 QOBJ_REG(bgp, bgp);
3028
3029 update_bgp_group_init(bgp);
3030
3031 /* assign a unique rd id for auto derivation of vrf's RD */
3032 bf_assign_index(bm->rd_idspace, bgp->vrf_rd_id);
3033
3034 bgp->evpn_info = XCALLOC(MTYPE_BGP_EVPN_INFO,
3035 sizeof(struct bgp_evpn_info));
3036
3037 bgp_evpn_init(bgp);
3038 bgp_pbr_init(bgp);
3039
3040 /*initilize global GR FSM */
3041 bgp_global_gr_init(bgp);
3042 return bgp;
3043 }
3044
3045 /* Return the "default VRF" instance of BGP. */
3046 struct bgp *bgp_get_default(void)
3047 {
3048 struct bgp *bgp;
3049 struct listnode *node, *nnode;
3050
3051 for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp))
3052 if (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
3053 return bgp;
3054 return NULL;
3055 }
3056
3057 /* Lookup BGP entry. */
3058 struct bgp *bgp_lookup(as_t as, const char *name)
3059 {
3060 struct bgp *bgp;
3061 struct listnode *node, *nnode;
3062
3063 for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp))
3064 if (bgp->as == as
3065 && ((bgp->name == NULL && name == NULL)
3066 || (bgp->name && name && strcmp(bgp->name, name) == 0)))
3067 return bgp;
3068 return NULL;
3069 }
3070
3071 /* Lookup BGP structure by view name. */
3072 struct bgp *bgp_lookup_by_name(const char *name)
3073 {
3074 struct bgp *bgp;
3075 struct listnode *node, *nnode;
3076
3077 for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp))
3078 if ((bgp->name == NULL && name == NULL)
3079 || (bgp->name && name && strcmp(bgp->name, name) == 0))
3080 return bgp;
3081 return NULL;
3082 }
3083
3084 /* Lookup BGP instance based on VRF id. */
3085 /* Note: Only to be used for incoming messages from Zebra. */
3086 struct bgp *bgp_lookup_by_vrf_id(vrf_id_t vrf_id)
3087 {
3088 struct vrf *vrf;
3089
3090 /* Lookup VRF (in tree) and follow link. */
3091 vrf = vrf_lookup_by_id(vrf_id);
3092 if (!vrf)
3093 return NULL;
3094 return (vrf->info) ? (struct bgp *)vrf->info : NULL;
3095 }
3096
3097 /* Sets the BGP instance where EVPN is enabled */
3098 void bgp_set_evpn(struct bgp *bgp)
3099 {
3100 if (bm->bgp_evpn == bgp)
3101 return;
3102
3103 /* First, release the reference count we hold on the instance */
3104 if (bm->bgp_evpn)
3105 bgp_unlock(bm->bgp_evpn);
3106
3107 bm->bgp_evpn = bgp;
3108
3109 /* Increase the reference count on this new VRF */
3110 if (bm->bgp_evpn)
3111 bgp_lock(bm->bgp_evpn);
3112 }
3113
3114 /* Returns the BGP instance where EVPN is enabled, if any */
3115 struct bgp *bgp_get_evpn(void)
3116 {
3117 return bm->bgp_evpn;
3118 }
3119
3120 /* handle socket creation or deletion, if necessary
3121 * this is called for all new BGP instances
3122 */
3123 int bgp_handle_socket(struct bgp *bgp, struct vrf *vrf, vrf_id_t old_vrf_id,
3124 bool create)
3125 {
3126 int ret = 0;
3127
3128 /* Create BGP server socket, if listen mode not disabled */
3129 if (!bgp || bgp_option_check(BGP_OPT_NO_LISTEN))
3130 return 0;
3131 if (bgp->inst_type == BGP_INSTANCE_TYPE_VRF) {
3132 /*
3133 * suppress vrf socket
3134 */
3135 if (create == false) {
3136 bgp_close_vrf_socket(bgp);
3137 return 0;
3138 }
3139 if (vrf == NULL)
3140 return BGP_ERR_INVALID_VALUE;
3141 /* do nothing
3142 * if vrf_id did not change
3143 */
3144 if (vrf->vrf_id == old_vrf_id)
3145 return 0;
3146 if (old_vrf_id != VRF_UNKNOWN) {
3147 /* look for old socket. close it. */
3148 bgp_close_vrf_socket(bgp);
3149 }
3150 /* if backend is not yet identified ( VRF_UNKNOWN) then
3151 * creation will be done later
3152 */
3153 if (vrf->vrf_id == VRF_UNKNOWN)
3154 return 0;
3155 ret = bgp_socket(bgp, bm->port, bm->address);
3156 if (ret < 0)
3157 return BGP_ERR_INVALID_VALUE;
3158 return 0;
3159 } else
3160 return bgp_check_main_socket(create, bgp);
3161 }
3162
3163 /* Called from VTY commands. */
3164 int bgp_get(struct bgp **bgp_val, as_t *as, const char *name,
3165 enum bgp_instance_type inst_type)
3166 {
3167 struct bgp *bgp;
3168 struct vrf *vrf = NULL;
3169
3170 /* Multiple instance check. */
3171 if (name)
3172 bgp = bgp_lookup_by_name(name);
3173 else
3174 bgp = bgp_get_default();
3175
3176 /* Already exists. */
3177 if (bgp) {
3178 if (bgp->as != *as) {
3179 *as = bgp->as;
3180 return BGP_ERR_INSTANCE_MISMATCH;
3181 }
3182 if (bgp->inst_type != inst_type)
3183 return BGP_ERR_INSTANCE_MISMATCH;
3184 *bgp_val = bgp;
3185 return BGP_SUCCESS;
3186 }
3187
3188 bgp = bgp_create(as, name, inst_type);
3189 if (bgp_option_check(BGP_OPT_NO_ZEBRA) && name)
3190 bgp->vrf_id = vrf_generate_id();
3191 bgp_router_id_set(bgp, &bgp->router_id_zebra, true);
3192 bgp_address_init(bgp);
3193 bgp_tip_hash_init(bgp);
3194 bgp_scan_init(bgp);
3195 *bgp_val = bgp;
3196
3197 bgp->t_rmap_def_originate_eval = NULL;
3198
3199 /* If Default instance or VRF, link to the VRF structure, if present. */
3200 if (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT
3201 || bgp->inst_type == BGP_INSTANCE_TYPE_VRF) {
3202 vrf = bgp_vrf_lookup_by_instance_type(bgp);
3203 if (vrf)
3204 bgp_vrf_link(bgp, vrf);
3205 }
3206 /* BGP server socket already processed if BGP instance
3207 * already part of the list
3208 */
3209 bgp_handle_socket(bgp, vrf, VRF_UNKNOWN, true);
3210 listnode_add(bm->bgp, bgp);
3211
3212 if (IS_BGP_INST_KNOWN_TO_ZEBRA(bgp)) {
3213 if (BGP_DEBUG(zebra, ZEBRA))
3214 zlog_debug("%s: Registering BGP instance %s to zebra",
3215 __PRETTY_FUNCTION__, name);
3216 bgp_zebra_instance_register(bgp);
3217 }
3218
3219 return BGP_CREATED;
3220 }
3221
3222 /*
3223 * Make BGP instance "up". Applies only to VRFs (non-default) and
3224 * implies the VRF has been learnt from Zebra.
3225 */
3226 void bgp_instance_up(struct bgp *bgp)
3227 {
3228 struct peer *peer;
3229 struct listnode *node, *next;
3230
3231 /* Register with zebra. */
3232 bgp_zebra_instance_register(bgp);
3233
3234 /* Kick off any peers that may have been configured. */
3235 for (ALL_LIST_ELEMENTS(bgp->peer, node, next, peer)) {
3236 if (!BGP_PEER_START_SUPPRESSED(peer))
3237 BGP_EVENT_ADD(peer, BGP_Start);
3238 }
3239
3240 /* Process any networks that have been configured. */
3241 bgp_static_add(bgp);
3242 }
3243
3244 /*
3245 * Make BGP instance "down". Applies only to VRFs (non-default) and
3246 * implies the VRF has been deleted by Zebra.
3247 */
3248 void bgp_instance_down(struct bgp *bgp)
3249 {
3250 struct peer *peer;
3251 struct listnode *node;
3252 struct listnode *next;
3253
3254 /* Stop timers. */
3255 if (bgp->t_rmap_def_originate_eval) {
3256 BGP_TIMER_OFF(bgp->t_rmap_def_originate_eval);
3257 bgp_unlock(bgp); /* TODO - This timer is started with a lock -
3258 why? */
3259 }
3260
3261 /* Bring down peers, so corresponding routes are purged. */
3262 for (ALL_LIST_ELEMENTS(bgp->peer, node, next, peer)) {
3263 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3264 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
3265 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN);
3266 else
3267 bgp_session_reset(peer);
3268 }
3269
3270 /* Purge network and redistributed routes. */
3271 bgp_purge_static_redist_routes(bgp);
3272
3273 /* Cleanup registered nexthops (flags) */
3274 bgp_cleanup_nexthops(bgp);
3275 }
3276
3277 /* Delete BGP instance. */
3278 int bgp_delete(struct bgp *bgp)
3279 {
3280 struct peer *peer;
3281 struct peer_group *group;
3282 struct listnode *node, *next;
3283 struct vrf *vrf;
3284 afi_t afi;
3285 safi_t safi;
3286 int i;
3287 struct graceful_restart_info *gr_info;
3288
3289 assert(bgp);
3290
3291 hook_call(bgp_inst_delete, bgp);
3292
3293 THREAD_OFF(bgp->t_startup);
3294 THREAD_OFF(bgp->t_maxmed_onstartup);
3295 THREAD_OFF(bgp->t_update_delay);
3296 THREAD_OFF(bgp->t_establish_wait);
3297
3298 /* Set flag indicating bgp instance delete in progress */
3299 SET_FLAG(bgp->flags, BGP_FLAG_DELETE_IN_PROGRESS);
3300
3301 /* Delete the graceful restart info */
3302 FOREACH_AFI_SAFI (afi, safi) {
3303 gr_info = &bgp->gr_info[afi][safi];
3304 if (!gr_info)
3305 continue;
3306
3307 BGP_TIMER_OFF(gr_info->t_select_deferral);
3308 BGP_TIMER_OFF(gr_info->t_route_select);
3309 if (gr_info->route_list)
3310 list_delete(&gr_info->route_list);
3311 }
3312
3313 if (BGP_DEBUG(zebra, ZEBRA)) {
3314 if (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
3315 zlog_debug("Deleting Default VRF");
3316 else
3317 zlog_debug("Deleting %s %s",
3318 (bgp->inst_type == BGP_INSTANCE_TYPE_VRF)
3319 ? "VRF"
3320 : "VIEW",
3321 bgp->name);
3322 }
3323
3324 /* unmap from RT list */
3325 bgp_evpn_vrf_delete(bgp);
3326
3327 /* unmap bgp vrf label */
3328 vpn_leak_zebra_vrf_label_withdraw(bgp, AFI_IP);
3329 vpn_leak_zebra_vrf_label_withdraw(bgp, AFI_IP6);
3330
3331 /* Stop timers. */
3332 if (bgp->t_rmap_def_originate_eval) {
3333 BGP_TIMER_OFF(bgp->t_rmap_def_originate_eval);
3334 bgp_unlock(bgp); /* TODO - This timer is started with a lock -
3335 why? */
3336 }
3337
3338 /* Inform peers we're going down. */
3339 for (ALL_LIST_ELEMENTS(bgp->peer, node, next, peer)) {
3340 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3341 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
3342 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN);
3343 }
3344
3345 /* Delete static routes (networks). */
3346 bgp_static_delete(bgp);
3347
3348 /* Unset redistribution. */
3349 for (afi = AFI_IP; afi < AFI_MAX; afi++)
3350 for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
3351 if (i != ZEBRA_ROUTE_BGP)
3352 bgp_redistribute_unset(bgp, afi, i, 0);
3353
3354 /* Free peers and peer-groups. */
3355 for (ALL_LIST_ELEMENTS(bgp->group, node, next, group))
3356 peer_group_delete(group);
3357
3358 for (ALL_LIST_ELEMENTS(bgp->peer, node, next, peer))
3359 peer_delete(peer);
3360
3361 if (bgp->peer_self) {
3362 peer_delete(bgp->peer_self);
3363 bgp->peer_self = NULL;
3364 }
3365
3366 update_bgp_group_free(bgp);
3367
3368 /* TODO - Other memory may need to be freed - e.g., NHT */
3369
3370 #if ENABLE_BGP_VNC
3371 rfapi_delete(bgp);
3372 #endif
3373 bgp_cleanup_routes(bgp);
3374
3375 for (afi = 0; afi < AFI_MAX; ++afi) {
3376 if (!bgp->vpn_policy[afi].import_redirect_rtlist)
3377 continue;
3378 ecommunity_free(
3379 &bgp->vpn_policy[afi]
3380 .import_redirect_rtlist);
3381 bgp->vpn_policy[afi].import_redirect_rtlist = NULL;
3382 }
3383
3384 /* Deregister from Zebra, if needed */
3385 if (IS_BGP_INST_KNOWN_TO_ZEBRA(bgp)) {
3386 if (BGP_DEBUG(zebra, ZEBRA))
3387 zlog_debug("%s: deregistering this bgp %s instance from zebra",
3388 __PRETTY_FUNCTION__, bgp->name);
3389 bgp_zebra_instance_deregister(bgp);
3390 }
3391
3392 /* Remove visibility via the master list - there may however still be
3393 * routes to be processed still referencing the struct bgp.
3394 */
3395 listnode_delete(bm->bgp, bgp);
3396
3397 /* Free interfaces in this instance. */
3398 bgp_if_finish(bgp);
3399
3400 vrf = bgp_vrf_lookup_by_instance_type(bgp);
3401 bgp_handle_socket(bgp, vrf, VRF_UNKNOWN, false);
3402 if (vrf)
3403 bgp_vrf_unlink(bgp, vrf);
3404
3405 /* Update EVPN VRF pointer */
3406 if (bm->bgp_evpn == bgp) {
3407 if (bgp->inst_type == BGP_INSTANCE_TYPE_DEFAULT)
3408 bgp_set_evpn(NULL);
3409 else
3410 bgp_set_evpn(bgp_get_default());
3411 }
3412
3413 thread_master_free_unused(bm->master);
3414 bgp_unlock(bgp); /* initial reference */
3415
3416 return 0;
3417 }
3418
3419 void bgp_free(struct bgp *bgp)
3420 {
3421 afi_t afi;
3422 safi_t safi;
3423 struct bgp_table *table;
3424 struct bgp_node *rn;
3425 struct bgp_rmap *rmap;
3426
3427 QOBJ_UNREG(bgp);
3428
3429 list_delete(&bgp->group);
3430 list_delete(&bgp->peer);
3431
3432 if (bgp->peerhash) {
3433 hash_free(bgp->peerhash);
3434 bgp->peerhash = NULL;
3435 }
3436
3437 FOREACH_AFI_SAFI (afi, safi) {
3438 /* Special handling for 2-level routing tables. */
3439 if (safi == SAFI_MPLS_VPN || safi == SAFI_ENCAP
3440 || safi == SAFI_EVPN) {
3441 for (rn = bgp_table_top(bgp->rib[afi][safi]); rn;
3442 rn = bgp_route_next(rn)) {
3443 table = bgp_node_get_bgp_table_info(rn);
3444 bgp_table_finish(&table);
3445 }
3446 }
3447 if (bgp->route[afi][safi])
3448 bgp_table_finish(&bgp->route[afi][safi]);
3449 if (bgp->aggregate[afi][safi])
3450 bgp_table_finish(&bgp->aggregate[afi][safi]);
3451 if (bgp->rib[afi][safi])
3452 bgp_table_finish(&bgp->rib[afi][safi]);
3453 rmap = &bgp->table_map[afi][safi];
3454 XFREE(MTYPE_ROUTE_MAP_NAME, rmap->name);
3455 }
3456
3457 bgp_scan_finish(bgp);
3458 bgp_address_destroy(bgp);
3459 bgp_tip_hash_destroy(bgp);
3460
3461 /* release the auto RD id */
3462 bf_release_index(bm->rd_idspace, bgp->vrf_rd_id);
3463
3464 bgp_evpn_cleanup(bgp);
3465 bgp_pbr_cleanup(bgp);
3466 XFREE(MTYPE_BGP_EVPN_INFO, bgp->evpn_info);
3467
3468 for (afi = AFI_IP; afi < AFI_MAX; afi++) {
3469 vpn_policy_direction_t dir;
3470
3471 if (bgp->vpn_policy[afi].import_vrf)
3472 list_delete(&bgp->vpn_policy[afi].import_vrf);
3473 if (bgp->vpn_policy[afi].export_vrf)
3474 list_delete(&bgp->vpn_policy[afi].export_vrf);
3475
3476 dir = BGP_VPN_POLICY_DIR_FROMVPN;
3477 if (bgp->vpn_policy[afi].rtlist[dir])
3478 ecommunity_free(&bgp->vpn_policy[afi].rtlist[dir]);
3479 dir = BGP_VPN_POLICY_DIR_TOVPN;
3480 if (bgp->vpn_policy[afi].rtlist[dir])
3481 ecommunity_free(&bgp->vpn_policy[afi].rtlist[dir]);
3482 }
3483
3484 XFREE(MTYPE_BGP, bgp->name);
3485 XFREE(MTYPE_BGP, bgp->name_pretty);
3486
3487 XFREE(MTYPE_BGP, bgp);
3488 }
3489
3490 struct peer *peer_lookup_by_conf_if(struct bgp *bgp, const char *conf_if)
3491 {
3492 struct peer *peer;
3493 struct listnode *node, *nnode;
3494
3495 if (!conf_if)
3496 return NULL;
3497
3498 if (bgp != NULL) {
3499 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer))
3500 if (peer->conf_if && !strcmp(peer->conf_if, conf_if)
3501 && !CHECK_FLAG(peer->sflags,
3502 PEER_STATUS_ACCEPT_PEER))
3503 return peer;
3504 } else if (bm->bgp != NULL) {
3505 struct listnode *bgpnode, *nbgpnode;
3506
3507 for (ALL_LIST_ELEMENTS(bm->bgp, bgpnode, nbgpnode, bgp))
3508 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer))
3509 if (peer->conf_if
3510 && !strcmp(peer->conf_if, conf_if)
3511 && !CHECK_FLAG(peer->sflags,
3512 PEER_STATUS_ACCEPT_PEER))
3513 return peer;
3514 }
3515 return NULL;
3516 }
3517
3518 struct peer *peer_lookup_by_hostname(struct bgp *bgp, const char *hostname)
3519 {
3520 struct peer *peer;
3521 struct listnode *node, *nnode;
3522
3523 if (!hostname)
3524 return NULL;
3525
3526 if (bgp != NULL) {
3527 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer))
3528 if (peer->hostname && !strcmp(peer->hostname, hostname)
3529 && !CHECK_FLAG(peer->sflags,
3530 PEER_STATUS_ACCEPT_PEER))
3531 return peer;
3532 } else if (bm->bgp != NULL) {
3533 struct listnode *bgpnode, *nbgpnode;
3534
3535 for (ALL_LIST_ELEMENTS(bm->bgp, bgpnode, nbgpnode, bgp))
3536 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer))
3537 if (peer->hostname
3538 && !strcmp(peer->hostname, hostname)
3539 && !CHECK_FLAG(peer->sflags,
3540 PEER_STATUS_ACCEPT_PEER))
3541 return peer;
3542 }
3543 return NULL;
3544 }
3545
3546 struct peer *peer_lookup(struct bgp *bgp, union sockunion *su)
3547 {
3548 struct peer *peer = NULL;
3549 struct peer tmp_peer;
3550
3551 memset(&tmp_peer, 0, sizeof(struct peer));
3552
3553 /*
3554 * We do not want to find the doppelganger peer so search for the peer
3555 * in
3556 * the hash that has PEER_FLAG_CONFIG_NODE
3557 */
3558 SET_FLAG(tmp_peer.flags, PEER_FLAG_CONFIG_NODE);
3559
3560 tmp_peer.su = *su;
3561
3562 if (bgp != NULL) {
3563 peer = hash_lookup(bgp->peerhash, &tmp_peer);
3564 } else if (bm->bgp != NULL) {
3565 struct listnode *bgpnode, *nbgpnode;
3566
3567 for (ALL_LIST_ELEMENTS(bm->bgp, bgpnode, nbgpnode, bgp)) {
3568 peer = hash_lookup(bgp->peerhash, &tmp_peer);
3569 if (peer)
3570 break;
3571 }
3572 }
3573
3574 return peer;
3575 }
3576
3577 struct peer *peer_create_bind_dynamic_neighbor(struct bgp *bgp,
3578 union sockunion *su,
3579 struct peer_group *group)
3580 {
3581 struct peer *peer;
3582 afi_t afi;
3583 safi_t safi;
3584
3585 /* Create peer first; we've already checked group config is valid. */
3586 peer = peer_create(su, NULL, bgp, bgp->as, group->conf->as,
3587 group->conf->as_type, 0, 0, group);
3588 if (!peer)
3589 return NULL;
3590
3591 /* Link to group */
3592 peer = peer_lock(peer);
3593 listnode_add(group->peer, peer);
3594
3595 peer_group2peer_config_copy(group, peer);
3596
3597 /*
3598 * Bind peer for all AFs configured for the group. We don't call
3599 * peer_group_bind as that is sub-optimal and does some stuff we don't
3600 * want.
3601 */
3602 FOREACH_AFI_SAFI (afi, safi) {
3603 if (!group->conf->afc[afi][safi])
3604 continue;
3605 peer->afc[afi][safi] = 1;
3606
3607 if (!peer_af_find(peer, afi, safi))
3608 peer_af_create(peer, afi, safi);
3609
3610 peer_group2peer_config_copy_af(group, peer, afi, safi);
3611 }
3612
3613 /* Mark as dynamic, but also as a "config node" for other things to
3614 * work. */
3615 SET_FLAG(peer->flags, PEER_FLAG_DYNAMIC_NEIGHBOR);
3616 SET_FLAG(peer->flags, PEER_FLAG_CONFIG_NODE);
3617
3618 return peer;
3619 }
3620
3621 struct prefix *
3622 peer_group_lookup_dynamic_neighbor_range(struct peer_group *group,
3623 struct prefix *prefix)
3624 {
3625 struct listnode *node, *nnode;
3626 struct prefix *range;
3627 afi_t afi;
3628
3629 afi = family2afi(prefix->family);
3630
3631 if (group->listen_range[afi])
3632 for (ALL_LIST_ELEMENTS(group->listen_range[afi], node, nnode,
3633 range))
3634 if (prefix_match(range, prefix))
3635 return range;
3636
3637 return NULL;
3638 }
3639
3640 struct peer_group *
3641 peer_group_lookup_dynamic_neighbor(struct bgp *bgp, struct prefix *prefix,
3642 struct prefix **listen_range)
3643 {
3644 struct prefix *range = NULL;
3645 struct peer_group *group = NULL;
3646 struct listnode *node, *nnode;
3647
3648 *listen_range = NULL;
3649 if (bgp != NULL) {
3650 for (ALL_LIST_ELEMENTS(bgp->group, node, nnode, group))
3651 if ((range = peer_group_lookup_dynamic_neighbor_range(
3652 group, prefix)))
3653 break;
3654 } else if (bm->bgp != NULL) {
3655 struct listnode *bgpnode, *nbgpnode;
3656
3657 for (ALL_LIST_ELEMENTS(bm->bgp, bgpnode, nbgpnode, bgp))
3658 for (ALL_LIST_ELEMENTS(bgp->group, node, nnode, group))
3659 if ((range = peer_group_lookup_dynamic_neighbor_range(
3660 group, prefix)))
3661 goto found_range;
3662 }
3663
3664 found_range:
3665 *listen_range = range;
3666 return (group && range) ? group : NULL;
3667 }
3668
3669 struct peer *peer_lookup_dynamic_neighbor(struct bgp *bgp, union sockunion *su)
3670 {
3671 struct peer_group *group;
3672 struct bgp *gbgp;
3673 struct peer *peer;
3674 struct prefix prefix;
3675 struct prefix *listen_range;
3676 int dncount;
3677 char buf[PREFIX2STR_BUFFER];
3678 char buf1[PREFIX2STR_BUFFER];
3679
3680 sockunion2hostprefix(su, &prefix);
3681
3682 /* See if incoming connection matches a configured listen range. */
3683 group = peer_group_lookup_dynamic_neighbor(bgp, &prefix, &listen_range);
3684
3685 if (!group)
3686 return NULL;
3687
3688
3689 gbgp = group->bgp;
3690
3691 if (!gbgp)
3692 return NULL;
3693
3694 prefix2str(&prefix, buf, sizeof(buf));
3695 prefix2str(listen_range, buf1, sizeof(buf1));
3696
3697 if (bgp_debug_neighbor_events(NULL))
3698 zlog_debug(
3699 "Dynamic Neighbor %s matches group %s listen range %s",
3700 buf, group->name, buf1);
3701
3702 /* Are we within the listen limit? */
3703 dncount = gbgp->dynamic_neighbors_count;
3704
3705 if (dncount >= gbgp->dynamic_neighbors_limit) {
3706 if (bgp_debug_neighbor_events(NULL))
3707 zlog_debug("Dynamic Neighbor %s rejected - at limit %d",
3708 inet_sutop(su, buf),
3709 gbgp->dynamic_neighbors_limit);
3710 return NULL;
3711 }
3712
3713 /* Ensure group is not disabled. */
3714 if (CHECK_FLAG(group->conf->flags, PEER_FLAG_SHUTDOWN)) {
3715 if (bgp_debug_neighbor_events(NULL))
3716 zlog_debug(
3717 "Dynamic Neighbor %s rejected - group %s disabled",
3718 buf, group->name);
3719 return NULL;
3720 }
3721
3722 /* Check that at least one AF is activated for the group. */
3723 if (!peer_group_af_configured(group)) {
3724 if (bgp_debug_neighbor_events(NULL))
3725 zlog_debug(
3726 "Dynamic Neighbor %s rejected - no AF activated for group %s",
3727 buf, group->name);
3728 return NULL;
3729 }
3730
3731 /* Create dynamic peer and bind to associated group. */
3732 peer = peer_create_bind_dynamic_neighbor(gbgp, su, group);
3733 assert(peer);
3734
3735 gbgp->dynamic_neighbors_count = ++dncount;
3736
3737 if (bgp_debug_neighbor_events(peer))
3738 zlog_debug("%s Dynamic Neighbor added, group %s count %d",
3739 peer->host, group->name, dncount);
3740
3741 return peer;
3742 }
3743
3744 static void peer_drop_dynamic_neighbor(struct peer *peer)
3745 {
3746 int dncount = -1;
3747 if (peer->group->bgp) {
3748 dncount = peer->group->bgp->dynamic_neighbors_count;
3749 if (dncount)
3750 peer->group->bgp->dynamic_neighbors_count = --dncount;
3751 }
3752 if (bgp_debug_neighbor_events(peer))
3753 zlog_debug("%s dropped from group %s, count %d", peer->host,
3754 peer->group->name, dncount);
3755 }
3756
3757 /* If peer is configured at least one address family return 1. */
3758 int peer_active(struct peer *peer)
3759 {
3760 if (BGP_PEER_SU_UNSPEC(peer))
3761 return 0;
3762 if (peer->afc[AFI_IP][SAFI_UNICAST] || peer->afc[AFI_IP][SAFI_MULTICAST]
3763 || peer->afc[AFI_IP][SAFI_LABELED_UNICAST]
3764 || peer->afc[AFI_IP][SAFI_MPLS_VPN] || peer->afc[AFI_IP][SAFI_ENCAP]
3765 || peer->afc[AFI_IP][SAFI_FLOWSPEC]
3766 || peer->afc[AFI_IP6][SAFI_UNICAST]
3767 || peer->afc[AFI_IP6][SAFI_MULTICAST]
3768 || peer->afc[AFI_IP6][SAFI_LABELED_UNICAST]
3769 || peer->afc[AFI_IP6][SAFI_MPLS_VPN]
3770 || peer->afc[AFI_IP6][SAFI_ENCAP]
3771 || peer->afc[AFI_IP6][SAFI_FLOWSPEC]
3772 || peer->afc[AFI_L2VPN][SAFI_EVPN])
3773 return 1;
3774 return 0;
3775 }
3776
3777 /* If peer is negotiated at least one address family return 1. */
3778 int peer_active_nego(struct peer *peer)
3779 {
3780 if (peer->afc_nego[AFI_IP][SAFI_UNICAST]
3781 || peer->afc_nego[AFI_IP][SAFI_MULTICAST]
3782 || peer->afc_nego[AFI_IP][SAFI_LABELED_UNICAST]
3783 || peer->afc_nego[AFI_IP][SAFI_MPLS_VPN]
3784 || peer->afc_nego[AFI_IP][SAFI_ENCAP]
3785 || peer->afc_nego[AFI_IP][SAFI_FLOWSPEC]
3786 || peer->afc_nego[AFI_IP6][SAFI_UNICAST]
3787 || peer->afc_nego[AFI_IP6][SAFI_MULTICAST]
3788 || peer->afc_nego[AFI_IP6][SAFI_LABELED_UNICAST]
3789 || peer->afc_nego[AFI_IP6][SAFI_MPLS_VPN]
3790 || peer->afc_nego[AFI_IP6][SAFI_ENCAP]
3791 || peer->afc_nego[AFI_IP6][SAFI_FLOWSPEC]
3792 || peer->afc_nego[AFI_L2VPN][SAFI_EVPN])
3793 return 1;
3794 return 0;
3795 }
3796
3797 void peer_change_action(struct peer *peer, afi_t afi, safi_t safi,
3798 enum peer_change_type type)
3799 {
3800 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
3801 return;
3802
3803 if (peer->status != Established)
3804 return;
3805
3806 if (type == peer_change_reset) {
3807 /* If we're resetting session, we've to delete both peer struct
3808 */
3809 if ((peer->doppelganger)
3810 && (peer->doppelganger->status != Deleted)
3811 && (!CHECK_FLAG(peer->doppelganger->flags,
3812 PEER_FLAG_CONFIG_NODE)))
3813 peer_delete(peer->doppelganger);
3814
3815 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
3816 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3817 } else if (type == peer_change_reset_in) {
3818 if (CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_OLD_RCV)
3819 || CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_NEW_RCV))
3820 bgp_route_refresh_send(peer, afi, safi, 0, 0, 0);
3821 else {
3822 if ((peer->doppelganger)
3823 && (peer->doppelganger->status != Deleted)
3824 && (!CHECK_FLAG(peer->doppelganger->flags,
3825 PEER_FLAG_CONFIG_NODE)))
3826 peer_delete(peer->doppelganger);
3827
3828 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
3829 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3830 }
3831 } else if (type == peer_change_reset_out) {
3832 update_group_adjust_peer(peer_af_find(peer, afi, safi));
3833 bgp_announce_route(peer, afi, safi);
3834 }
3835 }
3836
3837 struct peer_flag_action {
3838 /* Peer's flag. */
3839 uint32_t flag;
3840
3841 /* This flag can be set for peer-group member. */
3842 uint8_t not_for_member;
3843
3844 /* Action when the flag is changed. */
3845 enum peer_change_type type;
3846 };
3847
3848 static const struct peer_flag_action peer_flag_action_list[] = {
3849 {PEER_FLAG_PASSIVE, 0, peer_change_reset},
3850 {PEER_FLAG_SHUTDOWN, 0, peer_change_reset},
3851 {PEER_FLAG_DONT_CAPABILITY, 0, peer_change_none},
3852 {PEER_FLAG_OVERRIDE_CAPABILITY, 0, peer_change_none},
3853 {PEER_FLAG_STRICT_CAP_MATCH, 0, peer_change_none},
3854 {PEER_FLAG_DYNAMIC_CAPABILITY, 0, peer_change_reset},
3855 {PEER_FLAG_DISABLE_CONNECTED_CHECK, 0, peer_change_reset},
3856 {PEER_FLAG_CAPABILITY_ENHE, 0, peer_change_reset},
3857 {PEER_FLAG_ENFORCE_FIRST_AS, 0, peer_change_reset_in},
3858 {PEER_FLAG_IFPEER_V6ONLY, 0, peer_change_reset},
3859 {PEER_FLAG_ROUTEADV, 0, peer_change_none},
3860 {PEER_FLAG_TIMER, 0, peer_change_none},
3861 {PEER_FLAG_TIMER_CONNECT, 0, peer_change_none},
3862 {PEER_FLAG_PASSWORD, 0, peer_change_none},
3863 {PEER_FLAG_LOCAL_AS, 0, peer_change_none},
3864 {PEER_FLAG_LOCAL_AS_NO_PREPEND, 0, peer_change_none},
3865 {PEER_FLAG_LOCAL_AS_REPLACE_AS, 0, peer_change_none},
3866 {PEER_FLAG_UPDATE_SOURCE, 0, peer_change_none},
3867 {0, 0, 0}};
3868
3869 static const struct peer_flag_action peer_af_flag_action_list[] = {
3870 {PEER_FLAG_SEND_COMMUNITY, 1, peer_change_reset_out},
3871 {PEER_FLAG_SEND_EXT_COMMUNITY, 1, peer_change_reset_out},
3872 {PEER_FLAG_SEND_LARGE_COMMUNITY, 1, peer_change_reset_out},
3873 {PEER_FLAG_NEXTHOP_SELF, 1, peer_change_reset_out},
3874 {PEER_FLAG_REFLECTOR_CLIENT, 1, peer_change_reset},
3875 {PEER_FLAG_RSERVER_CLIENT, 1, peer_change_reset},
3876 {PEER_FLAG_SOFT_RECONFIG, 0, peer_change_reset_in},
3877 {PEER_FLAG_AS_PATH_UNCHANGED, 1, peer_change_reset_out},
3878 {PEER_FLAG_NEXTHOP_UNCHANGED, 1, peer_change_reset_out},
3879 {PEER_FLAG_MED_UNCHANGED, 1, peer_change_reset_out},
3880 {PEER_FLAG_DEFAULT_ORIGINATE, 0, peer_change_none},
3881 {PEER_FLAG_REMOVE_PRIVATE_AS, 1, peer_change_reset_out},
3882 {PEER_FLAG_ALLOWAS_IN, 0, peer_change_reset_in},
3883 {PEER_FLAG_ALLOWAS_IN_ORIGIN, 0, peer_change_reset_in},
3884 {PEER_FLAG_ORF_PREFIX_SM, 1, peer_change_reset},
3885 {PEER_FLAG_ORF_PREFIX_RM, 1, peer_change_reset},
3886 {PEER_FLAG_MAX_PREFIX, 0, peer_change_none},
3887 {PEER_FLAG_MAX_PREFIX_WARNING, 0, peer_change_none},
3888 {PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED, 0, peer_change_reset_out},
3889 {PEER_FLAG_FORCE_NEXTHOP_SELF, 1, peer_change_reset_out},
3890 {PEER_FLAG_REMOVE_PRIVATE_AS_ALL, 1, peer_change_reset_out},
3891 {PEER_FLAG_REMOVE_PRIVATE_AS_REPLACE, 1, peer_change_reset_out},
3892 {PEER_FLAG_AS_OVERRIDE, 1, peer_change_reset_out},
3893 {PEER_FLAG_REMOVE_PRIVATE_AS_ALL_REPLACE, 1, peer_change_reset_out},
3894 {PEER_FLAG_WEIGHT, 0, peer_change_reset_in},
3895 {0, 0, 0}};
3896
3897 /* Proper action set. */
3898 static int peer_flag_action_set(const struct peer_flag_action *action_list,
3899 int size, struct peer_flag_action *action,
3900 uint32_t flag)
3901 {
3902 int i;
3903 int found = 0;
3904 int reset_in = 0;
3905 int reset_out = 0;
3906 const struct peer_flag_action *match = NULL;
3907
3908 /* Check peer's frag action. */
3909 for (i = 0; i < size; i++) {
3910 match = &action_list[i];
3911
3912 if (match->flag == 0)
3913 break;
3914
3915 if (match->flag & flag) {
3916 found = 1;
3917
3918 if (match->type == peer_change_reset_in)
3919 reset_in = 1;
3920 if (match->type == peer_change_reset_out)
3921 reset_out = 1;
3922 if (match->type == peer_change_reset) {
3923 reset_in = 1;
3924 reset_out = 1;
3925 }
3926 if (match->not_for_member)
3927 action->not_for_member = 1;
3928 }
3929 }
3930
3931 /* Set peer clear type. */
3932 if (reset_in && reset_out)
3933 action->type = peer_change_reset;
3934 else if (reset_in)
3935 action->type = peer_change_reset_in;
3936 else if (reset_out)
3937 action->type = peer_change_reset_out;
3938 else
3939 action->type = peer_change_none;
3940
3941 return found;
3942 }
3943
3944 static void peer_flag_modify_action(struct peer *peer, uint32_t flag)
3945 {
3946 if (flag == PEER_FLAG_SHUTDOWN) {
3947 if (CHECK_FLAG(peer->flags, flag)) {
3948 if (CHECK_FLAG(peer->sflags, PEER_STATUS_NSF_WAIT))
3949 peer_nsf_stop(peer);
3950
3951 UNSET_FLAG(peer->sflags, PEER_STATUS_PREFIX_OVERFLOW);
3952 if (peer->t_pmax_restart) {
3953 BGP_TIMER_OFF(peer->t_pmax_restart);
3954 if (bgp_debug_neighbor_events(peer))
3955 zlog_debug(
3956 "%s Maximum-prefix restart timer canceled",
3957 peer->host);
3958 }
3959
3960 if (CHECK_FLAG(peer->sflags, PEER_STATUS_NSF_WAIT))
3961 peer_nsf_stop(peer);
3962
3963 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
3964 char *msg = peer->tx_shutdown_message;
3965 size_t msglen;
3966
3967 if (!msg && peer_group_active(peer))
3968 msg = peer->group->conf
3969 ->tx_shutdown_message;
3970 msglen = msg ? strlen(msg) : 0;
3971 if (msglen > 128)
3972 msglen = 128;
3973
3974 if (msglen) {
3975 uint8_t msgbuf[129];
3976
3977 msgbuf[0] = msglen;
3978 memcpy(msgbuf + 1, msg, msglen);
3979
3980 bgp_notify_send_with_data(
3981 peer, BGP_NOTIFY_CEASE,
3982 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN,
3983 msgbuf, msglen + 1);
3984 } else
3985 bgp_notify_send(
3986 peer, BGP_NOTIFY_CEASE,
3987 BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN);
3988 } else
3989 bgp_session_reset(peer);
3990 } else {
3991 peer->v_start = BGP_INIT_START_TIMER;
3992 BGP_EVENT_ADD(peer, BGP_Stop);
3993 }
3994 } else if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
3995 if (flag == PEER_FLAG_DYNAMIC_CAPABILITY)
3996 peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
3997 else if (flag == PEER_FLAG_PASSIVE)
3998 peer->last_reset = PEER_DOWN_PASSIVE_CHANGE;
3999 else if (flag == PEER_FLAG_DISABLE_CONNECTED_CHECK)
4000 peer->last_reset = PEER_DOWN_MULTIHOP_CHANGE;
4001
4002 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
4003 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4004 } else
4005 bgp_session_reset(peer);
4006 }
4007
4008 /* Change specified peer flag. */
4009 static int peer_flag_modify(struct peer *peer, uint32_t flag, int set)
4010 {
4011 int found;
4012 int size;
4013 bool invert, member_invert;
4014 struct peer *member;
4015 struct listnode *node, *nnode;
4016 struct peer_flag_action action;
4017
4018 memset(&action, 0, sizeof(struct peer_flag_action));
4019 size = sizeof peer_flag_action_list / sizeof(struct peer_flag_action);
4020
4021 invert = CHECK_FLAG(peer->flags_invert, flag);
4022 found = peer_flag_action_set(peer_flag_action_list, size, &action,
4023 flag);
4024
4025 /* Abort if no flag action exists. */
4026 if (!found)
4027 return BGP_ERR_INVALID_FLAG;
4028
4029 /* Check for flag conflict: STRICT_CAP_MATCH && OVERRIDE_CAPABILITY */
4030 if (set && CHECK_FLAG(peer->flags | flag, PEER_FLAG_STRICT_CAP_MATCH)
4031 && CHECK_FLAG(peer->flags | flag, PEER_FLAG_OVERRIDE_CAPABILITY))
4032 return BGP_ERR_PEER_FLAG_CONFLICT;
4033
4034 /* Handle flag updates where desired state matches current state. */
4035 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4036 if (set && CHECK_FLAG(peer->flags, flag)) {
4037 COND_FLAG(peer->flags_override, flag, !invert);
4038 return 0;
4039 }
4040
4041 if (!set && !CHECK_FLAG(peer->flags, flag)) {
4042 COND_FLAG(peer->flags_override, flag, invert);
4043 return 0;
4044 }
4045 }
4046
4047 /* Inherit from peer-group or set/unset flags accordingly. */
4048 if (peer_group_active(peer) && set == invert)
4049 peer_flag_inherit(peer, flag);
4050 else
4051 COND_FLAG(peer->flags, flag, set);
4052
4053 /* Check if handling a regular peer. */
4054 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4055 /* Update flag override state accordingly. */
4056 COND_FLAG(peer->flags_override, flag, set != invert);
4057
4058 /* Execute flag action on peer. */
4059 if (action.type == peer_change_reset)
4060 peer_flag_modify_action(peer, flag);
4061
4062 /* Skip peer-group mechanics for regular peers. */
4063 return 0;
4064 }
4065
4066 if (set && flag == PEER_FLAG_CAPABILITY_ENHE)
4067 bgp_nht_register_enhe_capability_interfaces(peer);
4068
4069 /*
4070 * Update peer-group members, unless they are explicitely overriding
4071 * peer-group configuration.
4072 */
4073 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4074 /* Skip peers with overridden configuration. */
4075 if (CHECK_FLAG(member->flags_override, flag))
4076 continue;
4077
4078 /* Check if only member without group is inverted. */
4079 member_invert =
4080 CHECK_FLAG(member->flags_invert, flag) && !invert;
4081
4082 /* Skip peers with equivalent configuration. */
4083 if (set != member_invert && CHECK_FLAG(member->flags, flag))
4084 continue;
4085
4086 if (set == member_invert && !CHECK_FLAG(member->flags, flag))
4087 continue;
4088
4089 /* Update flag on peer-group member. */
4090 COND_FLAG(member->flags, flag, set != member_invert);
4091
4092 if (set && flag == PEER_FLAG_CAPABILITY_ENHE)
4093 bgp_nht_register_enhe_capability_interfaces(member);
4094
4095 /* Execute flag action on peer-group member. */
4096 if (action.type == peer_change_reset)
4097 peer_flag_modify_action(member, flag);
4098 }
4099
4100 return 0;
4101 }
4102
4103 int peer_flag_set(struct peer *peer, uint32_t flag)
4104 {
4105 return peer_flag_modify(peer, flag, 1);
4106 }
4107
4108 int peer_flag_unset(struct peer *peer, uint32_t flag)
4109 {
4110 return peer_flag_modify(peer, flag, 0);
4111 }
4112
4113 static int peer_af_flag_modify(struct peer *peer, afi_t afi, safi_t safi,
4114 uint32_t flag, bool set)
4115 {
4116 int found;
4117 int size;
4118 bool invert, member_invert;
4119 struct peer *member;
4120 struct listnode *node, *nnode;
4121 struct peer_flag_action action;
4122
4123 memset(&action, 0, sizeof(struct peer_flag_action));
4124 size = sizeof peer_af_flag_action_list
4125 / sizeof(struct peer_flag_action);
4126
4127 invert = CHECK_FLAG(peer->af_flags_invert[afi][safi], flag);
4128 found = peer_flag_action_set(peer_af_flag_action_list, size, &action,
4129 flag);
4130
4131 /* Abort if flag action exists. */
4132 if (!found)
4133 return BGP_ERR_INVALID_FLAG;
4134
4135 /* Special check for reflector client. */
4136 if (flag & PEER_FLAG_REFLECTOR_CLIENT
4137 && peer_sort(peer) != BGP_PEER_IBGP)
4138 return BGP_ERR_NOT_INTERNAL_PEER;
4139
4140 /* Special check for remove-private-AS. */
4141 if (flag & PEER_FLAG_REMOVE_PRIVATE_AS
4142 && peer_sort(peer) == BGP_PEER_IBGP)
4143 return BGP_ERR_REMOVE_PRIVATE_AS;
4144
4145 /* as-override is not allowed for IBGP peers */
4146 if (flag & PEER_FLAG_AS_OVERRIDE && peer_sort(peer) == BGP_PEER_IBGP)
4147 return BGP_ERR_AS_OVERRIDE;
4148
4149 /* Handle flag updates where desired state matches current state. */
4150 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4151 if (set && CHECK_FLAG(peer->af_flags[afi][safi], flag)) {
4152 COND_FLAG(peer->af_flags_override[afi][safi], flag,
4153 !invert);
4154 return 0;
4155 }
4156
4157 if (!set && !CHECK_FLAG(peer->af_flags[afi][safi], flag)) {
4158 COND_FLAG(peer->af_flags_override[afi][safi], flag,
4159 invert);
4160 return 0;
4161 }
4162 }
4163
4164 /*
4165 * For EVPN we implicitly set the NEXTHOP_UNCHANGED flag,
4166 * if we are setting/unsetting flags which conflict with this flag
4167 * handle accordingly
4168 */
4169 if (afi == AFI_L2VPN && safi == SAFI_EVPN) {
4170 if (set) {
4171
4172 /*
4173 * if we are setting NEXTHOP_SELF, we need to unset the
4174 * NEXTHOP_UNCHANGED flag
4175 */
4176 if (CHECK_FLAG(flag, PEER_FLAG_NEXTHOP_SELF) ||
4177 CHECK_FLAG(flag, PEER_FLAG_FORCE_NEXTHOP_SELF))
4178 UNSET_FLAG(peer->af_flags[afi][safi],
4179 PEER_FLAG_NEXTHOP_UNCHANGED);
4180 } else {
4181
4182 /*
4183 * if we are unsetting NEXTHOP_SELF, we need to set the
4184 * NEXTHOP_UNCHANGED flag to reset the defaults for EVPN
4185 */
4186 if (CHECK_FLAG(flag, PEER_FLAG_NEXTHOP_SELF) ||
4187 CHECK_FLAG(flag, PEER_FLAG_FORCE_NEXTHOP_SELF))
4188 SET_FLAG(peer->af_flags[afi][safi],
4189 PEER_FLAG_NEXTHOP_UNCHANGED);
4190 }
4191 }
4192
4193 /* Inherit from peer-group or set/unset flags accordingly. */
4194 if (peer_group_active(peer) && set == invert)
4195 peer_af_flag_inherit(peer, afi, safi, flag);
4196 else
4197 COND_FLAG(peer->af_flags[afi][safi], flag, set);
4198
4199 /* Execute action when peer is established. */
4200 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)
4201 && peer->status == Established) {
4202 if (!set && flag == PEER_FLAG_SOFT_RECONFIG)
4203 bgp_clear_adj_in(peer, afi, safi);
4204 else {
4205 if (flag == PEER_FLAG_REFLECTOR_CLIENT)
4206 peer->last_reset = PEER_DOWN_RR_CLIENT_CHANGE;
4207 else if (flag == PEER_FLAG_RSERVER_CLIENT)
4208 peer->last_reset = PEER_DOWN_RS_CLIENT_CHANGE;
4209 else if (flag == PEER_FLAG_ORF_PREFIX_SM)
4210 peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
4211 else if (flag == PEER_FLAG_ORF_PREFIX_RM)
4212 peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
4213
4214 peer_change_action(peer, afi, safi, action.type);
4215 }
4216 }
4217
4218 /* Check if handling a regular peer. */
4219 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4220 COND_FLAG(peer->af_flags_override[afi][safi], flag,
4221 set != invert);
4222 } else {
4223 /*
4224 * Update peer-group members, unless they are explicitely
4225 * overriding peer-group configuration.
4226 */
4227 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode,
4228 member)) {
4229 /* Skip peers with overridden configuration. */
4230 if (CHECK_FLAG(member->af_flags_override[afi][safi],
4231 flag))
4232 continue;
4233
4234 /* Check if only member without group is inverted. */
4235 member_invert =
4236 CHECK_FLAG(member->af_flags_invert[afi][safi],
4237 flag)
4238 && !invert;
4239
4240 /* Skip peers with equivalent configuration. */
4241 if (set != member_invert
4242 && CHECK_FLAG(member->af_flags[afi][safi], flag))
4243 continue;
4244
4245 if (set == member_invert
4246 && !CHECK_FLAG(member->af_flags[afi][safi], flag))
4247 continue;
4248
4249 /* Update flag on peer-group member. */
4250 COND_FLAG(member->af_flags[afi][safi], flag,
4251 set != member_invert);
4252
4253 /* Execute flag action on peer-group member. */
4254 if (member->status == Established) {
4255 if (!set && flag == PEER_FLAG_SOFT_RECONFIG)
4256 bgp_clear_adj_in(member, afi, safi);
4257 else {
4258 if (flag == PEER_FLAG_REFLECTOR_CLIENT)
4259 member->last_reset =
4260 PEER_DOWN_RR_CLIENT_CHANGE;
4261 else if (flag
4262 == PEER_FLAG_RSERVER_CLIENT)
4263 member->last_reset =
4264 PEER_DOWN_RS_CLIENT_CHANGE;
4265 else if (flag
4266 == PEER_FLAG_ORF_PREFIX_SM)
4267 member->last_reset =
4268 PEER_DOWN_CAPABILITY_CHANGE;
4269 else if (flag
4270 == PEER_FLAG_ORF_PREFIX_RM)
4271 member->last_reset =
4272 PEER_DOWN_CAPABILITY_CHANGE;
4273
4274 peer_change_action(member, afi, safi,
4275 action.type);
4276 }
4277 }
4278 }
4279 }
4280
4281 return 0;
4282 }
4283
4284 int peer_af_flag_set(struct peer *peer, afi_t afi, safi_t safi, uint32_t flag)
4285 {
4286 return peer_af_flag_modify(peer, afi, safi, flag, 1);
4287 }
4288
4289 int peer_af_flag_unset(struct peer *peer, afi_t afi, safi_t safi, uint32_t flag)
4290 {
4291 return peer_af_flag_modify(peer, afi, safi, flag, 0);
4292 }
4293
4294
4295 int peer_tx_shutdown_message_set(struct peer *peer, const char *msg)
4296 {
4297 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG, peer->tx_shutdown_message);
4298 peer->tx_shutdown_message =
4299 msg ? XSTRDUP(MTYPE_PEER_TX_SHUTDOWN_MSG, msg) : NULL;
4300 return 0;
4301 }
4302
4303 int peer_tx_shutdown_message_unset(struct peer *peer)
4304 {
4305 XFREE(MTYPE_PEER_TX_SHUTDOWN_MSG, peer->tx_shutdown_message);
4306 return 0;
4307 }
4308
4309
4310 /* EBGP multihop configuration. */
4311 int peer_ebgp_multihop_set(struct peer *peer, int ttl)
4312 {
4313 struct peer_group *group;
4314 struct listnode *node, *nnode;
4315 struct peer *peer1;
4316
4317 if (peer->sort == BGP_PEER_IBGP || peer->conf_if)
4318 return 0;
4319
4320 /* see comment in peer_ttl_security_hops_set() */
4321 if (ttl != MAXTTL) {
4322 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4323 group = peer->group;
4324 if (group->conf->gtsm_hops != 0)
4325 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
4326
4327 for (ALL_LIST_ELEMENTS(group->peer, node, nnode,
4328 peer1)) {
4329 if (peer1->sort == BGP_PEER_IBGP)
4330 continue;
4331
4332 if (peer1->gtsm_hops != 0)
4333 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
4334 }
4335 } else {
4336 if (peer->gtsm_hops != 0)
4337 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
4338 }
4339 }
4340
4341 peer->ttl = ttl;
4342
4343 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4344 if (peer->fd >= 0 && peer->sort != BGP_PEER_IBGP) {
4345 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
4346 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
4347 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4348 else
4349 bgp_session_reset(peer);
4350 }
4351 } else {
4352 group = peer->group;
4353 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
4354 if (peer->sort == BGP_PEER_IBGP)
4355 continue;
4356
4357 peer->ttl = group->conf->ttl;
4358
4359 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
4360 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
4361 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4362 else
4363 bgp_session_reset(peer);
4364 }
4365 }
4366 return 0;
4367 }
4368
4369 int peer_ebgp_multihop_unset(struct peer *peer)
4370 {
4371 struct peer_group *group;
4372 struct listnode *node, *nnode;
4373
4374 if (peer->sort == BGP_PEER_IBGP)
4375 return 0;
4376
4377 if (peer->gtsm_hops != 0 && peer->ttl != MAXTTL)
4378 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
4379
4380 if (peer_group_active(peer))
4381 peer->ttl = peer->group->conf->ttl;
4382 else
4383 peer->ttl = BGP_DEFAULT_TTL;
4384
4385 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4386 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
4387 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
4388 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4389 else
4390 bgp_session_reset(peer);
4391 } else {
4392 group = peer->group;
4393 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
4394 if (peer->sort == BGP_PEER_IBGP)
4395 continue;
4396
4397 peer->ttl = BGP_DEFAULT_TTL;
4398
4399 if (peer->fd >= 0) {
4400 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
4401 bgp_notify_send(
4402 peer, BGP_NOTIFY_CEASE,
4403 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4404 else
4405 bgp_session_reset(peer);
4406 }
4407 }
4408 }
4409 return 0;
4410 }
4411
4412 /* Neighbor description. */
4413 int peer_description_set(struct peer *peer, const char *desc)
4414 {
4415 XFREE(MTYPE_PEER_DESC, peer->desc);
4416
4417 peer->desc = XSTRDUP(MTYPE_PEER_DESC, desc);
4418
4419 return 0;
4420 }
4421
4422 int peer_description_unset(struct peer *peer)
4423 {
4424 XFREE(MTYPE_PEER_DESC, peer->desc);
4425
4426 return 0;
4427 }
4428
4429 /* Neighbor update-source. */
4430 int peer_update_source_if_set(struct peer *peer, const char *ifname)
4431 {
4432 struct peer *member;
4433 struct listnode *node, *nnode;
4434
4435 /* Set flag and configuration on peer. */
4436 peer_flag_set(peer, PEER_FLAG_UPDATE_SOURCE);
4437 if (peer->update_if) {
4438 if (strcmp(peer->update_if, ifname) == 0)
4439 return 0;
4440 XFREE(MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
4441 }
4442 peer->update_if = XSTRDUP(MTYPE_PEER_UPDATE_SOURCE, ifname);
4443 sockunion_free(peer->update_source);
4444 peer->update_source = NULL;
4445
4446 /* Check if handling a regular peer. */
4447 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4448 /* Send notification or reset peer depending on state. */
4449 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
4450 peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
4451 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
4452 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4453 } else
4454 bgp_session_reset(peer);
4455
4456 /* Skip peer-group mechanics for regular peers. */
4457 return 0;
4458 }
4459
4460 /*
4461 * Set flag and configuration on all peer-group members, unless they are
4462 * explicitely overriding peer-group configuration.
4463 */
4464 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4465 /* Skip peers with overridden configuration. */
4466 if (CHECK_FLAG(member->flags_override, PEER_FLAG_UPDATE_SOURCE))
4467 continue;
4468
4469 /* Skip peers with the same configuration. */
4470 if (member->update_if) {
4471 if (strcmp(member->update_if, ifname) == 0)
4472 continue;
4473 XFREE(MTYPE_PEER_UPDATE_SOURCE, member->update_if);
4474 }
4475
4476 /* Set flag and configuration on peer-group member. */
4477 SET_FLAG(member->flags, PEER_FLAG_UPDATE_SOURCE);
4478 member->update_if = XSTRDUP(MTYPE_PEER_UPDATE_SOURCE, ifname);
4479 sockunion_free(member->update_source);
4480 member->update_source = NULL;
4481
4482 /* Send notification or reset peer depending on state. */
4483 if (BGP_IS_VALID_STATE_FOR_NOTIF(member->status)) {
4484 member->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
4485 bgp_notify_send(member, BGP_NOTIFY_CEASE,
4486 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4487 } else
4488 bgp_session_reset(member);
4489 }
4490
4491 return 0;
4492 }
4493
4494 int peer_update_source_addr_set(struct peer *peer, const union sockunion *su)
4495 {
4496 struct peer *member;
4497 struct listnode *node, *nnode;
4498
4499 /* Set flag and configuration on peer. */
4500 peer_flag_set(peer, PEER_FLAG_UPDATE_SOURCE);
4501 if (peer->update_source) {
4502 if (sockunion_cmp(peer->update_source, su) == 0)
4503 return 0;
4504 sockunion_free(peer->update_source);
4505 }
4506 peer->update_source = sockunion_dup(su);
4507 XFREE(MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
4508
4509 /* Check if handling a regular peer. */
4510 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4511 /* Send notification or reset peer depending on state. */
4512 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
4513 peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
4514 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
4515 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4516 } else
4517 bgp_session_reset(peer);
4518
4519 /* Skip peer-group mechanics for regular peers. */
4520 return 0;
4521 }
4522
4523 /*
4524 * Set flag and configuration on all peer-group members, unless they are
4525 * explicitely overriding peer-group configuration.
4526 */
4527 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4528 /* Skip peers with overridden configuration. */
4529 if (CHECK_FLAG(member->flags_override, PEER_FLAG_UPDATE_SOURCE))
4530 continue;
4531
4532 /* Skip peers with the same configuration. */
4533 if (member->update_source) {
4534 if (sockunion_cmp(member->update_source, su) == 0)
4535 continue;
4536 sockunion_free(member->update_source);
4537 }
4538
4539 /* Set flag and configuration on peer-group member. */
4540 SET_FLAG(member->flags, PEER_FLAG_UPDATE_SOURCE);
4541 member->update_source = sockunion_dup(su);
4542 XFREE(MTYPE_PEER_UPDATE_SOURCE, member->update_if);
4543
4544 /* Send notification or reset peer depending on state. */
4545 if (BGP_IS_VALID_STATE_FOR_NOTIF(member->status)) {
4546 member->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
4547 bgp_notify_send(member, BGP_NOTIFY_CEASE,
4548 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4549 } else
4550 bgp_session_reset(member);
4551 }
4552
4553 return 0;
4554 }
4555
4556 int peer_update_source_unset(struct peer *peer)
4557 {
4558 struct peer *member;
4559 struct listnode *node, *nnode;
4560
4561 if (!CHECK_FLAG(peer->flags, PEER_FLAG_UPDATE_SOURCE))
4562 return 0;
4563
4564 /* Inherit configuration from peer-group if peer is member. */
4565 if (peer_group_active(peer)) {
4566 peer_flag_inherit(peer, PEER_FLAG_UPDATE_SOURCE);
4567 PEER_SU_ATTR_INHERIT(peer, peer->group, update_source);
4568 PEER_STR_ATTR_INHERIT(peer, peer->group, update_if,
4569 MTYPE_PEER_UPDATE_SOURCE);
4570 } else {
4571 /* Otherwise remove flag and configuration from peer. */
4572 peer_flag_unset(peer, PEER_FLAG_UPDATE_SOURCE);
4573 sockunion_free(peer->update_source);
4574 peer->update_source = NULL;
4575 XFREE(MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
4576 }
4577
4578 /* Check if handling a regular peer. */
4579 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4580 /* Send notification or reset peer depending on state. */
4581 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
4582 peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
4583 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
4584 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4585 } else
4586 bgp_session_reset(peer);
4587
4588 /* Skip peer-group mechanics for regular peers. */
4589 return 0;
4590 }
4591
4592 /*
4593 * Set flag and configuration on all peer-group members, unless they are
4594 * explicitely overriding peer-group configuration.
4595 */
4596 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4597 /* Skip peers with overridden configuration. */
4598 if (CHECK_FLAG(member->flags_override, PEER_FLAG_UPDATE_SOURCE))
4599 continue;
4600
4601 /* Skip peers with the same configuration. */
4602 if (!CHECK_FLAG(member->flags, PEER_FLAG_UPDATE_SOURCE)
4603 && !member->update_source && !member->update_if)
4604 continue;
4605
4606 /* Remove flag and configuration on peer-group member. */
4607 UNSET_FLAG(member->flags, PEER_FLAG_UPDATE_SOURCE);
4608 sockunion_free(member->update_source);
4609 member->update_source = NULL;
4610 XFREE(MTYPE_PEER_UPDATE_SOURCE, member->update_if);
4611
4612 /* Send notification or reset peer depending on state. */
4613 if (BGP_IS_VALID_STATE_FOR_NOTIF(member->status)) {
4614 member->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
4615 bgp_notify_send(member, BGP_NOTIFY_CEASE,
4616 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
4617 } else
4618 bgp_session_reset(member);
4619 }
4620
4621 return 0;
4622 }
4623
4624 int peer_default_originate_set(struct peer *peer, afi_t afi, safi_t safi,
4625 const char *rmap, struct route_map *route_map)
4626 {
4627 struct peer *member;
4628 struct listnode *node, *nnode;
4629
4630 /* Set flag and configuration on peer. */
4631 peer_af_flag_set(peer, afi, safi, PEER_FLAG_DEFAULT_ORIGINATE);
4632 if (rmap) {
4633 if (!peer->default_rmap[afi][safi].name
4634 || strcmp(rmap, peer->default_rmap[afi][safi].name) != 0) {
4635 if (peer->default_rmap[afi][safi].name)
4636 XFREE(MTYPE_ROUTE_MAP_NAME,
4637 peer->default_rmap[afi][safi].name);
4638
4639 route_map_counter_decrement(peer->default_rmap[afi][safi].map);
4640 peer->default_rmap[afi][safi].name =
4641 XSTRDUP(MTYPE_ROUTE_MAP_NAME, rmap);
4642 peer->default_rmap[afi][safi].map = route_map;
4643 route_map_counter_increment(route_map);
4644 }
4645 } else if (!rmap) {
4646 if (peer->default_rmap[afi][safi].name)
4647 XFREE(MTYPE_ROUTE_MAP_NAME,
4648 peer->default_rmap[afi][safi].name);
4649
4650 route_map_counter_decrement(peer->default_rmap[afi][safi].map);
4651 peer->default_rmap[afi][safi].name = NULL;
4652 peer->default_rmap[afi][safi].map = NULL;
4653 }
4654
4655 /* Check if handling a regular peer. */
4656 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4657 /* Update peer route announcements. */
4658 if (peer->status == Established && peer->afc_nego[afi][safi]) {
4659 update_group_adjust_peer(peer_af_find(peer, afi, safi));
4660 bgp_default_originate(peer, afi, safi, 0);
4661 bgp_announce_route(peer, afi, safi);
4662 }
4663
4664 /* Skip peer-group mechanics for regular peers. */
4665 return 0;
4666 }
4667
4668 /*
4669 * Set flag and configuration on all peer-group members, unless they are
4670 * explicitely overriding peer-group configuration.
4671 */
4672 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4673 /* Skip peers with overridden configuration. */
4674 if (CHECK_FLAG(member->af_flags_override[afi][safi],
4675 PEER_FLAG_DEFAULT_ORIGINATE))
4676 continue;
4677
4678 /* Set flag and configuration on peer-group member. */
4679 SET_FLAG(member->af_flags[afi][safi],
4680 PEER_FLAG_DEFAULT_ORIGINATE);
4681 if (rmap) {
4682 if (member->default_rmap[afi][safi].name)
4683 XFREE(MTYPE_ROUTE_MAP_NAME,
4684 member->default_rmap[afi][safi].name);
4685 route_map_counter_decrement(
4686 member->default_rmap[afi][safi].map);
4687 member->default_rmap[afi][safi].name =
4688 XSTRDUP(MTYPE_ROUTE_MAP_NAME, rmap);
4689 member->default_rmap[afi][safi].map = route_map;
4690 route_map_counter_increment(route_map);
4691 }
4692
4693 /* Update peer route announcements. */
4694 if (member->status == Established
4695 && member->afc_nego[afi][safi]) {
4696 update_group_adjust_peer(
4697 peer_af_find(member, afi, safi));
4698 bgp_default_originate(member, afi, safi, 0);
4699 bgp_announce_route(member, afi, safi);
4700 }
4701 }
4702
4703 return 0;
4704 }
4705
4706 int peer_default_originate_unset(struct peer *peer, afi_t afi, safi_t safi)
4707 {
4708 struct peer *member;
4709 struct listnode *node, *nnode;
4710
4711 /* Inherit configuration from peer-group if peer is member. */
4712 if (peer_group_active(peer)) {
4713 peer_af_flag_inherit(peer, afi, safi,
4714 PEER_FLAG_DEFAULT_ORIGINATE);
4715 PEER_STR_ATTR_INHERIT(peer, peer->group,
4716 default_rmap[afi][safi].name,
4717 MTYPE_ROUTE_MAP_NAME);
4718 PEER_ATTR_INHERIT(peer, peer->group,
4719 default_rmap[afi][safi].map);
4720 } else {
4721 /* Otherwise remove flag and configuration from peer. */
4722 peer_af_flag_unset(peer, afi, safi,
4723 PEER_FLAG_DEFAULT_ORIGINATE);
4724 if (peer->default_rmap[afi][safi].name)
4725 XFREE(MTYPE_ROUTE_MAP_NAME,
4726 peer->default_rmap[afi][safi].name);
4727 route_map_counter_decrement(peer->default_rmap[afi][safi].map);
4728 peer->default_rmap[afi][safi].name = NULL;
4729 peer->default_rmap[afi][safi].map = NULL;
4730 }
4731
4732 /* Check if handling a regular peer. */
4733 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
4734 /* Update peer route announcements. */
4735 if (peer->status == Established && peer->afc_nego[afi][safi]) {
4736 update_group_adjust_peer(peer_af_find(peer, afi, safi));
4737 bgp_default_originate(peer, afi, safi, 1);
4738 bgp_announce_route(peer, afi, safi);
4739 }
4740
4741 /* Skip peer-group mechanics for regular peers. */
4742 return 0;
4743 }
4744
4745 /*
4746 * Remove flag and configuration from all peer-group members, unless
4747 * they are explicitely overriding peer-group configuration.
4748 */
4749 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4750 /* Skip peers with overridden configuration. */
4751 if (CHECK_FLAG(member->af_flags_override[afi][safi],
4752 PEER_FLAG_DEFAULT_ORIGINATE))
4753 continue;
4754
4755 /* Remove flag and configuration on peer-group member. */
4756 UNSET_FLAG(peer->af_flags[afi][safi],
4757 PEER_FLAG_DEFAULT_ORIGINATE);
4758 if (peer->default_rmap[afi][safi].name)
4759 XFREE(MTYPE_ROUTE_MAP_NAME,
4760 peer->default_rmap[afi][safi].name);
4761 route_map_counter_decrement(peer->default_rmap[afi][safi].map);
4762 peer->default_rmap[afi][safi].name = NULL;
4763 peer->default_rmap[afi][safi].map = NULL;
4764
4765 /* Update peer route announcements. */
4766 if (peer->status == Established && peer->afc_nego[afi][safi]) {
4767 update_group_adjust_peer(peer_af_find(peer, afi, safi));
4768 bgp_default_originate(peer, afi, safi, 1);
4769 bgp_announce_route(peer, afi, safi);
4770 }
4771 }
4772
4773 return 0;
4774 }
4775
4776 int peer_port_set(struct peer *peer, uint16_t port)
4777 {
4778 peer->port = port;
4779 return 0;
4780 }
4781
4782 int peer_port_unset(struct peer *peer)
4783 {
4784 peer->port = BGP_PORT_DEFAULT;
4785 return 0;
4786 }
4787
4788 /*
4789 * Helper function that is called after the name of the policy
4790 * being used by a peer has changed (AF specific). Automatically
4791 * initiates inbound or outbound processing as needed.
4792 */
4793 static void peer_on_policy_change(struct peer *peer, afi_t afi, safi_t safi,
4794 int outbound)
4795 {
4796 if (outbound) {
4797 update_group_adjust_peer(peer_af_find(peer, afi, safi));
4798 if (peer->status == Established)
4799 bgp_announce_route(peer, afi, safi);
4800 } else {
4801 if (peer->status != Established)
4802 return;
4803
4804 if (CHECK_FLAG(peer->af_flags[afi][safi],
4805 PEER_FLAG_SOFT_RECONFIG))
4806 bgp_soft_reconfig_in(peer, afi, safi);
4807 else if (CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_OLD_RCV)
4808 || CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_NEW_RCV))
4809 bgp_route_refresh_send(peer, afi, safi, 0, 0, 0);
4810 }
4811 }
4812
4813
4814 /* neighbor weight. */
4815 int peer_weight_set(struct peer *peer, afi_t afi, safi_t safi, uint16_t weight)
4816 {
4817 struct peer *member;
4818 struct listnode *node, *nnode;
4819
4820 /* Set flag and configuration on peer. */
4821 peer_af_flag_set(peer, afi, safi, PEER_FLAG_WEIGHT);
4822 if (peer->weight[afi][safi] != weight) {
4823 peer->weight[afi][safi] = weight;
4824 peer_on_policy_change(peer, afi, safi, 0);
4825 }
4826
4827 /* Skip peer-group mechanics for regular peers. */
4828 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
4829 return 0;
4830
4831 /*
4832 * Set flag and configuration on all peer-group members, unless they are
4833 * explicitely overriding peer-group configuration.
4834 */
4835 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4836 /* Skip peers with overridden configuration. */
4837 if (CHECK_FLAG(member->af_flags_override[afi][safi],
4838 PEER_FLAG_WEIGHT))
4839 continue;
4840
4841 /* Set flag and configuration on peer-group member. */
4842 SET_FLAG(member->af_flags[afi][safi], PEER_FLAG_WEIGHT);
4843 if (member->weight[afi][safi] != weight) {
4844 member->weight[afi][safi] = weight;
4845 peer_on_policy_change(member, afi, safi, 0);
4846 }
4847 }
4848
4849 return 0;
4850 }
4851
4852 int peer_weight_unset(struct peer *peer, afi_t afi, safi_t safi)
4853 {
4854 struct peer *member;
4855 struct listnode *node, *nnode;
4856
4857 if (!CHECK_FLAG(peer->af_flags[afi][safi], PEER_FLAG_WEIGHT))
4858 return 0;
4859
4860 /* Inherit configuration from peer-group if peer is member. */
4861 if (peer_group_active(peer)) {
4862 peer_af_flag_inherit(peer, afi, safi, PEER_FLAG_WEIGHT);
4863 PEER_ATTR_INHERIT(peer, peer->group, weight[afi][safi]);
4864
4865 peer_on_policy_change(peer, afi, safi, 0);
4866 return 0;
4867 }
4868
4869 /* Remove flag and configuration from peer. */
4870 peer_af_flag_unset(peer, afi, safi, PEER_FLAG_WEIGHT);
4871 peer->weight[afi][safi] = 0;
4872 peer_on_policy_change(peer, afi, safi, 0);
4873
4874 /* Skip peer-group mechanics for regular peers. */
4875 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
4876 return 0;
4877
4878 /*
4879 * Remove flag and configuration from all peer-group members, unless
4880 * they are explicitely overriding peer-group configuration.
4881 */
4882 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4883 /* Skip peers with overridden configuration. */
4884 if (CHECK_FLAG(member->af_flags_override[afi][safi],
4885 PEER_FLAG_WEIGHT))
4886 continue;
4887
4888 /* Skip peers where flag is already disabled. */
4889 if (!CHECK_FLAG(member->af_flags[afi][safi], PEER_FLAG_WEIGHT))
4890 continue;
4891
4892 /* Remove flag and configuration on peer-group member. */
4893 UNSET_FLAG(member->af_flags[afi][safi], PEER_FLAG_WEIGHT);
4894 member->weight[afi][safi] = 0;
4895 peer_on_policy_change(member, afi, safi, 0);
4896 }
4897
4898 return 0;
4899 }
4900
4901 int peer_timers_set(struct peer *peer, uint32_t keepalive, uint32_t holdtime)
4902 {
4903 struct peer *member;
4904 struct listnode *node, *nnode;
4905
4906 if (keepalive > 65535)
4907 return BGP_ERR_INVALID_VALUE;
4908
4909 if (holdtime > 65535)
4910 return BGP_ERR_INVALID_VALUE;
4911
4912 if (holdtime < 3 && holdtime != 0)
4913 return BGP_ERR_INVALID_VALUE;
4914
4915 /* Set flag and configuration on peer. */
4916 peer_flag_set(peer, PEER_FLAG_TIMER);
4917 peer->holdtime = holdtime;
4918 peer->keepalive = (keepalive < holdtime / 3 ? keepalive : holdtime / 3);
4919
4920 /* Skip peer-group mechanics for regular peers. */
4921 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
4922 return 0;
4923
4924 /*
4925 * Set flag and configuration on all peer-group members, unless they are
4926 * explicitely overriding peer-group configuration.
4927 */
4928 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4929 /* Skip peers with overridden configuration. */
4930 if (CHECK_FLAG(member->flags_override, PEER_FLAG_TIMER))
4931 continue;
4932
4933 /* Set flag and configuration on peer-group member. */
4934 SET_FLAG(member->flags, PEER_FLAG_TIMER);
4935 PEER_ATTR_INHERIT(peer, peer->group, holdtime);
4936 PEER_ATTR_INHERIT(peer, peer->group, keepalive);
4937 }
4938
4939 return 0;
4940 }
4941
4942 int peer_timers_unset(struct peer *peer)
4943 {
4944 struct peer *member;
4945 struct listnode *node, *nnode;
4946
4947 /* Inherit configuration from peer-group if peer is member. */
4948 if (peer_group_active(peer)) {
4949 peer_flag_inherit(peer, PEER_FLAG_TIMER);
4950 PEER_ATTR_INHERIT(peer, peer->group, holdtime);
4951 PEER_ATTR_INHERIT(peer, peer->group, keepalive);
4952 } else {
4953 /* Otherwise remove flag and configuration from peer. */
4954 peer_flag_unset(peer, PEER_FLAG_TIMER);
4955 peer->holdtime = 0;
4956 peer->keepalive = 0;
4957 }
4958
4959 /* Skip peer-group mechanics for regular peers. */
4960 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
4961 return 0;
4962
4963 /*
4964 * Remove flag and configuration from all peer-group members, unless
4965 * they are explicitely overriding peer-group configuration.
4966 */
4967 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
4968 /* Skip peers with overridden configuration. */
4969 if (CHECK_FLAG(member->flags_override, PEER_FLAG_TIMER))
4970 continue;
4971
4972 /* Remove flag and configuration on peer-group member. */
4973 UNSET_FLAG(member->flags, PEER_FLAG_TIMER);
4974 member->holdtime = 0;
4975 member->keepalive = 0;
4976 }
4977
4978 return 0;
4979 }
4980
4981 int peer_timers_connect_set(struct peer *peer, uint32_t connect)
4982 {
4983 struct peer *member;
4984 struct listnode *node, *nnode;
4985
4986 if (connect > 65535)
4987 return BGP_ERR_INVALID_VALUE;
4988
4989 /* Set flag and configuration on peer. */
4990 peer_flag_set(peer, PEER_FLAG_TIMER_CONNECT);
4991 peer->connect = connect;
4992 peer->v_connect = connect;
4993
4994 /* Skip peer-group mechanics for regular peers. */
4995 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
4996 return 0;
4997
4998 /*
4999 * Set flag and configuration on all peer-group members, unless they are
5000 * explicitely overriding peer-group configuration.
5001 */
5002 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5003 /* Skip peers with overridden configuration. */
5004 if (CHECK_FLAG(member->flags_override, PEER_FLAG_TIMER_CONNECT))
5005 continue;
5006
5007 /* Set flag and configuration on peer-group member. */
5008 SET_FLAG(member->flags, PEER_FLAG_TIMER_CONNECT);
5009 member->connect = connect;
5010 member->v_connect = connect;
5011 }
5012
5013 return 0;
5014 }
5015
5016 int peer_timers_connect_unset(struct peer *peer)
5017 {
5018 struct peer *member;
5019 struct listnode *node, *nnode;
5020
5021 /* Inherit configuration from peer-group if peer is member. */
5022 if (peer_group_active(peer)) {
5023 peer_flag_inherit(peer, PEER_FLAG_TIMER_CONNECT);
5024 PEER_ATTR_INHERIT(peer, peer->group, connect);
5025 } else {
5026 /* Otherwise remove flag and configuration from peer. */
5027 peer_flag_unset(peer, PEER_FLAG_TIMER_CONNECT);
5028 peer->connect = 0;
5029 }
5030
5031 /* Set timer with fallback to default value. */
5032 if (peer->connect)
5033 peer->v_connect = peer->connect;
5034 else
5035 peer->v_connect = peer->bgp->default_connect_retry;
5036
5037 /* Skip peer-group mechanics for regular peers. */
5038 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
5039 return 0;
5040
5041 /*
5042 * Remove flag and configuration from all peer-group members, unless
5043 * they are explicitely overriding peer-group configuration.
5044 */
5045 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5046 /* Skip peers with overridden configuration. */
5047 if (CHECK_FLAG(member->flags_override, PEER_FLAG_TIMER_CONNECT))
5048 continue;
5049
5050 /* Remove flag and configuration on peer-group member. */
5051 UNSET_FLAG(member->flags, PEER_FLAG_TIMER_CONNECT);
5052 member->connect = 0;
5053 member->v_connect = peer->bgp->default_connect_retry;
5054 }
5055
5056 return 0;
5057 }
5058
5059 int peer_advertise_interval_set(struct peer *peer, uint32_t routeadv)
5060 {
5061 struct peer *member;
5062 struct listnode *node, *nnode;
5063
5064 if (routeadv > 600)
5065 return BGP_ERR_INVALID_VALUE;
5066
5067 /* Set flag and configuration on peer. */
5068 peer_flag_set(peer, PEER_FLAG_ROUTEADV);
5069 peer->routeadv = routeadv;
5070 peer->v_routeadv = routeadv;
5071
5072 /* Check if handling a regular peer. */
5073 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5074 /* Update peer route announcements. */
5075 update_group_adjust_peer_afs(peer);
5076 if (peer->status == Established)
5077 bgp_announce_route_all(peer);
5078
5079 /* Skip peer-group mechanics for regular peers. */
5080 return 0;
5081 }
5082
5083 /*
5084 * Set flag and configuration on all peer-group members, unless they are
5085 * explicitely overriding peer-group configuration.
5086 */
5087 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5088 /* Skip peers with overridden configuration. */
5089 if (CHECK_FLAG(member->flags_override, PEER_FLAG_ROUTEADV))
5090 continue;
5091
5092 /* Set flag and configuration on peer-group member. */
5093 SET_FLAG(member->flags, PEER_FLAG_ROUTEADV);
5094 member->routeadv = routeadv;
5095 member->v_routeadv = routeadv;
5096
5097 /* Update peer route announcements. */
5098 update_group_adjust_peer_afs(member);
5099 if (member->status == Established)
5100 bgp_announce_route_all(member);
5101 }
5102
5103 return 0;
5104 }
5105
5106 int peer_advertise_interval_unset(struct peer *peer)
5107 {
5108 struct peer *member;
5109 struct listnode *node, *nnode;
5110
5111 /* Inherit configuration from peer-group if peer is member. */
5112 if (peer_group_active(peer)) {
5113 peer_flag_inherit(peer, PEER_FLAG_ROUTEADV);
5114 PEER_ATTR_INHERIT(peer, peer->group, routeadv);
5115 } else {
5116 /* Otherwise remove flag and configuration from peer. */
5117 peer_flag_unset(peer, PEER_FLAG_ROUTEADV);
5118 peer->routeadv = 0;
5119 }
5120
5121 /* Set timer with fallback to default value. */
5122 if (peer->routeadv)
5123 peer->v_routeadv = peer->routeadv;
5124 else
5125 peer->v_routeadv = (peer->sort == BGP_PEER_IBGP)
5126 ? BGP_DEFAULT_IBGP_ROUTEADV
5127 : BGP_DEFAULT_EBGP_ROUTEADV;
5128
5129 /* Check if handling a regular peer. */
5130 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5131 /* Update peer route announcements. */
5132 update_group_adjust_peer_afs(peer);
5133 if (peer->status == Established)
5134 bgp_announce_route_all(peer);
5135
5136 /* Skip peer-group mechanics for regular peers. */
5137 return 0;
5138 }
5139
5140 /*
5141 * Remove flag and configuration from all peer-group members, unless
5142 * they are explicitely overriding peer-group configuration.
5143 */
5144 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5145 /* Skip peers with overridden configuration. */
5146 if (CHECK_FLAG(member->flags_override, PEER_FLAG_ROUTEADV))
5147 continue;
5148
5149 /* Remove flag and configuration on peer-group member. */
5150 UNSET_FLAG(member->flags, PEER_FLAG_ROUTEADV);
5151 member->routeadv = 0;
5152 member->v_routeadv = (member->sort == BGP_PEER_IBGP)
5153 ? BGP_DEFAULT_IBGP_ROUTEADV
5154 : BGP_DEFAULT_EBGP_ROUTEADV;
5155
5156 /* Update peer route announcements. */
5157 update_group_adjust_peer_afs(member);
5158 if (member->status == Established)
5159 bgp_announce_route_all(member);
5160 }
5161
5162 return 0;
5163 }
5164
5165 /* neighbor interface */
5166 void peer_interface_set(struct peer *peer, const char *str)
5167 {
5168 XFREE(MTYPE_BGP_PEER_IFNAME, peer->ifname);
5169 peer->ifname = XSTRDUP(MTYPE_BGP_PEER_IFNAME, str);
5170 }
5171
5172 void peer_interface_unset(struct peer *peer)
5173 {
5174 XFREE(MTYPE_BGP_PEER_IFNAME, peer->ifname);
5175 }
5176
5177 /* Allow-as in. */
5178 int peer_allowas_in_set(struct peer *peer, afi_t afi, safi_t safi,
5179 int allow_num, int origin)
5180 {
5181 struct peer *member;
5182 struct listnode *node, *nnode;
5183
5184 if (!origin && (allow_num < 1 || allow_num > 10))
5185 return BGP_ERR_INVALID_VALUE;
5186
5187 /* Set flag and configuration on peer. */
5188 peer_af_flag_set(peer, afi, safi, PEER_FLAG_ALLOWAS_IN);
5189 if (origin) {
5190 if (peer->allowas_in[afi][safi] != 0
5191 || !CHECK_FLAG(peer->af_flags[afi][safi],
5192 PEER_FLAG_ALLOWAS_IN_ORIGIN)) {
5193 peer_af_flag_set(peer, afi, safi,
5194 PEER_FLAG_ALLOWAS_IN_ORIGIN);
5195 peer->allowas_in[afi][safi] = 0;
5196 peer_on_policy_change(peer, afi, safi, 0);
5197 }
5198 } else {
5199 if (peer->allowas_in[afi][safi] != allow_num
5200 || CHECK_FLAG(peer->af_flags[afi][safi],
5201 PEER_FLAG_ALLOWAS_IN_ORIGIN)) {
5202
5203 peer_af_flag_unset(peer, afi, safi,
5204 PEER_FLAG_ALLOWAS_IN_ORIGIN);
5205 peer->allowas_in[afi][safi] = allow_num;
5206 peer_on_policy_change(peer, afi, safi, 0);
5207 }
5208 }
5209
5210 /* Skip peer-group mechanics for regular peers. */
5211 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
5212 return 0;
5213
5214 /*
5215 * Set flag and configuration on all peer-group members, unless
5216 * they are explicitely overriding peer-group configuration.
5217 */
5218 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5219 /* Skip peers with overridden configuration. */
5220 if (CHECK_FLAG(member->af_flags_override[afi][safi],
5221 PEER_FLAG_ALLOWAS_IN))
5222 continue;
5223
5224 /* Set flag and configuration on peer-group member. */
5225 SET_FLAG(member->af_flags[afi][safi], PEER_FLAG_ALLOWAS_IN);
5226 if (origin) {
5227 if (member->allowas_in[afi][safi] != 0
5228 || !CHECK_FLAG(member->af_flags[afi][safi],
5229 PEER_FLAG_ALLOWAS_IN_ORIGIN)) {
5230 SET_FLAG(member->af_flags[afi][safi],
5231 PEER_FLAG_ALLOWAS_IN_ORIGIN);
5232 member->allowas_in[afi][safi] = 0;
5233 peer_on_policy_change(peer, afi, safi, 0);
5234 }
5235 } else {
5236 if (member->allowas_in[afi][safi] != allow_num
5237 || CHECK_FLAG(member->af_flags[afi][safi],
5238 PEER_FLAG_ALLOWAS_IN_ORIGIN)) {
5239 UNSET_FLAG(member->af_flags[afi][safi],
5240 PEER_FLAG_ALLOWAS_IN_ORIGIN);
5241 member->allowas_in[afi][safi] = allow_num;
5242 peer_on_policy_change(peer, afi, safi, 0);
5243 }
5244 }
5245 }
5246
5247 return 0;
5248 }
5249
5250 int peer_allowas_in_unset(struct peer *peer, afi_t afi, safi_t safi)
5251 {
5252 struct peer *member;
5253 struct listnode *node, *nnode;
5254
5255 /* Skip peer if flag is already disabled. */
5256 if (!CHECK_FLAG(peer->af_flags[afi][safi], PEER_FLAG_ALLOWAS_IN))
5257 return 0;
5258
5259 /* Inherit configuration from peer-group if peer is member. */
5260 if (peer_group_active(peer)) {
5261 peer_af_flag_inherit(peer, afi, safi, PEER_FLAG_ALLOWAS_IN);
5262 peer_af_flag_inherit(peer, afi, safi,
5263 PEER_FLAG_ALLOWAS_IN_ORIGIN);
5264 PEER_ATTR_INHERIT(peer, peer->group, allowas_in[afi][safi]);
5265 peer_on_policy_change(peer, afi, safi, 0);
5266
5267 return 0;
5268 }
5269
5270 /* Remove flag and configuration from peer. */
5271 peer_af_flag_unset(peer, afi, safi, PEER_FLAG_ALLOWAS_IN);
5272 peer_af_flag_unset(peer, afi, safi, PEER_FLAG_ALLOWAS_IN_ORIGIN);
5273 peer->allowas_in[afi][safi] = 0;
5274 peer_on_policy_change(peer, afi, safi, 0);
5275
5276 /* Skip peer-group mechanics if handling a regular peer. */
5277 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP))
5278 return 0;
5279
5280 /*
5281 * Remove flags and configuration from all peer-group members, unless
5282 * they are explicitely overriding peer-group configuration.
5283 */
5284 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5285 /* Skip peers with overridden configuration. */
5286 if (CHECK_FLAG(member->af_flags_override[afi][safi],
5287 PEER_FLAG_ALLOWAS_IN))
5288 continue;
5289
5290 /* Skip peers where flag is already disabled. */
5291 if (!CHECK_FLAG(member->af_flags[afi][safi],
5292 PEER_FLAG_ALLOWAS_IN))
5293 continue;
5294
5295 /* Remove flags and configuration on peer-group member. */
5296 UNSET_FLAG(member->af_flags[afi][safi], PEER_FLAG_ALLOWAS_IN);
5297 UNSET_FLAG(member->af_flags[afi][safi],
5298 PEER_FLAG_ALLOWAS_IN_ORIGIN);
5299 member->allowas_in[afi][safi] = 0;
5300 peer_on_policy_change(member, afi, safi, 0);
5301 }
5302
5303 return 0;
5304 }
5305
5306 int peer_local_as_set(struct peer *peer, as_t as, int no_prepend,
5307 int replace_as)
5308 {
5309 bool old_no_prepend, old_replace_as;
5310 struct bgp *bgp = peer->bgp;
5311 struct peer *member;
5312 struct listnode *node, *nnode;
5313
5314 if (peer_sort(peer) != BGP_PEER_EBGP
5315 && peer_sort(peer) != BGP_PEER_INTERNAL)
5316 return BGP_ERR_LOCAL_AS_ALLOWED_ONLY_FOR_EBGP;
5317
5318 if (bgp->as == as)
5319 return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS;
5320
5321 if (peer->as == as)
5322 return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS_REMOTE_AS;
5323
5324 /* Save previous flag states. */
5325 old_no_prepend =
5326 !!CHECK_FLAG(peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
5327 old_replace_as =
5328 !!CHECK_FLAG(peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
5329
5330 /* Set flag and configuration on peer. */
5331 peer_flag_set(peer, PEER_FLAG_LOCAL_AS);
5332 peer_flag_modify(peer, PEER_FLAG_LOCAL_AS_NO_PREPEND, no_prepend);
5333 peer_flag_modify(peer, PEER_FLAG_LOCAL_AS_REPLACE_AS, replace_as);
5334
5335 if (peer->change_local_as == as && old_no_prepend == no_prepend
5336 && old_replace_as == replace_as)
5337 return 0;
5338 peer->change_local_as = as;
5339
5340 /* Check if handling a regular peer. */
5341 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5342 /* Send notification or reset peer depending on state. */
5343 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
5344 peer->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
5345 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
5346 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5347 } else
5348 bgp_session_reset(peer);
5349
5350 /* Skip peer-group mechanics for regular peers. */
5351 return 0;
5352 }
5353
5354 /*
5355 * Set flag and configuration on all peer-group members, unless they are
5356 * explicitely overriding peer-group configuration.
5357 */
5358 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5359 /* Skip peers with overridden configuration. */
5360 if (CHECK_FLAG(member->flags_override, PEER_FLAG_LOCAL_AS))
5361 continue;
5362
5363 /* Skip peers with the same configuration. */
5364 old_no_prepend = CHECK_FLAG(member->flags,
5365 PEER_FLAG_LOCAL_AS_NO_PREPEND);
5366 old_replace_as = CHECK_FLAG(member->flags,
5367 PEER_FLAG_LOCAL_AS_REPLACE_AS);
5368 if (member->change_local_as == as
5369 && CHECK_FLAG(member->flags, PEER_FLAG_LOCAL_AS)
5370 && old_no_prepend == no_prepend
5371 && old_replace_as == replace_as)
5372 continue;
5373
5374 /* Set flag and configuration on peer-group member. */
5375 SET_FLAG(member->flags, PEER_FLAG_LOCAL_AS);
5376 COND_FLAG(member->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND,
5377 no_prepend);
5378 COND_FLAG(member->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS,
5379 replace_as);
5380 member->change_local_as = as;
5381
5382 /* Send notification or stop peer depending on state. */
5383 if (BGP_IS_VALID_STATE_FOR_NOTIF(member->status)) {
5384 member->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
5385 bgp_notify_send(member, BGP_NOTIFY_CEASE,
5386 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5387 } else
5388 BGP_EVENT_ADD(member, BGP_Stop);
5389 }
5390
5391 return 0;
5392 }
5393
5394 int peer_local_as_unset(struct peer *peer)
5395 {
5396 struct peer *member;
5397 struct listnode *node, *nnode;
5398
5399 if (!CHECK_FLAG(peer->flags, PEER_FLAG_LOCAL_AS))
5400 return 0;
5401
5402 /* Inherit configuration from peer-group if peer is member. */
5403 if (peer_group_active(peer)) {
5404 peer_flag_inherit(peer, PEER_FLAG_LOCAL_AS);
5405 peer_flag_inherit(peer, PEER_FLAG_LOCAL_AS_NO_PREPEND);
5406 peer_flag_inherit(peer, PEER_FLAG_LOCAL_AS_REPLACE_AS);
5407 PEER_ATTR_INHERIT(peer, peer->group, change_local_as);
5408 } else {
5409 /* Otherwise remove flag and configuration from peer. */
5410 peer_flag_unset(peer, PEER_FLAG_LOCAL_AS);
5411 peer_flag_unset(peer, PEER_FLAG_LOCAL_AS_NO_PREPEND);
5412 peer_flag_unset(peer, PEER_FLAG_LOCAL_AS_REPLACE_AS);
5413 peer->change_local_as = 0;
5414 }
5415
5416 /* Check if handling a regular peer. */
5417 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5418 /* Send notification or stop peer depending on state. */
5419 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status)) {
5420 peer->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
5421 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
5422 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5423 } else
5424 BGP_EVENT_ADD(peer, BGP_Stop);
5425
5426 /* Skip peer-group mechanics for regular peers. */
5427 return 0;
5428 }
5429
5430 /*
5431 * Remove flag and configuration from all peer-group members, unless
5432 * they are explicitely overriding peer-group configuration.
5433 */
5434 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5435 /* Skip peers with overridden configuration. */
5436 if (CHECK_FLAG(member->flags_override, PEER_FLAG_LOCAL_AS))
5437 continue;
5438
5439 /* Remove flag and configuration on peer-group member. */
5440 UNSET_FLAG(member->flags, PEER_FLAG_LOCAL_AS);
5441 UNSET_FLAG(member->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
5442 UNSET_FLAG(member->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
5443 member->change_local_as = 0;
5444
5445 /* Send notification or stop peer depending on state. */
5446 if (BGP_IS_VALID_STATE_FOR_NOTIF(member->status)) {
5447 member->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
5448 bgp_notify_send(member, BGP_NOTIFY_CEASE,
5449 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5450 } else
5451 bgp_session_reset(member);
5452 }
5453
5454 return 0;
5455 }
5456
5457 /* Set password for authenticating with the peer. */
5458 int peer_password_set(struct peer *peer, const char *password)
5459 {
5460 struct peer *member;
5461 struct listnode *node, *nnode;
5462 int len = password ? strlen(password) : 0;
5463 int ret = BGP_SUCCESS;
5464
5465 if ((len < PEER_PASSWORD_MINLEN) || (len > PEER_PASSWORD_MAXLEN))
5466 return BGP_ERR_INVALID_VALUE;
5467
5468 /* Set flag and configuration on peer. */
5469 peer_flag_set(peer, PEER_FLAG_PASSWORD);
5470 if (peer->password && strcmp(peer->password, password) == 0)
5471 return 0;
5472 XFREE(MTYPE_PEER_PASSWORD, peer->password);
5473 peer->password = XSTRDUP(MTYPE_PEER_PASSWORD, password);
5474
5475 /* Check if handling a regular peer. */
5476 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5477 /* Send notification or reset peer depending on state. */
5478 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
5479 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
5480 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5481 else
5482 bgp_session_reset(peer);
5483
5484 /*
5485 * Attempt to install password on socket and skip peer-group
5486 * mechanics.
5487 */
5488 if (BGP_PEER_SU_UNSPEC(peer))
5489 return BGP_SUCCESS;
5490 return (bgp_md5_set(peer) >= 0) ? BGP_SUCCESS
5491 : BGP_ERR_TCPSIG_FAILED;
5492 }
5493
5494 /*
5495 * Set flag and configuration on all peer-group members, unless they are
5496 * explicitely overriding peer-group configuration.
5497 */
5498 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5499 /* Skip peers with overridden configuration. */
5500 if (CHECK_FLAG(member->flags_override, PEER_FLAG_PASSWORD))
5501 continue;
5502
5503 /* Skip peers with the same password. */
5504 if (member->password && strcmp(member->password, password) == 0)
5505 continue;
5506
5507 /* Set flag and configuration on peer-group member. */
5508 SET_FLAG(member->flags, PEER_FLAG_PASSWORD);
5509 if (member->password)
5510 XFREE(MTYPE_PEER_PASSWORD, member->password);
5511 member->password = XSTRDUP(MTYPE_PEER_PASSWORD, password);
5512
5513 /* Send notification or reset peer depending on state. */
5514 if (BGP_IS_VALID_STATE_FOR_NOTIF(member->status))
5515 bgp_notify_send(member, BGP_NOTIFY_CEASE,
5516 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5517 else
5518 bgp_session_reset(member);
5519
5520 /* Attempt to install password on socket. */
5521 if (!BGP_PEER_SU_UNSPEC(member) && bgp_md5_set(member) < 0)
5522 ret = BGP_ERR_TCPSIG_FAILED;
5523 }
5524
5525 /* Set flag and configuration on all peer-group listen ranges */
5526 struct listnode *ln;
5527 struct prefix *lr;
5528
5529 for (ALL_LIST_ELEMENTS_RO(peer->group->listen_range[AFI_IP], ln, lr))
5530 bgp_md5_set_prefix(lr, password);
5531 for (ALL_LIST_ELEMENTS_RO(peer->group->listen_range[AFI_IP6], ln, lr))
5532 bgp_md5_set_prefix(lr, password);
5533
5534 return ret;
5535 }
5536
5537 int peer_password_unset(struct peer *peer)
5538 {
5539 struct peer *member;
5540 struct listnode *node, *nnode;
5541
5542 if (!CHECK_FLAG(peer->flags, PEER_FLAG_PASSWORD))
5543 return 0;
5544
5545 /* Inherit configuration from peer-group if peer is member. */
5546 if (peer_group_active(peer)) {
5547 peer_flag_inherit(peer, PEER_FLAG_PASSWORD);
5548 PEER_STR_ATTR_INHERIT(peer, peer->group, password,
5549 MTYPE_PEER_PASSWORD);
5550 } else {
5551 /* Otherwise remove flag and configuration from peer. */
5552 peer_flag_unset(peer, PEER_FLAG_PASSWORD);
5553 XFREE(MTYPE_PEER_PASSWORD, peer->password);
5554 }
5555
5556 /* Check if handling a regular peer. */
5557 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5558 /* Send notification or reset peer depending on state. */
5559 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
5560 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
5561 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5562 else
5563 bgp_session_reset(peer);
5564
5565 /* Attempt to uninstall password on socket. */
5566 if (!BGP_PEER_SU_UNSPEC(peer))
5567 bgp_md5_unset(peer);
5568
5569 /* Skip peer-group mechanics for regular peers. */
5570 return 0;
5571 }
5572
5573 /*
5574 * Remove flag and configuration from all peer-group members, unless
5575 * they are explicitely overriding peer-group configuration.
5576 */
5577 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5578 /* Skip peers with overridden configuration. */
5579 if (CHECK_FLAG(member->flags_override, PEER_FLAG_PASSWORD))
5580 continue;
5581
5582 /* Remove flag and configuration on peer-group member. */
5583 UNSET_FLAG(member->flags, PEER_FLAG_PASSWORD);
5584 XFREE(MTYPE_PEER_PASSWORD, member->password);
5585
5586 /* Send notification or reset peer depending on state. */
5587 if (BGP_IS_VALID_STATE_FOR_NOTIF(member->status))
5588 bgp_notify_send(member, BGP_NOTIFY_CEASE,
5589 BGP_NOTIFY_CEASE_CONFIG_CHANGE);
5590 else
5591 bgp_session_reset(member);
5592
5593 /* Attempt to uninstall password on socket. */
5594 if (!BGP_PEER_SU_UNSPEC(member))
5595 bgp_md5_unset(member);
5596 }
5597
5598 /* Set flag and configuration on all peer-group listen ranges */
5599 struct listnode *ln;
5600 struct prefix *lr;
5601
5602 for (ALL_LIST_ELEMENTS_RO(peer->group->listen_range[AFI_IP], ln, lr))
5603 bgp_md5_unset_prefix(lr);
5604 for (ALL_LIST_ELEMENTS_RO(peer->group->listen_range[AFI_IP6], ln, lr))
5605 bgp_md5_unset_prefix(lr);
5606
5607 return 0;
5608 }
5609
5610
5611 /* Set distribute list to the peer. */
5612 int peer_distribute_set(struct peer *peer, afi_t afi, safi_t safi, int direct,
5613 const char *name)
5614 {
5615 struct peer *member;
5616 struct bgp_filter *filter;
5617 struct listnode *node, *nnode;
5618
5619 if (direct != FILTER_IN && direct != FILTER_OUT)
5620 return BGP_ERR_INVALID_VALUE;
5621
5622 /* Set configuration on peer. */
5623 filter = &peer->filter[afi][safi];
5624 if (filter->plist[direct].name)
5625 return BGP_ERR_PEER_FILTER_CONFLICT;
5626 if (filter->dlist[direct].name)
5627 XFREE(MTYPE_BGP_FILTER_NAME, filter->dlist[direct].name);
5628 filter->dlist[direct].name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
5629 filter->dlist[direct].alist = access_list_lookup(afi, name);
5630
5631 /* Check if handling a regular peer. */
5632 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5633 /* Set override-flag and process peer route updates. */
5634 SET_FLAG(peer->filter_override[afi][safi][direct],
5635 PEER_FT_DISTRIBUTE_LIST);
5636 peer_on_policy_change(peer, afi, safi,
5637 (direct == FILTER_OUT) ? 1 : 0);
5638
5639 /* Skip peer-group mechanics for regular peers. */
5640 return 0;
5641 }
5642
5643 /*
5644 * Set configuration on all peer-group members, un less they are
5645 * explicitely overriding peer-group configuration.
5646 */
5647 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5648 /* Skip peers with overridden configuration. */
5649 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
5650 PEER_FT_DISTRIBUTE_LIST))
5651 continue;
5652
5653 /* Set configuration on peer-group member. */
5654 filter = &member->filter[afi][safi];
5655 if (filter->dlist[direct].name)
5656 XFREE(MTYPE_BGP_FILTER_NAME,
5657 filter->dlist[direct].name);
5658 filter->dlist[direct].name =
5659 XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
5660 filter->dlist[direct].alist = access_list_lookup(afi, name);
5661
5662 /* Process peer route updates. */
5663 peer_on_policy_change(member, afi, safi,
5664 (direct == FILTER_OUT) ? 1 : 0);
5665 }
5666
5667 return 0;
5668 }
5669
5670 int peer_distribute_unset(struct peer *peer, afi_t afi, safi_t safi, int direct)
5671 {
5672 struct peer *member;
5673 struct bgp_filter *filter;
5674 struct listnode *node, *nnode;
5675
5676 if (direct != FILTER_IN && direct != FILTER_OUT)
5677 return BGP_ERR_INVALID_VALUE;
5678
5679 /* Unset override-flag unconditionally. */
5680 UNSET_FLAG(peer->filter_override[afi][safi][direct],
5681 PEER_FT_DISTRIBUTE_LIST);
5682
5683 /* Inherit configuration from peer-group if peer is member. */
5684 if (peer_group_active(peer)) {
5685 PEER_STR_ATTR_INHERIT(peer, peer->group,
5686 filter[afi][safi].dlist[direct].name,
5687 MTYPE_BGP_FILTER_NAME);
5688 PEER_ATTR_INHERIT(peer, peer->group,
5689 filter[afi][safi].dlist[direct].alist);
5690 } else {
5691 /* Otherwise remove configuration from peer. */
5692 filter = &peer->filter[afi][safi];
5693 if (filter->dlist[direct].name)
5694 XFREE(MTYPE_BGP_FILTER_NAME,
5695 filter->dlist[direct].name);
5696 filter->dlist[direct].name = NULL;
5697 filter->dlist[direct].alist = NULL;
5698 }
5699
5700 /* Check if handling a regular peer. */
5701 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5702 /* Process peer route updates. */
5703 peer_on_policy_change(peer, afi, safi,
5704 (direct == FILTER_OUT) ? 1 : 0);
5705
5706 /* Skip peer-group mechanics for regular peers. */
5707 return 0;
5708 }
5709
5710 /*
5711 * Remove configuration on all peer-group members, unless they are
5712 * explicitely overriding peer-group configuration.
5713 */
5714 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5715 /* Skip peers with overridden configuration. */
5716 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
5717 PEER_FT_DISTRIBUTE_LIST))
5718 continue;
5719
5720 /* Remove configuration on peer-group member. */
5721 filter = &member->filter[afi][safi];
5722 if (filter->dlist[direct].name)
5723 XFREE(MTYPE_BGP_FILTER_NAME,
5724 filter->dlist[direct].name);
5725 filter->dlist[direct].name = NULL;
5726 filter->dlist[direct].alist = NULL;
5727
5728 /* Process peer route updates. */
5729 peer_on_policy_change(member, afi, safi,
5730 (direct == FILTER_OUT) ? 1 : 0);
5731 }
5732
5733 return 0;
5734 }
5735
5736 /* Update distribute list. */
5737 static void peer_distribute_update(struct access_list *access)
5738 {
5739 afi_t afi;
5740 safi_t safi;
5741 int direct;
5742 struct listnode *mnode, *mnnode;
5743 struct listnode *node, *nnode;
5744 struct bgp *bgp;
5745 struct peer *peer;
5746 struct peer_group *group;
5747 struct bgp_filter *filter;
5748
5749 for (ALL_LIST_ELEMENTS(bm->bgp, mnode, mnnode, bgp)) {
5750 if (access->name)
5751 update_group_policy_update(bgp, BGP_POLICY_FILTER_LIST,
5752 access->name, 0, 0);
5753 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
5754 FOREACH_AFI_SAFI (afi, safi) {
5755 filter = &peer->filter[afi][safi];
5756
5757 for (direct = FILTER_IN; direct < FILTER_MAX;
5758 direct++) {
5759 if (filter->dlist[direct].name)
5760 filter->dlist[direct]
5761 .alist = access_list_lookup(
5762 afi,
5763 filter->dlist[direct]
5764 .name);
5765 else
5766 filter->dlist[direct].alist =
5767 NULL;
5768 }
5769 }
5770 }
5771 for (ALL_LIST_ELEMENTS(bgp->group, node, nnode, group)) {
5772 FOREACH_AFI_SAFI (afi, safi) {
5773 filter = &group->conf->filter[afi][safi];
5774
5775 for (direct = FILTER_IN; direct < FILTER_MAX;
5776 direct++) {
5777 if (filter->dlist[direct].name)
5778 filter->dlist[direct]
5779 .alist = access_list_lookup(
5780 afi,
5781 filter->dlist[direct]
5782 .name);
5783 else
5784 filter->dlist[direct].alist =
5785 NULL;
5786 }
5787 }
5788 }
5789 #if ENABLE_BGP_VNC
5790 vnc_prefix_list_update(bgp);
5791 #endif
5792 }
5793 }
5794
5795 /* Set prefix list to the peer. */
5796 int peer_prefix_list_set(struct peer *peer, afi_t afi, safi_t safi, int direct,
5797 const char *name)
5798 {
5799 struct peer *member;
5800 struct bgp_filter *filter;
5801 struct listnode *node, *nnode;
5802
5803 if (direct != FILTER_IN && direct != FILTER_OUT)
5804 return BGP_ERR_INVALID_VALUE;
5805
5806 /* Set configuration on peer. */
5807 filter = &peer->filter[afi][safi];
5808 if (filter->dlist[direct].name)
5809 return BGP_ERR_PEER_FILTER_CONFLICT;
5810 if (filter->plist[direct].name)
5811 XFREE(MTYPE_BGP_FILTER_NAME, filter->plist[direct].name);
5812 filter->plist[direct].name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
5813 filter->plist[direct].plist = prefix_list_lookup(afi, name);
5814
5815 /* Check if handling a regular peer. */
5816 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5817 /* Set override-flag and process peer route updates. */
5818 SET_FLAG(peer->filter_override[afi][safi][direct],
5819 PEER_FT_PREFIX_LIST);
5820 peer_on_policy_change(peer, afi, safi,
5821 (direct == FILTER_OUT) ? 1 : 0);
5822
5823 /* Skip peer-group mechanics for regular peers. */
5824 return 0;
5825 }
5826
5827 /*
5828 * Set configuration on all peer-group members, unless they are
5829 * explicitely overriding peer-group configuration.
5830 */
5831 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5832 /* Skip peers with overridden configuration. */
5833 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
5834 PEER_FT_PREFIX_LIST))
5835 continue;
5836
5837 /* Set configuration on peer-group member. */
5838 filter = &member->filter[afi][safi];
5839 if (filter->plist[direct].name)
5840 XFREE(MTYPE_BGP_FILTER_NAME,
5841 filter->plist[direct].name);
5842 filter->plist[direct].name =
5843 XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
5844 filter->plist[direct].plist = prefix_list_lookup(afi, name);
5845
5846 /* Process peer route updates. */
5847 peer_on_policy_change(member, afi, safi,
5848 (direct == FILTER_OUT) ? 1 : 0);
5849 }
5850
5851 return 0;
5852 }
5853
5854 int peer_prefix_list_unset(struct peer *peer, afi_t afi, safi_t safi,
5855 int direct)
5856 {
5857 struct peer *member;
5858 struct bgp_filter *filter;
5859 struct listnode *node, *nnode;
5860
5861 if (direct != FILTER_IN && direct != FILTER_OUT)
5862 return BGP_ERR_INVALID_VALUE;
5863
5864 /* Unset override-flag unconditionally. */
5865 UNSET_FLAG(peer->filter_override[afi][safi][direct],
5866 PEER_FT_PREFIX_LIST);
5867
5868 /* Inherit configuration from peer-group if peer is member. */
5869 if (peer_group_active(peer)) {
5870 PEER_STR_ATTR_INHERIT(peer, peer->group,
5871 filter[afi][safi].plist[direct].name,
5872 MTYPE_BGP_FILTER_NAME);
5873 PEER_ATTR_INHERIT(peer, peer->group,
5874 filter[afi][safi].plist[direct].plist);
5875 } else {
5876 /* Otherwise remove configuration from peer. */
5877 filter = &peer->filter[afi][safi];
5878 if (filter->plist[direct].name)
5879 XFREE(MTYPE_BGP_FILTER_NAME,
5880 filter->plist[direct].name);
5881 filter->plist[direct].name = NULL;
5882 filter->plist[direct].plist = NULL;
5883 }
5884
5885 /* Check if handling a regular peer. */
5886 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
5887 /* Process peer route updates. */
5888 peer_on_policy_change(peer, afi, safi,
5889 (direct == FILTER_OUT) ? 1 : 0);
5890
5891 /* Skip peer-group mechanics for regular peers. */
5892 return 0;
5893 }
5894
5895 /*
5896 * Remove configuration on all peer-group members, unless they are
5897 * explicitely overriding peer-group configuration.
5898 */
5899 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
5900 /* Skip peers with overridden configuration. */
5901 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
5902 PEER_FT_PREFIX_LIST))
5903 continue;
5904
5905 /* Remove configuration on peer-group member. */
5906 filter = &member->filter[afi][safi];
5907 if (filter->plist[direct].name)
5908 XFREE(MTYPE_BGP_FILTER_NAME,
5909 filter->plist[direct].name);
5910 filter->plist[direct].name = NULL;
5911 filter->plist[direct].plist = NULL;
5912
5913 /* Process peer route updates. */
5914 peer_on_policy_change(member, afi, safi,
5915 (direct == FILTER_OUT) ? 1 : 0);
5916 }
5917
5918 return 0;
5919 }
5920
5921 /* Update prefix-list list. */
5922 static void peer_prefix_list_update(struct prefix_list *plist)
5923 {
5924 struct listnode *mnode, *mnnode;
5925 struct listnode *node, *nnode;
5926 struct bgp *bgp;
5927 struct peer *peer;
5928 struct peer_group *group;
5929 struct bgp_filter *filter;
5930 afi_t afi;
5931 safi_t safi;
5932 int direct;
5933
5934 for (ALL_LIST_ELEMENTS(bm->bgp, mnode, mnnode, bgp)) {
5935
5936 /*
5937 * Update the prefix-list on update groups.
5938 */
5939 update_group_policy_update(
5940 bgp, BGP_POLICY_PREFIX_LIST,
5941 plist ? prefix_list_name(plist) : NULL, 0, 0);
5942
5943 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
5944 FOREACH_AFI_SAFI (afi, safi) {
5945 filter = &peer->filter[afi][safi];
5946
5947 for (direct = FILTER_IN; direct < FILTER_MAX;
5948 direct++) {
5949 if (filter->plist[direct].name)
5950 filter->plist[direct]
5951 .plist = prefix_list_lookup(
5952 afi,
5953 filter->plist[direct]
5954 .name);
5955 else
5956 filter->plist[direct].plist =
5957 NULL;
5958 }
5959 }
5960 }
5961 for (ALL_LIST_ELEMENTS(bgp->group, node, nnode, group)) {
5962 FOREACH_AFI_SAFI (afi, safi) {
5963 filter = &group->conf->filter[afi][safi];
5964
5965 for (direct = FILTER_IN; direct < FILTER_MAX;
5966 direct++) {
5967 if (filter->plist[direct].name)
5968 filter->plist[direct]
5969 .plist = prefix_list_lookup(
5970 afi,
5971 filter->plist[direct]
5972 .name);
5973 else
5974 filter->plist[direct].plist =
5975 NULL;
5976 }
5977 }
5978 }
5979 }
5980 }
5981
5982 int peer_aslist_set(struct peer *peer, afi_t afi, safi_t safi, int direct,
5983 const char *name)
5984 {
5985 struct peer *member;
5986 struct bgp_filter *filter;
5987 struct listnode *node, *nnode;
5988
5989 if (direct != FILTER_IN && direct != FILTER_OUT)
5990 return BGP_ERR_INVALID_VALUE;
5991
5992 /* Set configuration on peer. */
5993 filter = &peer->filter[afi][safi];
5994 if (filter->aslist[direct].name)
5995 XFREE(MTYPE_BGP_FILTER_NAME, filter->aslist[direct].name);
5996 filter->aslist[direct].name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
5997 filter->aslist[direct].aslist = as_list_lookup(name);
5998
5999 /* Check if handling a regular peer. */
6000 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6001 /* Set override-flag and process peer route updates. */
6002 SET_FLAG(peer->filter_override[afi][safi][direct],
6003 PEER_FT_FILTER_LIST);
6004 peer_on_policy_change(peer, afi, safi,
6005 (direct == FILTER_OUT) ? 1 : 0);
6006
6007 /* Skip peer-group mechanics for regular peers. */
6008 return 0;
6009 }
6010
6011 /*
6012 * Set configuration on all peer-group members, unless they are
6013 * explicitely overriding peer-group configuration.
6014 */
6015 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
6016 /* Skip peers with overridden configuration. */
6017 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
6018 PEER_FT_FILTER_LIST))
6019 continue;
6020
6021 /* Set configuration on peer-group member. */
6022 filter = &member->filter[afi][safi];
6023 if (filter->aslist[direct].name)
6024 XFREE(MTYPE_BGP_FILTER_NAME,
6025 filter->aslist[direct].name);
6026 filter->aslist[direct].name =
6027 XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
6028 filter->aslist[direct].aslist = as_list_lookup(name);
6029
6030 /* Process peer route updates. */
6031 peer_on_policy_change(member, afi, safi,
6032 (direct == FILTER_OUT) ? 1 : 0);
6033 }
6034
6035 return 0;
6036 }
6037
6038 int peer_aslist_unset(struct peer *peer, afi_t afi, safi_t safi, int direct)
6039 {
6040 struct peer *member;
6041 struct bgp_filter *filter;
6042 struct listnode *node, *nnode;
6043
6044 if (direct != FILTER_IN && direct != FILTER_OUT)
6045 return BGP_ERR_INVALID_VALUE;
6046
6047 /* Unset override-flag unconditionally. */
6048 UNSET_FLAG(peer->filter_override[afi][safi][direct],
6049 PEER_FT_FILTER_LIST);
6050
6051 /* Inherit configuration from peer-group if peer is member. */
6052 if (peer_group_active(peer)) {
6053 PEER_STR_ATTR_INHERIT(peer, peer->group,
6054 filter[afi][safi].aslist[direct].name,
6055 MTYPE_BGP_FILTER_NAME);
6056 PEER_ATTR_INHERIT(peer, peer->group,
6057 filter[afi][safi].aslist[direct].aslist);
6058 } else {
6059 /* Otherwise remove configuration from peer. */
6060 filter = &peer->filter[afi][safi];
6061 if (filter->aslist[direct].name)
6062 XFREE(MTYPE_BGP_FILTER_NAME,
6063 filter->aslist[direct].name);
6064 filter->aslist[direct].name = NULL;
6065 filter->aslist[direct].aslist = NULL;
6066 }
6067
6068 /* Check if handling a regular peer. */
6069 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6070 /* Process peer route updates. */
6071 peer_on_policy_change(peer, afi, safi,
6072 (direct == FILTER_OUT) ? 1 : 0);
6073
6074 /* Skip peer-group mechanics for regular peers. */
6075 return 0;
6076 }
6077
6078 /*
6079 * Remove configuration on all peer-group members, unless they are
6080 * explicitely overriding peer-group configuration.
6081 */
6082 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
6083 /* Skip peers with overridden configuration. */
6084 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
6085 PEER_FT_FILTER_LIST))
6086 continue;
6087
6088 /* Remove configuration on peer-group member. */
6089 filter = &member->filter[afi][safi];
6090 if (filter->aslist[direct].name)
6091 XFREE(MTYPE_BGP_FILTER_NAME,
6092 filter->aslist[direct].name);
6093 filter->aslist[direct].name = NULL;
6094 filter->aslist[direct].aslist = NULL;
6095
6096 /* Process peer route updates. */
6097 peer_on_policy_change(member, afi, safi,
6098 (direct == FILTER_OUT) ? 1 : 0);
6099 }
6100
6101 return 0;
6102 }
6103
6104 static void peer_aslist_update(const char *aslist_name)
6105 {
6106 afi_t afi;
6107 safi_t safi;
6108 int direct;
6109 struct listnode *mnode, *mnnode;
6110 struct listnode *node, *nnode;
6111 struct bgp *bgp;
6112 struct peer *peer;
6113 struct peer_group *group;
6114 struct bgp_filter *filter;
6115
6116 for (ALL_LIST_ELEMENTS(bm->bgp, mnode, mnnode, bgp)) {
6117 update_group_policy_update(bgp, BGP_POLICY_FILTER_LIST,
6118 aslist_name, 0, 0);
6119
6120 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
6121 FOREACH_AFI_SAFI (afi, safi) {
6122 filter = &peer->filter[afi][safi];
6123
6124 for (direct = FILTER_IN; direct < FILTER_MAX;
6125 direct++) {
6126 if (filter->aslist[direct].name)
6127 filter->aslist[direct]
6128 .aslist = as_list_lookup(
6129 filter->aslist[direct]
6130 .name);
6131 else
6132 filter->aslist[direct].aslist =
6133 NULL;
6134 }
6135 }
6136 }
6137 for (ALL_LIST_ELEMENTS(bgp->group, node, nnode, group)) {
6138 FOREACH_AFI_SAFI (afi, safi) {
6139 filter = &group->conf->filter[afi][safi];
6140
6141 for (direct = FILTER_IN; direct < FILTER_MAX;
6142 direct++) {
6143 if (filter->aslist[direct].name)
6144 filter->aslist[direct]
6145 .aslist = as_list_lookup(
6146 filter->aslist[direct]
6147 .name);
6148 else
6149 filter->aslist[direct].aslist =
6150 NULL;
6151 }
6152 }
6153 }
6154 }
6155 }
6156
6157 static void peer_aslist_add(char *aslist_name)
6158 {
6159 peer_aslist_update(aslist_name);
6160 route_map_notify_dependencies((char *)aslist_name,
6161 RMAP_EVENT_ASLIST_ADDED);
6162 }
6163
6164 static void peer_aslist_del(const char *aslist_name)
6165 {
6166 peer_aslist_update(aslist_name);
6167 route_map_notify_dependencies(aslist_name, RMAP_EVENT_ASLIST_DELETED);
6168 }
6169
6170
6171 int peer_route_map_set(struct peer *peer, afi_t afi, safi_t safi, int direct,
6172 const char *name, struct route_map *route_map)
6173 {
6174 struct peer *member;
6175 struct bgp_filter *filter;
6176 struct listnode *node, *nnode;
6177
6178 if (direct != RMAP_IN && direct != RMAP_OUT)
6179 return BGP_ERR_INVALID_VALUE;
6180
6181 /* Set configuration on peer. */
6182 filter = &peer->filter[afi][safi];
6183 if (filter->map[direct].name) {
6184 /* If the neighbor is configured with the same route-map
6185 * again then, ignore the duplicate configuration.
6186 */
6187 if (strcmp(filter->map[direct].name, name) == 0)
6188 return 0;
6189
6190 XFREE(MTYPE_BGP_FILTER_NAME, filter->map[direct].name);
6191 }
6192 route_map_counter_decrement(filter->map[direct].map);
6193 filter->map[direct].name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
6194 filter->map[direct].map = route_map;
6195 route_map_counter_increment(route_map);
6196
6197 /* Check if handling a regular peer. */
6198 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6199 /* Set override-flag and process peer route updates. */
6200 SET_FLAG(peer->filter_override[afi][safi][direct],
6201 PEER_FT_ROUTE_MAP);
6202 peer_on_policy_change(peer, afi, safi,
6203 (direct == RMAP_OUT) ? 1 : 0);
6204
6205 /* Skip peer-group mechanics for regular peers. */
6206 return 0;
6207 }
6208
6209 /*
6210 * Set configuration on all peer-group members, unless they are
6211 * explicitely overriding peer-group configuration.
6212 */
6213 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
6214 /* Skip peers with overridden configuration. */
6215 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
6216 PEER_FT_ROUTE_MAP))
6217 continue;
6218
6219 /* Set configuration on peer-group member. */
6220 filter = &member->filter[afi][safi];
6221 if (filter->map[direct].name)
6222 XFREE(MTYPE_BGP_FILTER_NAME, filter->map[direct].name);
6223 route_map_counter_decrement(filter->map[direct].map);
6224 filter->map[direct].name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
6225 filter->map[direct].map = route_map;
6226 route_map_counter_increment(route_map);
6227
6228 /* Process peer route updates. */
6229 peer_on_policy_change(member, afi, safi,
6230 (direct == RMAP_OUT) ? 1 : 0);
6231 }
6232 return 0;
6233 }
6234
6235 /* Unset route-map from the peer. */
6236 int peer_route_map_unset(struct peer *peer, afi_t afi, safi_t safi, int direct)
6237 {
6238 struct peer *member;
6239 struct bgp_filter *filter;
6240 struct listnode *node, *nnode;
6241
6242 if (direct != RMAP_IN && direct != RMAP_OUT)
6243 return BGP_ERR_INVALID_VALUE;
6244
6245 /* Unset override-flag unconditionally. */
6246 UNSET_FLAG(peer->filter_override[afi][safi][direct], PEER_FT_ROUTE_MAP);
6247
6248 /* Inherit configuration from peer-group if peer is member. */
6249 if (peer_group_active(peer)) {
6250 PEER_STR_ATTR_INHERIT(peer, peer->group,
6251 filter[afi][safi].map[direct].name,
6252 MTYPE_BGP_FILTER_NAME);
6253 PEER_ATTR_INHERIT(peer, peer->group,
6254 filter[afi][safi].map[direct].map);
6255 } else {
6256 /* Otherwise remove configuration from peer. */
6257 filter = &peer->filter[afi][safi];
6258 if (filter->map[direct].name)
6259 XFREE(MTYPE_BGP_FILTER_NAME, filter->map[direct].name);
6260 route_map_counter_decrement(filter->map[direct].map);
6261 filter->map[direct].name = NULL;
6262 filter->map[direct].map = NULL;
6263 }
6264
6265 /* Check if handling a regular peer. */
6266 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6267 /* Process peer route updates. */
6268 peer_on_policy_change(peer, afi, safi,
6269 (direct == RMAP_OUT) ? 1 : 0);
6270
6271 /* Skip peer-group mechanics for regular peers. */
6272 return 0;
6273 }
6274
6275 /*
6276 * Remove configuration on all peer-group members, unless they are
6277 * explicitely overriding peer-group configuration.
6278 */
6279 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
6280 /* Skip peers with overridden configuration. */
6281 if (CHECK_FLAG(member->filter_override[afi][safi][direct],
6282 PEER_FT_ROUTE_MAP))
6283 continue;
6284
6285 /* Remove configuration on peer-group member. */
6286 filter = &member->filter[afi][safi];
6287 if (filter->map[direct].name)
6288 XFREE(MTYPE_BGP_FILTER_NAME, filter->map[direct].name);
6289 route_map_counter_decrement(filter->map[direct].map);
6290 filter->map[direct].name = NULL;
6291 filter->map[direct].map = NULL;
6292
6293 /* Process peer route updates. */
6294 peer_on_policy_change(member, afi, safi,
6295 (direct == RMAP_OUT) ? 1 : 0);
6296 }
6297
6298 return 0;
6299 }
6300
6301 /* Set unsuppress-map to the peer. */
6302 int peer_unsuppress_map_set(struct peer *peer, afi_t afi, safi_t safi,
6303 const char *name, struct route_map *route_map)
6304 {
6305 struct peer *member;
6306 struct bgp_filter *filter;
6307 struct listnode *node, *nnode;
6308
6309 /* Set configuration on peer. */
6310 filter = &peer->filter[afi][safi];
6311 if (filter->usmap.name)
6312 XFREE(MTYPE_BGP_FILTER_NAME, filter->usmap.name);
6313 route_map_counter_decrement(filter->usmap.map);
6314 filter->usmap.name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
6315 filter->usmap.map = route_map;
6316 route_map_counter_increment(route_map);
6317
6318 /* Check if handling a regular peer. */
6319 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6320 /* Set override-flag and process peer route updates. */
6321 SET_FLAG(peer->filter_override[afi][safi][0],
6322 PEER_FT_UNSUPPRESS_MAP);
6323 peer_on_policy_change(peer, afi, safi, 1);
6324
6325 /* Skip peer-group mechanics for regular peers. */
6326 return 0;
6327 }
6328
6329 /*
6330 * Set configuration on all peer-group members, unless they are
6331 * explicitely overriding peer-group configuration.
6332 */
6333 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
6334 /* Skip peers with overridden configuration. */
6335 if (CHECK_FLAG(member->filter_override[afi][safi][0],
6336 PEER_FT_UNSUPPRESS_MAP))
6337 continue;
6338
6339 /* Set configuration on peer-group member. */
6340 filter = &member->filter[afi][safi];
6341 if (filter->usmap.name)
6342 XFREE(MTYPE_BGP_FILTER_NAME, filter->usmap.name);
6343 route_map_counter_decrement(filter->usmap.map);
6344 filter->usmap.name = XSTRDUP(MTYPE_BGP_FILTER_NAME, name);
6345 filter->usmap.map = route_map;
6346 route_map_counter_increment(route_map);
6347
6348 /* Process peer route updates. */
6349 peer_on_policy_change(member, afi, safi, 1);
6350 }
6351
6352 return 0;
6353 }
6354
6355 /* Unset route-map from the peer. */
6356 int peer_unsuppress_map_unset(struct peer *peer, afi_t afi, safi_t safi)
6357 {
6358 struct peer *member;
6359 struct bgp_filter *filter;
6360 struct listnode *node, *nnode;
6361
6362 /* Unset override-flag unconditionally. */
6363 UNSET_FLAG(peer->filter_override[afi][safi][0], PEER_FT_UNSUPPRESS_MAP);
6364
6365 /* Inherit configuration from peer-group if peer is member. */
6366 if (peer_group_active(peer)) {
6367 PEER_STR_ATTR_INHERIT(peer, peer->group,
6368 filter[afi][safi].usmap.name,
6369 MTYPE_BGP_FILTER_NAME);
6370 PEER_ATTR_INHERIT(peer, peer->group,
6371 filter[afi][safi].usmap.map);
6372 } else {
6373 /* Otherwise remove configuration from peer. */
6374 filter = &peer->filter[afi][safi];
6375 if (filter->usmap.name)
6376 XFREE(MTYPE_BGP_FILTER_NAME, filter->usmap.name);
6377 route_map_counter_decrement(filter->usmap.map);
6378 filter->usmap.name = NULL;
6379 filter->usmap.map = NULL;
6380 }
6381
6382 /* Check if handling a regular peer. */
6383 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6384 /* Process peer route updates. */
6385 peer_on_policy_change(peer, afi, safi, 1);
6386
6387 /* Skip peer-group mechanics for regular peers. */
6388 return 0;
6389 }
6390
6391 /*
6392 * Remove configuration on all peer-group members, unless they are
6393 * explicitely overriding peer-group configuration.
6394 */
6395 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
6396 /* Skip peers with overridden configuration. */
6397 if (CHECK_FLAG(member->filter_override[afi][safi][0],
6398 PEER_FT_UNSUPPRESS_MAP))
6399 continue;
6400
6401 /* Remove configuration on peer-group member. */
6402 filter = &member->filter[afi][safi];
6403 if (filter->usmap.name)
6404 XFREE(MTYPE_BGP_FILTER_NAME, filter->usmap.name);
6405 route_map_counter_decrement(filter->usmap.map);
6406 filter->usmap.name = NULL;
6407 filter->usmap.map = NULL;
6408
6409 /* Process peer route updates. */
6410 peer_on_policy_change(member, afi, safi, 1);
6411 }
6412
6413 return 0;
6414 }
6415
6416 int peer_maximum_prefix_set(struct peer *peer, afi_t afi, safi_t safi,
6417 uint32_t max, uint8_t threshold, int warning,
6418 uint16_t restart)
6419 {
6420 struct peer *member;
6421 struct listnode *node, *nnode;
6422
6423 /* Set flags and configuration on peer. */
6424 peer_af_flag_set(peer, afi, safi, PEER_FLAG_MAX_PREFIX);
6425 if (warning)
6426 peer_af_flag_set(peer, afi, safi, PEER_FLAG_MAX_PREFIX_WARNING);
6427 else
6428 peer_af_flag_unset(peer, afi, safi,
6429 PEER_FLAG_MAX_PREFIX_WARNING);
6430
6431 peer->pmax[afi][safi] = max;
6432 peer->pmax_threshold[afi][safi] = threshold;
6433 peer->pmax_restart[afi][safi] = restart;
6434
6435 /* Check if handling a regular peer. */
6436 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6437 /* Re-check if peer violates maximum-prefix. */
6438 if ((peer->status == Established) && (peer->afc[afi][safi]))
6439 bgp_maximum_prefix_overflow(peer, afi, safi, 1);
6440
6441 /* Skip peer-group mechanics for regular peers. */
6442 return 0;
6443 }
6444
6445 /*
6446 * Set flags and configuration on all peer-group members, unless they
6447 * are explicitely overriding peer-group configuration.
6448 */
6449 for (ALL_LIST_ELEMENTS(peer->group->peer, node, nnode, member)) {
6450 /* Skip peers with overridden configuration. */
6451 if (CHECK_FLAG(member->af_flags_override[afi][safi],
6452 PEER_FLAG_MAX_PREFIX))
6453 continue;
6454
6455 /* Set flag and configuration on peer-group member. */
6456 member->pmax[afi][safi] = max;
6457 member->pmax_threshold[afi][safi] = threshold;
6458 member->pmax_restart[afi][safi] = restart;
6459 if (warning)
6460 SET_FLAG(member->af_flags[afi][safi],
6461 PEER_FLAG_MAX_PREFIX_WARNING);
6462 else
6463 UNSET_FLAG(member->af_flags[afi][safi],
6464 PEER_FLAG_MAX_PREFIX_WARNING);
6465
6466 /* Re-check if peer violates maximum-prefix. */
6467 if ((member->status == Established) && (member->afc[afi][safi]))
6468 bgp_maximum_prefix_overflow(member, afi, safi, 1);
6469 }
6470
6471 return 0;
6472 }
6473
6474 int peer_maximum_prefix_unset(struct peer *peer, afi_t afi, safi_t safi)
6475 {
6476 /* Inherit configuration from peer-group if peer is member. */
6477 if (peer_group_active(peer)) {
6478 peer_af_flag_inherit(peer, afi, safi, PEER_FLAG_MAX_PREFIX);
6479 peer_af_flag_inherit(peer, afi, safi,
6480 PEER_FLAG_MAX_PREFIX_WARNING);
6481 PEER_ATTR_INHERIT(peer, peer->group, pmax[afi][safi]);
6482 PEER_ATTR_INHERIT(peer, peer->group, pmax_threshold[afi][safi]);
6483 PEER_ATTR_INHERIT(peer, peer->group, pmax_restart[afi][safi]);
6484
6485 return 0;
6486 }
6487
6488 /* Remove flags and configuration from peer. */
6489 peer_af_flag_unset(peer, afi, safi, PEER_FLAG_MAX_PREFIX);
6490 peer_af_flag_unset(peer, afi, safi, PEER_FLAG_MAX_PREFIX_WARNING);
6491 peer->pmax[afi][safi] = 0;
6492 peer->pmax_threshold[afi][safi] = 0;
6493 peer->pmax_restart[afi][safi] = 0;
6494
6495 /*
6496 * Remove flags and configuration from all peer-group members, unless
6497 * they are explicitely overriding peer-group configuration.
6498 */
6499 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6500 struct peer *member;
6501 struct listnode *node;
6502
6503 for (ALL_LIST_ELEMENTS_RO(peer->group->peer, node, member)) {
6504 /* Skip peers with overridden configuration. */
6505 if (CHECK_FLAG(member->af_flags_override[afi][safi],
6506 PEER_FLAG_MAX_PREFIX))
6507 continue;
6508
6509 /* Remove flag and configuration on peer-group member.
6510 */
6511 UNSET_FLAG(member->af_flags[afi][safi],
6512 PEER_FLAG_MAX_PREFIX);
6513 UNSET_FLAG(member->af_flags[afi][safi],
6514 PEER_FLAG_MAX_PREFIX_WARNING);
6515 member->pmax[afi][safi] = 0;
6516 member->pmax_threshold[afi][safi] = 0;
6517 member->pmax_restart[afi][safi] = 0;
6518 }
6519 }
6520
6521 return 0;
6522 }
6523
6524 int is_ebgp_multihop_configured(struct peer *peer)
6525 {
6526 struct peer_group *group;
6527 struct listnode *node, *nnode;
6528 struct peer *peer1;
6529
6530 if (CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6531 group = peer->group;
6532 if ((peer_sort(peer) != BGP_PEER_IBGP)
6533 && (group->conf->ttl != BGP_DEFAULT_TTL))
6534 return 1;
6535
6536 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer1)) {
6537 if ((peer_sort(peer1) != BGP_PEER_IBGP)
6538 && (peer1->ttl != BGP_DEFAULT_TTL))
6539 return 1;
6540 }
6541 } else {
6542 if ((peer_sort(peer) != BGP_PEER_IBGP)
6543 && (peer->ttl != BGP_DEFAULT_TTL))
6544 return 1;
6545 }
6546 return 0;
6547 }
6548
6549 /* Set # of hops between us and BGP peer. */
6550 int peer_ttl_security_hops_set(struct peer *peer, int gtsm_hops)
6551 {
6552 struct peer_group *group;
6553 struct listnode *node, *nnode;
6554 int ret;
6555
6556 zlog_debug("peer_ttl_security_hops_set: set gtsm_hops to %d for %s",
6557 gtsm_hops, peer->host);
6558
6559 /* We cannot configure ttl-security hops when ebgp-multihop is already
6560 set. For non peer-groups, the check is simple. For peer-groups,
6561 it's
6562 slightly messy, because we need to check both the peer-group
6563 structure
6564 and all peer-group members for any trace of ebgp-multihop
6565 configuration
6566 before actually applying the ttl-security rules. Cisco really made a
6567 mess of this configuration parameter, and OpenBGPD got it right.
6568 */
6569
6570 if ((peer->gtsm_hops == 0) && (peer->sort != BGP_PEER_IBGP)) {
6571 if (is_ebgp_multihop_configured(peer))
6572 return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
6573
6574 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6575 peer->gtsm_hops = gtsm_hops;
6576
6577 /* Calling ebgp multihop also resets the session.
6578 * On restart, NHT will get setup correctly as will the
6579 * min & max ttls on the socket. The return value is
6580 * irrelevant.
6581 */
6582 ret = peer_ebgp_multihop_set(peer, MAXTTL);
6583
6584 if (ret != 0)
6585 return ret;
6586 } else {
6587 group = peer->group;
6588 for (ALL_LIST_ELEMENTS(group->peer, node, nnode,
6589 peer)) {
6590 peer->gtsm_hops = group->conf->gtsm_hops;
6591
6592 /* Calling ebgp multihop also resets the
6593 * session.
6594 * On restart, NHT will get setup correctly as
6595 * will the
6596 * min & max ttls on the socket. The return
6597 * value is
6598 * irrelevant.
6599 */
6600 peer_ebgp_multihop_set(peer, MAXTTL);
6601 }
6602 }
6603 } else {
6604 /* Post the first gtsm setup or if its ibgp, maxttl setting
6605 * isn't
6606 * necessary, just set the minttl.
6607 */
6608 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6609 peer->gtsm_hops = gtsm_hops;
6610
6611 if (peer->fd >= 0)
6612 sockopt_minttl(peer->su.sa.sa_family, peer->fd,
6613 MAXTTL + 1 - gtsm_hops);
6614 if ((peer->status < Established) && peer->doppelganger
6615 && (peer->doppelganger->fd >= 0))
6616 sockopt_minttl(peer->su.sa.sa_family,
6617 peer->doppelganger->fd,
6618 MAXTTL + 1 - gtsm_hops);
6619 } else {
6620 group = peer->group;
6621 for (ALL_LIST_ELEMENTS(group->peer, node, nnode,
6622 peer)) {
6623 peer->gtsm_hops = group->conf->gtsm_hops;
6624
6625 /* Change setting of existing peer
6626 * established then change value (may break
6627 * connectivity)
6628 * not established yet (teardown session and
6629 * restart)
6630 * no session then do nothing (will get
6631 * handled by next connection)
6632 */
6633 if (peer->fd >= 0 && peer->gtsm_hops != 0)
6634 sockopt_minttl(
6635 peer->su.sa.sa_family, peer->fd,
6636 MAXTTL + 1 - peer->gtsm_hops);
6637 if ((peer->status < Established)
6638 && peer->doppelganger
6639 && (peer->doppelganger->fd >= 0))
6640 sockopt_minttl(peer->su.sa.sa_family,
6641 peer->doppelganger->fd,
6642 MAXTTL + 1 - gtsm_hops);
6643 }
6644 }
6645 }
6646
6647 return 0;
6648 }
6649
6650 int peer_ttl_security_hops_unset(struct peer *peer)
6651 {
6652 struct peer_group *group;
6653 struct listnode *node, *nnode;
6654 int ret = 0;
6655
6656 zlog_debug("peer_ttl_security_hops_unset: set gtsm_hops to zero for %s",
6657 peer->host);
6658
6659 /* if a peer-group member, then reset to peer-group default rather than
6660 * 0 */
6661 if (peer_group_active(peer))
6662 peer->gtsm_hops = peer->group->conf->gtsm_hops;
6663 else
6664 peer->gtsm_hops = 0;
6665
6666 if (!CHECK_FLAG(peer->sflags, PEER_STATUS_GROUP)) {
6667 /* Invoking ebgp_multihop_set will set the TTL back to the
6668 * original
6669 * value as well as restting the NHT and such. The session is
6670 * reset.
6671 */
6672 if (peer->sort == BGP_PEER_EBGP)
6673 ret = peer_ebgp_multihop_unset(peer);
6674 else {
6675 if (peer->fd >= 0)
6676 sockopt_minttl(peer->su.sa.sa_family, peer->fd,
6677 0);
6678
6679 if ((peer->status < Established) && peer->doppelganger
6680 && (peer->doppelganger->fd >= 0))
6681 sockopt_minttl(peer->su.sa.sa_family,
6682 peer->doppelganger->fd, 0);
6683 }
6684 } else {
6685 group = peer->group;
6686 for (ALL_LIST_ELEMENTS(group->peer, node, nnode, peer)) {
6687 peer->gtsm_hops = 0;
6688 if (peer->sort == BGP_PEER_EBGP)
6689 ret = peer_ebgp_multihop_unset(peer);
6690 else {
6691 if (peer->fd >= 0)
6692 sockopt_minttl(peer->su.sa.sa_family,
6693 peer->fd, 0);
6694
6695 if ((peer->status < Established)
6696 && peer->doppelganger
6697 && (peer->doppelganger->fd >= 0))
6698 sockopt_minttl(peer->su.sa.sa_family,
6699 peer->doppelganger->fd,
6700 0);
6701 }
6702 }
6703 }
6704
6705 return ret;
6706 }
6707
6708 /*
6709 * If peer clear is invoked in a loop for all peers on the BGP instance,
6710 * it may end up freeing the doppelganger, and if this was the next node
6711 * to the current node, we would end up accessing the freed next node.
6712 * Pass along additional parameter which can be updated if next node
6713 * is freed; only required when walking the peer list on BGP instance.
6714 */
6715 int peer_clear(struct peer *peer, struct listnode **nnode)
6716 {
6717 if (!CHECK_FLAG(peer->flags, PEER_FLAG_SHUTDOWN)) {
6718 if (CHECK_FLAG(peer->sflags, PEER_STATUS_PREFIX_OVERFLOW)) {
6719 UNSET_FLAG(peer->sflags, PEER_STATUS_PREFIX_OVERFLOW);
6720 if (peer->t_pmax_restart) {
6721 BGP_TIMER_OFF(peer->t_pmax_restart);
6722 if (bgp_debug_neighbor_events(peer))
6723 zlog_debug(
6724 "%s Maximum-prefix restart timer canceled",
6725 peer->host);
6726 }
6727 BGP_EVENT_ADD(peer, BGP_Start);
6728 return 0;
6729 }
6730
6731 peer->v_start = BGP_INIT_START_TIMER;
6732 if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
6733 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
6734 BGP_NOTIFY_CEASE_ADMIN_RESET);
6735 else
6736 bgp_session_reset_safe(peer, nnode);
6737 }
6738 return 0;
6739 }
6740
6741 int peer_clear_soft(struct peer *peer, afi_t afi, safi_t safi,
6742 enum bgp_clear_type stype)
6743 {
6744 struct peer_af *paf;
6745
6746 if (peer->status != Established)
6747 return 0;
6748
6749 if (!peer->afc[afi][safi])
6750 return BGP_ERR_AF_UNCONFIGURED;
6751
6752 peer->rtt = sockopt_tcp_rtt(peer->fd);
6753
6754 if (stype == BGP_CLEAR_SOFT_OUT || stype == BGP_CLEAR_SOFT_BOTH) {
6755 /* Clear the "neighbor x.x.x.x default-originate" flag */
6756 paf = peer_af_find(peer, afi, safi);
6757 if (paf && paf->subgroup
6758 && CHECK_FLAG(paf->subgroup->sflags,
6759 SUBGRP_STATUS_DEFAULT_ORIGINATE))
6760 UNSET_FLAG(paf->subgroup->sflags,
6761 SUBGRP_STATUS_DEFAULT_ORIGINATE);
6762
6763 bgp_announce_route(peer, afi, safi);
6764 }
6765
6766 if (stype == BGP_CLEAR_SOFT_IN_ORF_PREFIX) {
6767 if (CHECK_FLAG(peer->af_cap[afi][safi],
6768 PEER_CAP_ORF_PREFIX_SM_ADV)
6769 && (CHECK_FLAG(peer->af_cap[afi][safi],
6770 PEER_CAP_ORF_PREFIX_RM_RCV)
6771 || CHECK_FLAG(peer->af_cap[afi][safi],
6772 PEER_CAP_ORF_PREFIX_RM_OLD_RCV))) {
6773 struct bgp_filter *filter = &peer->filter[afi][safi];
6774 uint8_t prefix_type;
6775
6776 if (CHECK_FLAG(peer->af_cap[afi][safi],
6777 PEER_CAP_ORF_PREFIX_RM_RCV))
6778 prefix_type = ORF_TYPE_PREFIX;
6779 else
6780 prefix_type = ORF_TYPE_PREFIX_OLD;
6781
6782 if (filter->plist[FILTER_IN].plist) {
6783 if (CHECK_FLAG(peer->af_sflags[afi][safi],
6784 PEER_STATUS_ORF_PREFIX_SEND))
6785 bgp_route_refresh_send(
6786 peer, afi, safi, prefix_type,
6787 REFRESH_DEFER, 1);
6788 bgp_route_refresh_send(peer, afi, safi,
6789 prefix_type,
6790 REFRESH_IMMEDIATE, 0);
6791 } else {
6792 if (CHECK_FLAG(peer->af_sflags[afi][safi],
6793 PEER_STATUS_ORF_PREFIX_SEND))
6794 bgp_route_refresh_send(
6795 peer, afi, safi, prefix_type,
6796 REFRESH_IMMEDIATE, 1);
6797 else
6798 bgp_route_refresh_send(peer, afi, safi,
6799 0, 0, 0);
6800 }
6801 return 0;
6802 }
6803 }
6804
6805 if (stype == BGP_CLEAR_SOFT_IN || stype == BGP_CLEAR_SOFT_BOTH
6806 || stype == BGP_CLEAR_SOFT_IN_ORF_PREFIX) {
6807 /* If neighbor has soft reconfiguration inbound flag.
6808 Use Adj-RIB-In database. */
6809 if (CHECK_FLAG(peer->af_flags[afi][safi],
6810 PEER_FLAG_SOFT_RECONFIG))
6811 bgp_soft_reconfig_in(peer, afi, safi);
6812 else {
6813 /* If neighbor has route refresh capability, send route
6814 refresh
6815 message to the peer. */
6816 if (CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_OLD_RCV)
6817 || CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_NEW_RCV))
6818 bgp_route_refresh_send(peer, afi, safi, 0, 0,
6819 0);
6820 else
6821 return BGP_ERR_SOFT_RECONFIG_UNCONFIGURED;
6822 }
6823 }
6824 return 0;
6825 }
6826
6827 /* Display peer uptime.*/
6828 char *peer_uptime(time_t uptime2, char *buf, size_t len, bool use_json,
6829 json_object *json)
6830 {
6831 time_t uptime1, epoch_tbuf;
6832 struct tm *tm;
6833
6834 /* If there is no connection has been done before print `never'. */
6835 if (uptime2 == 0) {
6836 if (use_json) {
6837 json_object_string_add(json, "peerUptime", "never");
6838 json_object_int_add(json, "peerUptimeMsec", 0);
6839 } else
6840 snprintf(buf, len, "never");
6841 return buf;
6842 }
6843
6844 /* Get current time. */
6845 uptime1 = bgp_clock();
6846 uptime1 -= uptime2;
6847 tm = gmtime(&uptime1);
6848
6849 if (uptime1 < ONE_DAY_SECOND)
6850 snprintf(buf, len, "%02d:%02d:%02d", tm->tm_hour, tm->tm_min,
6851 tm->tm_sec);
6852 else if (uptime1 < ONE_WEEK_SECOND)
6853 snprintf(buf, len, "%dd%02dh%02dm", tm->tm_yday, tm->tm_hour,
6854 tm->tm_min);
6855 else if (uptime1 < ONE_YEAR_SECOND)
6856 snprintf(buf, len, "%02dw%dd%02dh", tm->tm_yday / 7,
6857 tm->tm_yday - ((tm->tm_yday / 7) * 7), tm->tm_hour);
6858 else
6859 snprintf(buf, len, "%02dy%02dw%dd", tm->tm_year - 70,
6860 tm->tm_yday / 7,
6861 tm->tm_yday - ((tm->tm_yday / 7) * 7));
6862
6863 if (use_json) {
6864 epoch_tbuf = time(NULL) - uptime1;
6865 json_object_string_add(json, "peerUptime", buf);
6866 json_object_int_add(json, "peerUptimeMsec", uptime1 * 1000);
6867 json_object_int_add(json, "peerUptimeEstablishedEpoch",
6868 epoch_tbuf);
6869 }
6870
6871 return buf;
6872 }
6873
6874 void bgp_master_init(struct thread_master *master, const int buffer_size)
6875 {
6876 qobj_init();
6877
6878 memset(&bgp_master, 0, sizeof(struct bgp_master));
6879
6880 bm = &bgp_master;
6881 bm->bgp = list_new();
6882 bm->listen_sockets = list_new();
6883 bm->port = BGP_PORT_DEFAULT;
6884 bm->master = master;
6885 bm->start_time = bgp_clock();
6886 bm->t_rmap_update = NULL;
6887 bm->rmap_update_timer = RMAP_DEFAULT_UPDATE_TIMER;
6888 bm->terminating = false;
6889 bm->socket_buffer = buffer_size;
6890
6891 bgp_process_queue_init();
6892
6893 bgp_mac_init();
6894 /* init the rd id space.
6895 assign 0th index in the bitfield,
6896 so that we start with id 1
6897 */
6898 bf_init(bm->rd_idspace, UINT16_MAX);
6899 bf_assign_zero_index(bm->rd_idspace);
6900
6901 /* mpls label dynamic allocation pool */
6902 bgp_lp_init(bm->master, &bm->labelpool);
6903
6904 QOBJ_REG(bm, bgp_master);
6905 }
6906
6907 /*
6908 * Free up connected routes and interfaces for a BGP instance. Invoked upon
6909 * instance delete (non-default only) or BGP exit.
6910 */
6911 static void bgp_if_finish(struct bgp *bgp)
6912 {
6913 struct vrf *vrf;
6914 struct interface *ifp;
6915
6916 vrf = bgp_vrf_lookup_by_instance_type(bgp);
6917
6918 if (bgp->inst_type == BGP_INSTANCE_TYPE_VIEW || !vrf)
6919 return;
6920
6921 FOR_ALL_INTERFACES (vrf, ifp) {
6922 struct listnode *c_node, *c_nnode;
6923 struct connected *c;
6924
6925 for (ALL_LIST_ELEMENTS(ifp->connected, c_node, c_nnode, c))
6926 bgp_connected_delete(bgp, c);
6927 }
6928 }
6929
6930 static void bgp_viewvrf_autocomplete(vector comps, struct cmd_token *token)
6931 {
6932 struct vrf *vrf = NULL;
6933 struct listnode *next;
6934 struct bgp *bgp;
6935
6936 RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name)
6937 vector_set(comps, XSTRDUP(MTYPE_COMPLETION, vrf->name));
6938
6939 for (ALL_LIST_ELEMENTS_RO(bm->bgp, next, bgp)) {
6940 if (bgp->inst_type != BGP_INSTANCE_TYPE_VIEW)
6941 continue;
6942
6943 vector_set(comps, XSTRDUP(MTYPE_COMPLETION, bgp->name));
6944 }
6945 }
6946
6947 static void bgp_instasn_autocomplete(vector comps, struct cmd_token *token)
6948 {
6949 struct listnode *next, *next2;
6950 struct bgp *bgp, *bgp2;
6951 char buf[11];
6952
6953 for (ALL_LIST_ELEMENTS_RO(bm->bgp, next, bgp)) {
6954 /* deduplicate */
6955 for (ALL_LIST_ELEMENTS_RO(bm->bgp, next2, bgp2)) {
6956 if (bgp2->as == bgp->as)
6957 break;
6958 if (bgp2 == bgp)
6959 break;
6960 }
6961 if (bgp2 != bgp)
6962 continue;
6963
6964 snprintf(buf, sizeof(buf), "%u", bgp->as);
6965 vector_set(comps, XSTRDUP(MTYPE_COMPLETION, buf));
6966 }
6967 }
6968
6969 static const struct cmd_variable_handler bgp_viewvrf_var_handlers[] = {
6970 {.tokenname = "VIEWVRFNAME", .completions = bgp_viewvrf_autocomplete},
6971 {.varname = "instasn", .completions = bgp_instasn_autocomplete},
6972 {.completions = NULL},
6973 };
6974
6975 struct frr_pthread *bgp_pth_io;
6976 struct frr_pthread *bgp_pth_ka;
6977
6978 static void bgp_pthreads_init(void)
6979 {
6980 assert(!bgp_pth_io);
6981 assert(!bgp_pth_ka);
6982
6983 struct frr_pthread_attr io = {
6984 .start = frr_pthread_attr_default.start,
6985 .stop = frr_pthread_attr_default.stop,
6986 };
6987 struct frr_pthread_attr ka = {
6988 .start = bgp_keepalives_start,
6989 .stop = bgp_keepalives_stop,
6990 };
6991 bgp_pth_io = frr_pthread_new(&io, "BGP I/O thread", "bgpd_io");
6992 bgp_pth_ka = frr_pthread_new(&ka, "BGP Keepalives thread", "bgpd_ka");
6993 }
6994
6995 void bgp_pthreads_run(void)
6996 {
6997 frr_pthread_run(bgp_pth_io, NULL);
6998 frr_pthread_run(bgp_pth_ka, NULL);
6999
7000 /* Wait until threads are ready. */
7001 frr_pthread_wait_running(bgp_pth_io);
7002 frr_pthread_wait_running(bgp_pth_ka);
7003 }
7004
7005 void bgp_pthreads_finish(void)
7006 {
7007 frr_pthread_stop_all();
7008 }
7009
7010 void bgp_init(unsigned short instance)
7011 {
7012
7013 /* allocates some vital data structures used by peer commands in
7014 * vty_init */
7015
7016 /* pre-init pthreads */
7017 bgp_pthreads_init();
7018
7019 /* Init zebra. */
7020 bgp_zebra_init(bm->master, instance);
7021
7022 #if ENABLE_BGP_VNC
7023 vnc_zebra_init(bm->master);
7024 #endif
7025
7026 /* BGP VTY commands installation. */
7027 bgp_vty_init();
7028
7029 /* BGP inits. */
7030 bgp_attr_init();
7031 bgp_debug_init();
7032 bgp_dump_init();
7033 bgp_route_init();
7034 bgp_route_map_init();
7035 bgp_scan_vty_init();
7036 bgp_mplsvpn_init();
7037 #if ENABLE_BGP_VNC
7038 rfapi_init();
7039 #endif
7040 bgp_ethernetvpn_init();
7041 bgp_flowspec_vty_init();
7042
7043 /* Access list initialize. */
7044 access_list_init();
7045 access_list_add_hook(peer_distribute_update);
7046 access_list_delete_hook(peer_distribute_update);
7047
7048 /* Filter list initialize. */
7049 bgp_filter_init();
7050 as_list_add_hook(peer_aslist_add);
7051 as_list_delete_hook(peer_aslist_del);
7052
7053 /* Prefix list initialize.*/
7054 prefix_list_init();
7055 prefix_list_add_hook(peer_prefix_list_update);
7056 prefix_list_delete_hook(peer_prefix_list_update);
7057
7058 /* Community list initialize. */
7059 bgp_clist = community_list_init();
7060
7061 /* BFD init */
7062 bgp_bfd_init();
7063
7064 cmd_variable_handler_register(bgp_viewvrf_var_handlers);
7065 }
7066
7067 void bgp_terminate(void)
7068 {
7069 struct bgp *bgp;
7070 struct peer *peer;
7071 struct listnode *node, *nnode;
7072 struct listnode *mnode, *mnnode;
7073
7074 QOBJ_UNREG(bm);
7075
7076 /* Close the listener sockets first as this prevents peers from
7077 * attempting
7078 * to reconnect on receiving the peer unconfig message. In the presence
7079 * of a large number of peers this will ensure that no peer is left with
7080 * a dangling connection
7081 */
7082 /* reverse bgp_master_init */
7083 bgp_close();
7084
7085 if (bm->listen_sockets)
7086 list_delete(&bm->listen_sockets);
7087
7088 for (ALL_LIST_ELEMENTS(bm->bgp, mnode, mnnode, bgp))
7089 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer))
7090 if (peer->status == Established
7091 || peer->status == OpenSent
7092 || peer->status == OpenConfirm)
7093 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
7094 BGP_NOTIFY_CEASE_PEER_UNCONFIG);
7095
7096 if (bm->process_main_queue)
7097 work_queue_free_and_null(&bm->process_main_queue);
7098
7099 if (bm->t_rmap_update)
7100 BGP_TIMER_OFF(bm->t_rmap_update);
7101
7102 bgp_mac_finish();
7103 }
7104
7105 struct peer *peer_lookup_in_view(struct vty *vty, struct bgp *bgp,
7106 const char *ip_str, bool use_json)
7107 {
7108 int ret;
7109 struct peer *peer;
7110 union sockunion su;
7111
7112 /* Get peer sockunion. */
7113 ret = str2sockunion(ip_str, &su);
7114 if (ret < 0) {
7115 peer = peer_lookup_by_conf_if(bgp, ip_str);
7116 if (!peer) {
7117 peer = peer_lookup_by_hostname(bgp, ip_str);
7118
7119 if (!peer) {
7120 if (use_json) {
7121 json_object *json_no = NULL;
7122 json_no = json_object_new_object();
7123 json_object_string_add(
7124 json_no,
7125 "malformedAddressOrName",
7126 ip_str);
7127 vty_out(vty, "%s\n",
7128 json_object_to_json_string_ext(
7129 json_no,
7130 JSON_C_TO_STRING_PRETTY));
7131 json_object_free(json_no);
7132 } else
7133 vty_out(vty,
7134 "%% Malformed address or name: %s\n",
7135 ip_str);
7136 return NULL;
7137 }
7138 }
7139 return peer;
7140 }
7141
7142 /* Peer structure lookup. */
7143 peer = peer_lookup(bgp, &su);
7144 if (!peer) {
7145 if (use_json) {
7146 json_object *json_no = NULL;
7147 json_no = json_object_new_object();
7148 json_object_string_add(json_no, "warning",
7149 "No such neighbor in this view/vrf");
7150 vty_out(vty, "%s\n",
7151 json_object_to_json_string_ext(
7152 json_no, JSON_C_TO_STRING_PRETTY));
7153 json_object_free(json_no);
7154 } else
7155 vty_out(vty, "No such neighbor in this view/vrf\n");
7156 return NULL;
7157 }
7158
7159 return peer;
7160 }
7161
7162 void bgp_gr_apply_running_config(void)
7163 {
7164 struct peer *peer = NULL;
7165 struct bgp *bgp = NULL;
7166 struct listnode *node, *nnode;
7167 bool gr_router_detected = false;
7168
7169 if (BGP_DEBUG(graceful_restart, GRACEFUL_RESTART))
7170 zlog_debug("[BGP_GR] %s called !", __func__);
7171
7172 for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp)) {
7173 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
7174 bgp_peer_gr_flags_update(peer);
7175 if (CHECK_FLAG(peer->flags, PEER_FLAG_GRACEFUL_RESTART))
7176 gr_router_detected = true;
7177 }
7178
7179 if (gr_router_detected
7180 && bgp->present_zebra_gr_state == ZEBRA_GR_DISABLE) {
7181 bgp_zebra_send_capabilities(bgp, true);
7182 } else if (!gr_router_detected
7183 && bgp->present_zebra_gr_state == ZEBRA_GR_ENABLE) {
7184 bgp_zebra_send_capabilities(bgp, false);
7185 }
7186
7187 gr_router_detected = false;
7188 }
7189 }