]> git.proxmox.com Git - mirror_frr.git/blame - bgpd/bgp_main.c
bgpd: [7.1] Strip `delete` keyword when looking up for lcommuni… (#4786)
[mirror_frr.git] / bgpd / bgp_main.c
CommitLineData
718e3744 1/* Main routine of bgpd.
896014f4
DL
2 * Copyright (C) 1996, 97, 98, 1999 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 */
718e3744 20
21#include <zebra.h>
22
03014d48 23#include <pthread.h>
718e3744 24#include "vector.h"
718e3744 25#include "command.h"
26#include "getopt.h"
27#include "thread.h"
5e4fa164 28#include <lib/version.h>
718e3744 29#include "memory.h"
fc7948fa 30#include "memory_vty.h"
718e3744 31#include "prefix.h"
32#include "log.h"
edd7c245 33#include "privs.h"
2d75d052 34#include "sigevent.h"
228da428
CC
35#include "zclient.h"
36#include "routemap.h"
37#include "filter.h"
38#include "plist.h"
8196f13d 39#include "stream.h"
3f9c7369 40#include "queue.h"
6a69b354 41#include "vrf.h"
567b877d 42#include "bfd.h"
4f04a76b 43#include "libfrr.h"
61cf4b37 44#include "ns.h"
718e3744 45
46#include "bgpd/bgpd.h"
47#include "bgpd/bgp_attr.h"
b2f0fa55 48#include "bgpd/bgp_route.h"
718e3744 49#include "bgpd/bgp_mplsvpn.h"
228da428
CC
50#include "bgpd/bgp_aspath.h"
51#include "bgpd/bgp_dump.h"
52#include "bgpd/bgp_route.h"
53#include "bgpd/bgp_nexthop.h"
54#include "bgpd/bgp_regex.h"
55#include "bgpd/bgp_clist.h"
56#include "bgpd/bgp_debug.h"
14454c9f 57#include "bgpd/bgp_errors.h"
228da428 58#include "bgpd/bgp_filter.h"
8196f13d 59#include "bgpd/bgp_zebra.h"
d3ecc69e 60#include "bgpd/bgp_packet.h"
03014d48 61#include "bgpd/bgp_keepalives.h"
61cf4b37 62#include "bgpd/bgp_network.h"
def31c13 63#include "bgpd/bgp_errors.h"
718e3744 64
65efcfce 65#ifdef ENABLE_BGP_VNC
f8b6f499 66#include "bgpd/rfapi/rfapi_backend.h"
65efcfce
LB
67#endif
68
718e3744 69/* bgpd options, we use GNU getopt library. */
d62a17ae 70static const struct option longopts[] = {
71 {"bgp_port", required_argument, NULL, 'p'},
72 {"listenon", required_argument, NULL, 'l'},
c8dde10f
QY
73#if CONFDATE > 20190521
74 CPP_NOTICE("-r / --retain has reached deprecation EOL, remove")
75#endif
d62a17ae 76 {"retain", no_argument, NULL, 'r'},
77 {"no_kernel", no_argument, NULL, 'n'},
78 {"skip_runas", no_argument, NULL, 'S'},
79 {"ecmp", required_argument, NULL, 'e'},
f533be73 80 {"int_num", required_argument, NULL, 'I'},
c0064d2a 81 {"no_zebra", no_argument, NULL, 'Z'},
d62a17ae 82 {0}};
718e3744 83
2d75d052 84/* signal definitions */
d62a17ae 85void sighup(void);
86void sigint(void);
87void sigusr1(void);
2d75d052 88
d62a17ae 89static void bgp_exit(int);
90static void bgp_vrf_terminate(void);
228da428 91
d62a17ae 92static struct quagga_signal_t bgp_signals[] = {
93 {
94 .signal = SIGHUP,
95 .handler = &sighup,
96 },
97 {
98 .signal = SIGUSR1,
99 .handler = &sigusr1,
100 },
101 {
102 .signal = SIGINT,
103 .handler = &sigint,
104 },
105 {
106 .signal = SIGTERM,
107 .handler = &sigint,
108 },
2d75d052 109};
110
edd7c245 111/* privileges */
996c9314
LB
112static zebra_capabilities_t _caps_p[] = {ZCAP_BIND, ZCAP_NET_RAW,
113 ZCAP_NET_ADMIN, ZCAP_SYS_ADMIN};
edd7c245 114
d62a17ae 115struct zebra_privs_t bgpd_privs = {
b2f36157 116#if defined(FRR_USER) && defined(FRR_GROUP)
d62a17ae 117 .user = FRR_USER,
118 .group = FRR_GROUP,
d81fadfd 119#endif
120#ifdef VTY_GROUP
d62a17ae 121 .vty_group = VTY_GROUP,
edd7c245 122#endif
d62a17ae 123 .caps_p = _caps_p,
124 .cap_num_p = array_size(_caps_p),
125 .cap_num_i = 0,
edd7c245 126};
127
eb05883f
DL
128static struct frr_daemon_info bgpd_di;
129
718e3744 130/* SIGHUP handler. */
d62a17ae 131void sighup(void)
718e3744 132{
d62a17ae 133 zlog_info("SIGHUP received");
718e3744 134
d62a17ae 135 /* Terminate all thread. */
136 bgp_terminate();
137 bgp_reset();
138 zlog_info("bgpd restarting!");
718e3744 139
d62a17ae 140 /* Reload config file. */
1c2facd1 141 vty_read_config(NULL, bgpd_di.config_file, config_default);
718e3744 142
d62a17ae 143 /* Try to return to normal operation. */
718e3744 144}
145
146/* SIGINT handler. */
d62a17ae 147__attribute__((__noreturn__)) void sigint(void)
718e3744 148{
d62a17ae 149 zlog_notice("Terminating on signal");
97b4a0ec
LB
150 assert(bm->terminating == false);
151 bm->terminating = true; /* global flag that shutting down */
718e3744 152
c8dde10f 153 bgp_terminate();
718e3744 154
d62a17ae 155 bgp_exit(0);
540766e7 156
d62a17ae 157 exit(0);
718e3744 158}
159
160/* SIGUSR1 handler. */
d62a17ae 161void sigusr1(void)
718e3744 162{
d62a17ae 163 zlog_rotate();
718e3744 164}
228da428
CC
165
166/*
167 Try to free up allocations we know about so that diagnostic tools such as
168 valgrind are able to better illuminate leaks.
169
170 Zebra route removal and protocol teardown are not meant to be done here.
171 For example, "retain_mode" may be set.
172*/
d62a17ae 173static __attribute__((__noreturn__)) void bgp_exit(int status)
228da428 174{
e2f3a930 175 struct bgp *bgp, *bgp_default, *bgp_evpn;
d62a17ae 176 struct listnode *node, *nnode;
228da428 177
d62a17ae 178 /* it only makes sense for this to be called on a clean exit */
179 assert(status == 0);
228da428 180
03951374
DL
181 frr_early_fini();
182
d62a17ae 183 bfd_gbl_exit();
567b877d 184
d62a17ae 185 bgp_close();
1ff9a340 186
0e42e319 187 bgp_default = bgp_get_default();
e2f3a930 188 bgp_evpn = bgp_get_evpn();
0e42e319 189
d62a17ae 190 /* reverse bgp_master_init */
0e42e319 191 for (ALL_LIST_ELEMENTS(bm->bgp, node, nnode, bgp)) {
e2f3a930 192 if (bgp_default == bgp || bgp_evpn == bgp)
0e42e319 193 continue;
d62a17ae 194 bgp_delete(bgp);
0e42e319 195 }
e2f3a930
T
196 if (bgp_evpn && bgp_evpn != bgp_default)
197 bgp_delete(bgp_evpn);
1f4b2cce
DS
198 if (bgp_default)
199 bgp_delete(bgp_default);
46abd3e3 200
d62a17ae 201 /* reverse bgp_dump_init */
202 bgp_dump_finish();
228da428 203
d62a17ae 204 /* reverse bgp_route_init */
205 bgp_route_finish();
228da428 206
d62a17ae 207 /* cleanup route maps */
208 bgp_route_map_terminate();
228da428 209
d62a17ae 210 /* reverse bgp_attr_init */
211 bgp_attr_finish();
7b8def58 212
2d4ee774
QY
213 /* stop pthreads */
214 bgp_pthreads_finish();
215
d62a17ae 216 /* reverse access_list_init */
217 access_list_add_hook(NULL);
218 access_list_delete_hook(NULL);
219 access_list_reset();
228da428 220
d62a17ae 221 /* reverse bgp_filter_init */
222 as_list_add_hook(NULL);
223 as_list_delete_hook(NULL);
224 bgp_filter_reset();
228da428 225
d62a17ae 226 /* reverse prefix_list_init */
227 prefix_list_add_hook(NULL);
228 prefix_list_delete_hook(NULL);
229 prefix_list_reset();
228da428 230
d62a17ae 231 /* reverse community_list_init */
232 community_list_terminate(bgp_clist);
228da428 233
d62a17ae 234 bgp_vrf_terminate();
65efcfce 235#if ENABLE_BGP_VNC
d62a17ae 236 vnc_zebra_destroy();
65efcfce 237#endif
d62a17ae 238 bgp_zebra_destroy();
228da428 239
3d57c994 240 bf_free(bm->rd_idspace);
6a154c88 241 list_delete(&bm->bgp);
0768f289
PG
242
243 bgp_lp_finish();
244
d62a17ae 245 memset(bm, 0, sizeof(*bm));
46857efe 246
03951374 247 frr_fini();
d62a17ae 248 exit(status);
228da428 249}
6b0655a2 250
d62a17ae 251static int bgp_vrf_new(struct vrf *vrf)
2fcc254e 252{
d62a17ae 253 if (BGP_DEBUG(zebra, ZEBRA))
a8bf7d9c 254 zlog_debug("VRF Created: %s(%u)", vrf->name, vrf->vrf_id);
2fcc254e 255
d62a17ae 256 return 0;
2fcc254e
DS
257}
258
d62a17ae 259static int bgp_vrf_delete(struct vrf *vrf)
2fcc254e 260{
d62a17ae 261 if (BGP_DEBUG(zebra, ZEBRA))
a8bf7d9c 262 zlog_debug("VRF Deletion: %s(%u)", vrf->name, vrf->vrf_id);
2fcc254e 263
d62a17ae 264 return 0;
2fcc254e
DS
265}
266
d62a17ae 267static int bgp_vrf_enable(struct vrf *vrf)
2fcc254e 268{
d62a17ae 269 struct bgp *bgp;
270 vrf_id_t old_vrf_id;
271
272 if (BGP_DEBUG(zebra, ZEBRA))
a8bf7d9c 273 zlog_debug("VRF enable add %s id %u", vrf->name, vrf->vrf_id);
d62a17ae 274
275 bgp = bgp_lookup_by_name(vrf->name);
276 if (bgp) {
9a8bdf1c
PG
277 if (bgp->name && strmatch(vrf->name, VRF_DEFAULT_NAME)) {
278 XFREE(MTYPE_BGP, bgp->name);
279 bgp->name = NULL;
280 XFREE(MTYPE_BGP, bgp->name_pretty);
281 bgp->name_pretty = XSTRDUP(MTYPE_BGP, "VRF default");
282 }
d62a17ae 283 old_vrf_id = bgp->vrf_id;
284 /* We have instance configured, link to VRF and make it "up". */
285 bgp_vrf_link(bgp, vrf);
286
e5619c28 287 bgp_handle_socket(bgp, vrf, old_vrf_id, true);
401d56cc 288 /* Update any redistribution if vrf_id changed */
d62a17ae 289 if (old_vrf_id != bgp->vrf_id)
401d56cc 290 bgp_redistribute_redo(bgp);
d62a17ae 291 bgp_instance_up(bgp);
ddb5b488
PZ
292 vpn_leak_zebra_vrf_label_update(bgp, AFI_IP);
293 vpn_leak_zebra_vrf_label_update(bgp, AFI_IP6);
e504cf3b
DS
294 vpn_leak_postchange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP,
295 bgp_get_default(), bgp);
296 vpn_leak_postchange(BGP_VPN_POLICY_DIR_FROMVPN, AFI_IP,
297 bgp_get_default(), bgp);
298 vpn_leak_postchange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP6,
299 bgp_get_default(), bgp);
300 vpn_leak_postchange(BGP_VPN_POLICY_DIR_FROMVPN, AFI_IP6,
301 bgp_get_default(), bgp);
d62a17ae 302 }
303
304 return 0;
2fcc254e
DS
305}
306
d62a17ae 307static int bgp_vrf_disable(struct vrf *vrf)
2fcc254e 308{
d62a17ae 309 struct bgp *bgp;
310 vrf_id_t old_vrf_id;
311
312 if (vrf->vrf_id == VRF_DEFAULT)
313 return 0;
314
315 if (BGP_DEBUG(zebra, ZEBRA))
316 zlog_debug("VRF disable %s id %d", vrf->name, vrf->vrf_id);
317
318 bgp = bgp_lookup_by_name(vrf->name);
319 if (bgp) {
ddb5b488
PZ
320
321 vpn_leak_zebra_vrf_label_withdraw(bgp, AFI_IP);
322 vpn_leak_zebra_vrf_label_withdraw(bgp, AFI_IP6);
e504cf3b
DS
323 vpn_leak_prechange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP,
324 bgp_get_default(), bgp);
325 vpn_leak_prechange(BGP_VPN_POLICY_DIR_FROMVPN, AFI_IP,
326 bgp_get_default(), bgp);
327 vpn_leak_prechange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP6,
328 bgp_get_default(), bgp);
329 vpn_leak_prechange(BGP_VPN_POLICY_DIR_FROMVPN, AFI_IP6,
330 bgp_get_default(), bgp);
ddb5b488 331
d62a17ae 332 old_vrf_id = bgp->vrf_id;
e5619c28 333 bgp_handle_socket(bgp, vrf, VRF_UNKNOWN, false);
d62a17ae 334 /* We have instance configured, unlink from VRF and make it
335 * "down". */
336 bgp_vrf_unlink(bgp, vrf);
401d56cc 337 /* Delete any redistribute vrf bitmaps if the vrf_id changed */
d62a17ae 338 if (old_vrf_id != bgp->vrf_id)
401d56cc 339 bgp_unset_redist_vrf_bitmaps(bgp, old_vrf_id);
d62a17ae 340 bgp_instance_down(bgp);
341 }
342
343 /* Note: This is a callback, the VRF will be deleted by the caller. */
344 return 0;
2fcc254e
DS
345}
346
d62a17ae 347static void bgp_vrf_init(void)
2fcc254e 348{
ecbc5a37
PG
349 vrf_init(bgp_vrf_new, bgp_vrf_enable, bgp_vrf_disable,
350 bgp_vrf_delete, NULL);
2fcc254e
DS
351}
352
d62a17ae 353static void bgp_vrf_terminate(void)
021530c1 354{
d62a17ae 355 vrf_terminate();
021530c1 356}
357
8fcdd0d6
RW
358static const struct frr_yang_module_info *bgpd_yang_modules[] = {
359};
360
d62a17ae 361FRR_DAEMON_INFO(bgpd, BGP, .vty_port = BGP_VTY_PORT,
4f04a76b 362
d62a17ae 363 .proghelp = "Implementation of the BGP routing protocol.",
4f04a76b 364
d62a17ae 365 .signals = bgp_signals, .n_signals = array_size(bgp_signals),
4f04a76b 366
8fcdd0d6
RW
367 .privs = &bgpd_privs, .yang_modules = bgpd_yang_modules,
368 .n_yang_modules = array_size(bgpd_yang_modules), )
4f04a76b 369
c8dde10f
QY
370#if CONFDATE > 20190521
371CPP_NOTICE("-r / --retain has reached deprecation EOL, remove")
372#endif
373#define DEPRECATED_OPTIONS "r"
374
718e3744 375/* Main routine of bgpd. Treatment of argument and start bgp finite
376 state machine is handled at here. */
d62a17ae 377int main(int argc, char **argv)
718e3744 378{
d62a17ae 379 int opt;
380 int tmp_port;
381
382 int bgp_port = BGP_PORT_DEFAULT;
383 char *bgp_address = NULL;
384 int no_fib_flag = 0;
0b014ea6 385 int no_zebra_flag = 0;
d62a17ae 386 int skip_runas = 0;
f533be73 387 int instance = 0;
d62a17ae 388
389 frr_preinit(&bgpd_di, argc, argv);
390 frr_opt_add(
c0064d2a 391 "p:l:SnZe:I:" DEPRECATED_OPTIONS, longopts,
580f8636 392 " -p, --bgp_port Set BGP listen port number (0 means do not listen).\n"
d62a17ae 393 " -l, --listenon Listen on specified address (implies -n)\n"
d62a17ae 394 " -n, --no_kernel Do not install route to kernel.\n"
0b014ea6 395 " -Z, --no_zebra Do not communicate with Zebra.\n"
d62a17ae 396 " -S, --skip_runas Skip capabilities checks, and changing user and group IDs.\n"
f533be73 397 " -e, --ecmp Specify ECMP to use.\n"
398 " -I, --int_num Set instance number (label-manager)\n");
d62a17ae 399
400 /* Command line argument treatment. */
401 while (1) {
402 opt = frr_getopt(argc, argv, 0);
403
c8dde10f
QY
404 if (opt && opt < 128 && strchr(DEPRECATED_OPTIONS, opt)) {
405 fprintf(stderr,
406 "The -%c option no longer exists.\nPlease refer to the manual.\n",
407 opt);
408 continue;
409 }
410
d62a17ae 411 if (opt == EOF)
412 break;
413
414 switch (opt) {
415 case 0:
416 break;
417 case 'p':
418 tmp_port = atoi(optarg);
580f8636 419 if (tmp_port < 0 || tmp_port > 0xffff)
d62a17ae 420 bgp_port = BGP_PORT_DEFAULT;
421 else
422 bgp_port = tmp_port;
423 break;
424 case 'e':
425 multipath_num = atoi(optarg);
426 if (multipath_num > MULTIPATH_NUM
427 || multipath_num <= 0) {
af4c2728 428 flog_err(
e50f7cfd 429 EC_BGP_MULTIPATH,
d62a17ae 430 "Multipath Number specified must be less than %d and greater than 0",
431 MULTIPATH_NUM);
432 return 1;
433 }
434 break;
d62a17ae 435 case 'l':
436 bgp_address = optarg;
437 /* listenon implies -n */
438 /* fallthru */
439 case 'n':
440 no_fib_flag = 1;
441 break;
0b014ea6
PG
442 case 'Z':
443 no_zebra_flag = 1;
444 break;
d62a17ae 445 case 'S':
446 skip_runas = 1;
447 break;
f533be73 448 case 'I':
449 instance = atoi(optarg);
450 if (instance > (unsigned short)-1)
451 zlog_err("Instance %i out of range (0..%u)",
452 instance, (unsigned short)-1);
453 break;
d62a17ae 454 default:
455 frr_help_exit(1);
456 break;
457 }
718e3744 458 }
d62a17ae 459 if (skip_runas)
460 memset(&bgpd_privs, 0, sizeof(bgpd_privs));
718e3744 461
d62a17ae 462 /* BGP master init. */
463 bgp_master_init(frr_init());
464 bm->port = bgp_port;
580f8636 465 if (bgp_port == 0)
466 bgp_option_set(BGP_OPT_NO_LISTEN);
d62a17ae 467 bm->address = bgp_address;
0b014ea6 468 if (no_fib_flag || no_zebra_flag)
d62a17ae 469 bgp_option_set(BGP_OPT_NO_FIB);
0b014ea6
PG
470 if (no_zebra_flag)
471 bgp_option_set(BGP_OPT_NO_ZEBRA);
def31c13 472 bgp_error_init();
d62a17ae 473 /* Initializations. */
474 bgp_vrf_init();
718e3744 475
d62a17ae 476 /* BGP related initialization. */
f533be73 477 bgp_init((unsigned short)instance);
718e3744 478
d62a17ae 479 snprintf(bgpd_di.startinfo, sizeof(bgpd_di.startinfo), ", bgp@%s:%d",
480 (bm->address ? bm->address : "<all>"), bm->port);
718e3744 481
d62a17ae 482 frr_config_fork();
2d4ee774 483 /* must be called after fork() */
419dfe6a 484 bgp_pthreads_run();
d62a17ae 485 frr_run(bm->master);
718e3744 486
d62a17ae 487 /* Not reached. */
488 return (0);
718e3744 489}