0
0
mirror of https://gitlab.nic.cz/labs/bird.git synced 2024-12-22 17:51:53 +00:00

Merge commit '692055e3df6cc9f0d428d3b0dd8cdd8e825eb6f4' into haugesund-to-2.0

This commit is contained in:
Maria Matejka 2022-05-30 15:17:52 +02:00
commit 097f157182
9 changed files with 90 additions and 2202 deletions

View File

@ -50,6 +50,7 @@ static byte *server_read_pos = server_read_buf;
int init = 1; /* During intial sequence */ int init = 1; /* During intial sequence */
int busy = 1; /* Executing BIRD command */ int busy = 1; /* Executing BIRD command */
int interactive; /* Whether stdin is terminal */ int interactive; /* Whether stdin is terminal */
int last_code; /* Last return code */
static int num_lines, skip_input; static int num_lines, skip_input;
int term_lns, term_cls; int term_lns, term_cls;
@ -196,7 +197,7 @@ init_commands(void)
{ {
/* Initial command is finished and we want to exit */ /* Initial command is finished and we want to exit */
cleanup(); cleanup();
exit(0); exit((last_code < 8000) ? 0 : 1);
} }
input_init(); input_init();
@ -283,6 +284,8 @@ server_got_reply(char *x)
if (code) if (code)
PRINTF(len, "%s\n", verbose ? x : x+5); PRINTF(len, "%s\n", verbose ? x : x+5);
last_code = code;
if (x[4] == ' ') if (x[4] == ' ')
{ {
busy = 0; busy = 0;

View File

@ -5,8 +5,9 @@ After=network.target
[Service] [Service]
Type=simple Type=simple
ExecStartPre=/usr/sbin/bird -p
ExecStart=/usr/sbin/bird -f -u bird -g bird ExecStart=/usr/sbin/bird -f -u bird -g bird
ExecReload=/bin/kill -HUP $MAINPID ExecReload=/usr/sbin/birdc configure
Restart=on-failure Restart=on-failure
[Install] [Install]

View File

@ -2153,6 +2153,13 @@ protocol bfd [&lt;name&gt;] {
to configure separate BFD protocol instances for IPv4 and for IPv6 to configure separate BFD protocol instances for IPv4 and for IPv6
sessions. sessions.
<tag><label id="bfd-strict-bind">strict bind <m/switch/</tag>
Specify whether each BFD interface should use a separate listening
socket bound to its local address, or just use a shared listening socket
accepting all addresses. Binding to a specific address could be useful
in cases like running multiple BIRD instances on a machine, each
handling a different set of interfaces. Default: disabled.
<tag><label id="bfd-iface">interface <m/pattern/ [, <m/.../] { <m/options/ }</tag> <tag><label id="bfd-iface">interface <m/pattern/ [, <m/.../] { <m/options/ }</tag>
Interface definitions allow to specify options for sessions associated Interface definitions allow to specify options for sessions associated
with such interfaces and also may contain interface specific options. with such interfaces and also may contain interface specific options.

View File

@ -85,25 +85,29 @@ ip4_classify(ip4_addr ad)
u32 a = _I(ad); u32 a = _I(ad);
u32 b = a >> 24U; u32 b = a >> 24U;
if (b && b <= 0xdf) if (b < 0xe0)
{ {
if (b == 0x7f) if (b == 0x00) /* 0.0.0.0/8 This network */
return IADDR_INVALID;
if (b == 0x7f) /* 127.0.0.0/8 Loopback address */
return IADDR_HOST | SCOPE_HOST; return IADDR_HOST | SCOPE_HOST;
else if ((b == 0x0a) ||
((a & 0xffff0000) == 0xc0a80000) || if ((b == 0x0a) || /* 10.0.0.0/8 Private range */
((a & 0xfff00000) == 0xac100000)) ((a & 0xffff0000) == 0xc0a80000) || /* 192.168.0.0/16 Private range */
((a & 0xfff00000) == 0xac100000)) /* 172.16.0.0/12 Private range */
return IADDR_HOST | SCOPE_SITE; return IADDR_HOST | SCOPE_SITE;
else
return IADDR_HOST | SCOPE_UNIVERSE; return IADDR_HOST | SCOPE_UNIVERSE;
} }
if (b >= 0xe0 && b <= 0xef) if (b < 0xf0) /* 224.0.0.0/4 Multicast address */
return IADDR_MULTICAST | SCOPE_UNIVERSE; return IADDR_MULTICAST | SCOPE_UNIVERSE;
if (a == 0xffffffff) if (a == 0xffffffff) /* 255.255.255.255 Broadcast address */
return IADDR_BROADCAST | SCOPE_LINK; return IADDR_BROADCAST | SCOPE_LINK;
return IADDR_INVALID; return IADDR_HOST | SCOPE_SITE; /* 240.0.0.0/4 Reserved / private */
} }
int int

View File

@ -582,6 +582,9 @@ bfd_get_iface(struct bfd_proto *p, ip_addr local, struct iface *iface)
ifa->sk = bfd_open_tx_sk(p, local, iface); ifa->sk = bfd_open_tx_sk(p, local, iface);
ifa->uc = 1; ifa->uc = 1;
if (cf->strict_bind)
ifa->rx = bfd_open_rx_sk_bound(p, local, iface);
add_tail(&p->iface_list, &ifa->n); add_tail(&p->iface_list, &ifa->n);
return ifa; return ifa;
@ -599,6 +602,12 @@ bfd_free_iface(struct bfd_iface *ifa)
rfree(ifa->sk); rfree(ifa->sk);
} }
if (ifa->rx)
{
sk_stop(ifa->rx);
rfree(ifa->rx);
}
rem_node(&ifa->n); rem_node(&ifa->n);
mb_free(ifa); mb_free(ifa);
} }
@ -1031,6 +1040,8 @@ bfd_start(struct proto *P)
birdloop_enter(p->loop); birdloop_enter(p->loop);
if (!cf->strict_bind)
{
if (cf->accept_ipv4 && cf->accept_direct) if (cf->accept_ipv4 && cf->accept_direct)
p->rx4_1 = bfd_open_rx_sk(p, 0, SK_IPV4); p->rx4_1 = bfd_open_rx_sk(p, 0, SK_IPV4);
@ -1042,6 +1053,7 @@ bfd_start(struct proto *P)
if (cf->accept_ipv6 && cf->accept_multihop) if (cf->accept_ipv6 && cf->accept_multihop)
p->rx6_m = bfd_open_rx_sk(p, 1, SK_IPV6); p->rx6_m = bfd_open_rx_sk(p, 1, SK_IPV6);
}
birdloop_leave(p->loop); birdloop_leave(p->loop);
@ -1095,7 +1107,8 @@ bfd_reconfigure(struct proto *P, struct proto_config *c)
if ((new->accept_ipv4 != old->accept_ipv4) || if ((new->accept_ipv4 != old->accept_ipv4) ||
(new->accept_ipv6 != old->accept_ipv6) || (new->accept_ipv6 != old->accept_ipv6) ||
(new->accept_direct != old->accept_direct) || (new->accept_direct != old->accept_direct) ||
(new->accept_multihop != old->accept_multihop)) (new->accept_multihop != old->accept_multihop) ||
(new->strict_bind != old->strict_bind))
return 0; return 0;
birdloop_mask_wakeups(p->loop); birdloop_mask_wakeups(p->loop);

View File

@ -47,6 +47,7 @@ struct bfd_config
u8 accept_ipv6; u8 accept_ipv6;
u8 accept_direct; u8 accept_direct;
u8 accept_multihop; u8 accept_multihop;
u8 strict_bind;
}; };
struct bfd_iface_config struct bfd_iface_config
@ -116,6 +117,7 @@ struct bfd_iface
struct bfd_proto *bfd; struct bfd_proto *bfd;
sock *sk; sock *sk;
sock *rx;
u32 uc; u32 uc;
u8 changed; u8 changed;
}; };
@ -221,6 +223,7 @@ void bfd_show_sessions(struct proto *P);
/* packets.c */ /* packets.c */
void bfd_send_ctl(struct bfd_proto *p, struct bfd_session *s, int final); void bfd_send_ctl(struct bfd_proto *p, struct bfd_session *s, int final);
sock * bfd_open_rx_sk(struct bfd_proto *p, int multihop, int inet_version); sock * bfd_open_rx_sk(struct bfd_proto *p, int multihop, int inet_version);
sock * bfd_open_rx_sk_bound(struct bfd_proto *p, ip_addr local, struct iface *ifa);
sock * bfd_open_tx_sk(struct bfd_proto *p, ip_addr local, struct iface *ifa); sock * bfd_open_tx_sk(struct bfd_proto *p, ip_addr local, struct iface *ifa);

View File

@ -23,7 +23,8 @@ CF_DECLS
CF_KEYWORDS(BFD, MIN, IDLE, RX, TX, INTERVAL, MULTIPLIER, PASSIVE, CF_KEYWORDS(BFD, MIN, IDLE, RX, TX, INTERVAL, MULTIPLIER, PASSIVE,
INTERFACE, MULTIHOP, NEIGHBOR, DEV, LOCAL, AUTHENTICATION, INTERFACE, MULTIHOP, NEIGHBOR, DEV, LOCAL, AUTHENTICATION,
NONE, SIMPLE, METICULOUS, KEYED, MD5, SHA1, IPV4, IPV6, DIRECT) NONE, SIMPLE, METICULOUS, KEYED, MD5, SHA1, IPV4, IPV6, DIRECT,
STRICT, BIND)
%type <iface> bfd_neigh_iface %type <iface> bfd_neigh_iface
%type <a> bfd_neigh_local %type <a> bfd_neigh_local
@ -48,6 +49,7 @@ bfd_proto_item:
| INTERFACE bfd_iface | INTERFACE bfd_iface
| MULTIHOP bfd_multihop | MULTIHOP bfd_multihop
| NEIGHBOR bfd_neighbor | NEIGHBOR bfd_neighbor
| STRICT BIND bool { BFD_CFG->strict_bind = $3; }
; ;
bfd_proto_opts: bfd_proto_opts:

View File

@ -366,7 +366,9 @@ bfd_rx_hook(sock *sk, uint len)
if (ps > BFD_STATE_DOWN) if (ps > BFD_STATE_DOWN)
DROP("invalid init state", ps); DROP("invalid init state", ps);
uint ifindex = (sk->sport == BFD_CONTROL_PORT) ? sk->lifindex : 0; uint ifindex = (sk->sport == BFD_CONTROL_PORT) ?
(sk->iface ? sk->iface->index : sk->lifindex) :
0;
s = bfd_find_session_by_addr(p, sk->faddr, ifindex); s = bfd_find_session_by_addr(p, sk->faddr, ifindex);
/* FIXME: better session matching and message */ /* FIXME: better session matching and message */
@ -438,6 +440,38 @@ bfd_open_rx_sk(struct bfd_proto *p, int multihop, int af)
return NULL; return NULL;
} }
sock *
bfd_open_rx_sk_bound(struct bfd_proto *p, ip_addr local, struct iface *ifa)
{
sock *sk = sk_new(p->tpool);
sk->type = SK_UDP;
sk->saddr = local;
sk->sport = ifa ? BFD_CONTROL_PORT : BFD_MULTI_CTL_PORT;
sk->iface = ifa;
sk->vrf = p->p.vrf;
sk->data = p;
sk->rbsize = BFD_MAX_LEN;
sk->rx_hook = bfd_rx_hook;
sk->err_hook = bfd_err_hook;
/* TODO: configurable ToS and priority */
sk->tos = IP_PREC_INTERNET_CONTROL;
sk->priority = sk_priority_control;
sk->flags = SKF_THREAD | SKF_BIND | (ifa ? SKF_TTL_RX : 0);
if (sk_open(sk) < 0)
goto err;
sk_start(sk);
return sk;
err:
sk_log_error(sk, p->p.name);
rfree(sk);
return NULL;
}
sock * sock *
bfd_open_tx_sk(struct bfd_proto *p, ip_addr local, struct iface *ifa) bfd_open_tx_sk(struct bfd_proto *p, ip_addr local, struct iface *ifa)
{ {

File diff suppressed because it is too large Load Diff