summaryrefslogtreecommitdiff
path: root/usr.sbin
diff options
context:
space:
mode:
authorClaudio Jeker <claudio@cvs.openbsd.org>2020-03-16 14:47:31 +0000
committerClaudio Jeker <claudio@cvs.openbsd.org>2020-03-16 14:47:31 +0000
commit0e6548a3bc2aa39fb4202e3df2a3b9133efafa24 (patch)
treecad7dd8c18e732e27a9ed3a7ce2f8338a18874cc /usr.sbin
parent71e5e353a7656d5a43655b48d847fca5a09771e3 (diff)
The assumption that in roa tables a prefix / source-as combo only appears
once in the input file is not correct. I thought the RPKI validators would aggreagte these entries but that is not necessarily the case. There are cases where prefixes show up with the same source-as multiple times with different maxlen lenght. In those cases merge these multiple entries and keep the one entry with the longest maxlen length since that is the VRP which covers all others. Found by job@ OK benno@
Diffstat (limited to 'usr.sbin')
-rw-r--r--usr.sbin/bgpd/parse.y21
1 files changed, 15 insertions, 6 deletions
diff --git a/usr.sbin/bgpd/parse.y b/usr.sbin/bgpd/parse.y
index 93aa40da1f5..b5b9db12f3c 100644
--- a/usr.sbin/bgpd/parse.y
+++ b/usr.sbin/bgpd/parse.y
@@ -1,4 +1,4 @@
-/* $OpenBSD: parse.y,v 1.404 2020/02/14 13:54:31 claudio Exp $ */
+/* $OpenBSD: parse.y,v 1.405 2020/03/16 14:47:30 claudio Exp $ */
/*
* Copyright (c) 2002, 2003, 2004 Henning Brauer <henning@openbsd.org>
@@ -4480,7 +4480,7 @@ static void
add_roa_set(struct prefixset_item *npsi, u_int32_t as, u_int8_t max)
{
struct prefixset_item *psi;
- struct roa_set rs;
+ struct roa_set rs, *rsp;
/* no prefixlen option in this tree */
npsi->p.op = OP_NONE;
@@ -4492,8 +4492,17 @@ add_roa_set(struct prefixset_item *npsi, u_int32_t as, u_int8_t max)
if (psi->set == NULL)
if ((psi->set = set_new(1, sizeof(rs))) == NULL)
fatal("set_new");
- rs.as = as;
- rs.maxlen = max;
- if (set_add(psi->set, &rs, 1) != 0)
- fatal("as_set_new");
+
+ /* merge sets with same key, longer maxlen wins */
+ if ((rsp = set_match(psi->set, as)) != NULL) {
+ if (rsp->maxlen < max)
+ rsp->maxlen = max;
+ } else {
+ rs.as = as;
+ rs.maxlen = max;
+ if (set_add(psi->set, &rs, 1) != 0)
+ fatal("as_set_new");
+ /* prep data so that set_match works */
+ set_prep(psi->set);
+ }
}