summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorclaudio <claudio@openbsd.org>2018-10-15 10:44:47 +0000
committerclaudio <claudio@openbsd.org>2018-10-15 10:44:47 +0000
commit099becd680b9cd19d51348f585ac5e93cf334887 (patch)
tree666b2e56cd1605bb55bf7fe61a72aaf2c2a69f95
parentPrevent VM reboot loops by rate-limiting the interval a VM can reboot. (diff)
downloadwireguard-openbsd-099becd680b9cd19d51348f585ac5e93cf334887.tar.xz
wireguard-openbsd-099becd680b9cd19d51348f585ac5e93cf334887.zip
Use the up_rib tree to withdraw all prefixes of a peer which is used to
reload peers into a new RIB. Removes one additional full RIB tree walker. OK benno@
-rw-r--r--usr.sbin/bgpd/rde.c32
-rw-r--r--usr.sbin/bgpd/rde.h3
-rw-r--r--usr.sbin/bgpd/rde_update.c18
3 files changed, 21 insertions, 32 deletions
diff --git a/usr.sbin/bgpd/rde.c b/usr.sbin/bgpd/rde.c
index 80a6131a00f..1665ed66ac1 100644
--- a/usr.sbin/bgpd/rde.c
+++ b/usr.sbin/bgpd/rde.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: rde.c,v 1.434 2018/10/14 10:21:30 claudio Exp $ */
+/* $OpenBSD: rde.c,v 1.435 2018/10/15 10:44:47 claudio Exp $ */
/*
* Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org>
@@ -96,7 +96,6 @@ static void rde_softreconfig_out_done(void *);
static void rde_softreconfig_done(void);
static void rde_softreconfig_out(struct rib_entry *, void *);
static void rde_softreconfig_in(struct rib_entry *, void *);
-static void rde_softreconfig_unload_peer(struct rib_entry *, void *);
void rde_up_dump_upcall(struct rib_entry *, void *);
void rde_update_queue_runner(void);
void rde_update6_queue_runner(u_int8_t);
@@ -2934,8 +2933,7 @@ rde_reload_done(void)
peer->reconf_out = 0;
peer->reconf_rib = 0;
if (peer->rib != rib_find(peer->conf.rib)) {
- rib_dump(peer->rib, rde_softreconfig_unload_peer, peer,
- AID_UNSPEC);
+ up_withdraw_all(peer);
peer->rib = rib_find(peer->conf.rib);
if (peer->rib == NULL)
fatalx("King Bula's peer met an unknown RIB");
@@ -3233,32 +3231,6 @@ rde_softreconfig_out(struct rib_entry *re, void *bula)
}
}
-static void
-rde_softreconfig_unload_peer(struct rib_entry *re, void *ptr)
-{
- struct filterstate ostate;
- struct rde_peer *peer = ptr;
- struct prefix *p = re->active;
- struct pt_entry *pt;
- struct bgpd_addr addr;
-
- pt = re->prefix;
- pt_getaddr(pt, &addr);
-
- /* check if prefix was announced */
- if (up_test_update(peer, p) != 1)
- return;
-
- rde_filterstate_prep(&ostate, prefix_aspath(p), prefix_nexthop(p),
- prefix_nhflags(p));
- if (rde_filter(out_rules_tmp, peer, p, &ostate) != ACTION_DENY) {
- /* send withdraw */
- up_rib_remove(peer, re);
- up_generate(peer, NULL, &addr, pt->prefixlen);
- }
- rde_filterstate_clean(&ostate);
-}
-
/*
* generic helper function
*/
diff --git a/usr.sbin/bgpd/rde.h b/usr.sbin/bgpd/rde.h
index b174fb78420..677cf963365 100644
--- a/usr.sbin/bgpd/rde.h
+++ b/usr.sbin/bgpd/rde.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: rde.h,v 1.196 2018/10/01 23:09:53 job Exp $ */
+/* $OpenBSD: rde.h,v 1.197 2018/10/15 10:44:47 claudio Exp $ */
/*
* Copyright (c) 2003, 2004 Claudio Jeker <claudio@openbsd.org> and
@@ -555,6 +555,7 @@ void up_init(struct rde_peer *);
void up_down(struct rde_peer *);
int up_rib_remove(struct rde_peer *, struct rib_entry *);
void up_rib_add(struct rde_peer *, struct rib_entry *);
+void up_withdraw_all(struct rde_peer *);
int up_test_update(struct rde_peer *, struct prefix *);
int up_generate(struct rde_peer *, struct filterstate *,
struct bgpd_addr *, u_int8_t);
diff --git a/usr.sbin/bgpd/rde_update.c b/usr.sbin/bgpd/rde_update.c
index a42d6f88381..f1e35197f1f 100644
--- a/usr.sbin/bgpd/rde_update.c
+++ b/usr.sbin/bgpd/rde_update.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: rde_update.c,v 1.100 2018/09/29 07:43:36 claudio Exp $ */
+/* $OpenBSD: rde_update.c,v 1.101 2018/10/15 10:44:47 claudio Exp $ */
/*
* Copyright (c) 2004 Claudio Jeker <claudio@openbsd.org>
@@ -245,6 +245,22 @@ up_rib_add(struct rde_peer *peer, struct rib_entry *re)
free(ur);
}
+void
+up_withdraw_all(struct rde_peer *peer)
+{
+ struct bgpd_addr addr;
+ struct update_rib *ur, *nur;
+
+ RB_FOREACH_SAFE(ur, uptree_rib, &peer->up_rib, nur) {
+ RB_REMOVE(uptree_rib, &peer->up_rib, ur);
+
+ /* withdraw prefix */
+ pt_getaddr(ur->re->prefix, &addr);
+ up_generate(peer, NULL, &addr, ur->re->prefix->prefixlen);
+ free(ur);
+ }
+}
+
int
up_add(struct rde_peer *peer, struct update_prefix *p, struct update_attr *a)
{