From: claudio Date: Wed, 5 Sep 2018 09:49:57 +0000 (+0000) Subject: Change the way as_compare() and aspath_match() handle 'neighbor-as'. Instead X-Git-Url: http://artulab.com/gitweb/?a=commitdiff_plain;h=052562fe3d2f91fb3aa9e099095c9e9eddc142d3;p=openbsd Change the way as_compare() and aspath_match() handle 'neighbor-as'. Instead of doing the condition before calling aspath_match() just pass the neighbor-as down to as_compare() which then has all needed data for the lookup. While doing this also remove one of the as fields in struct filter_as since the min/max fields can be reused for unary operations. OK denis@ phessler@ --- diff --git a/usr.sbin/bgpd/bgpd.h b/usr.sbin/bgpd/bgpd.h index 71622512a4b..56f9ffad1aa 100644 --- a/usr.sbin/bgpd/bgpd.h +++ b/usr.sbin/bgpd/bgpd.h @@ -1,4 +1,4 @@ -/* $OpenBSD: bgpd.h,v 1.332 2018/09/04 12:00:29 claudio Exp $ */ +/* $OpenBSD: bgpd.h,v 1.333 2018/09/05 09:49:57 claudio Exp $ */ /* * Copyright (c) 2003, 2004 Henning Brauer @@ -649,7 +649,6 @@ enum aslen_spec { }; struct filter_as { - u_int32_t as; u_int16_t flags; enum as_spec type; u_int8_t op; diff --git a/usr.sbin/bgpd/parse.y b/usr.sbin/bgpd/parse.y index f9cc9c5ef1c..6e21b01ade7 100644 --- a/usr.sbin/bgpd/parse.y +++ b/usr.sbin/bgpd/parse.y @@ -1,4 +1,4 @@ -/* $OpenBSD: parse.y,v 1.331 2018/08/27 19:32:37 claudio Exp $ */ +/* $OpenBSD: parse.y,v 1.332 2018/09/05 09:49:57 claudio Exp $ */ /* * Copyright (c) 2002, 2003, 2004 Henning Brauer @@ -1902,7 +1902,7 @@ filter_as : as4number_any { if (($$ = calloc(1, sizeof(struct filter_as_l))) == NULL) fatal(NULL); - $$->a.as = $1; + $$->a.as_min = $1; $$->a.op = OP_EQ; } | NEIGHBORAS { @@ -1916,7 +1916,7 @@ filter_as : as4number_any { NULL) fatal(NULL); $$->a.op = $1; - $$->a.as = $2; + $$->a.as_min = $2; } | as4number_any binaryop as4number_any { if (($$ = calloc(1, sizeof(struct filter_as_l))) == diff --git a/usr.sbin/bgpd/printconf.c b/usr.sbin/bgpd/printconf.c index 6cae947f8ba..49e93e16954 100644 --- a/usr.sbin/bgpd/printconf.c +++ b/usr.sbin/bgpd/printconf.c @@ -1,4 +1,4 @@ -/* $OpenBSD: printconf.c,v 1.109 2018/07/11 14:08:46 benno Exp $ */ +/* $OpenBSD: printconf.c,v 1.110 2018/09/05 09:49:57 claudio Exp $ */ /* * Copyright (c) 2003, 2004 Henning Brauer @@ -619,10 +619,10 @@ void print_as(struct filter_rule *r) printf("%s ", log_as(r->match.as.as_max)); break; case OP_NE: - printf("!= %s ", log_as(r->match.as.as)); + printf("!= %s ", log_as(r->match.as.as_min)); break; default: - printf("%s ", log_as(r->match.as.as)); + printf("%s ", log_as(r->match.as.as_min)); break; } } diff --git a/usr.sbin/bgpd/rde.c b/usr.sbin/bgpd/rde.c index a9a33451bb4..6b140783b9f 100644 --- a/usr.sbin/bgpd/rde.c +++ b/usr.sbin/bgpd/rde.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rde.c,v 1.417 2018/09/05 07:31:29 claudio Exp $ */ +/* $OpenBSD: rde.c,v 1.418 2018/09/05 09:49:57 claudio Exp $ */ /* * Copyright (c) 2003, 2004 Henning Brauer @@ -2171,7 +2171,7 @@ rde_dump_filter(struct prefix *p, struct ctl_show_rib_request *req) return; if (req->type == IMSG_CTL_SHOW_RIB_AS && !aspath_match(asp->aspath->data, asp->aspath->len, - &req->as, req->as.as)) + &req->as, 0)) return; if (req->type == IMSG_CTL_SHOW_RIB_COMMUNITY && !community_match(asp, req->community.as, @@ -3782,5 +3782,4 @@ rde_mark_prefixsets_dirty(struct prefixset_head *psold, } } } - return; } diff --git a/usr.sbin/bgpd/rde_filter.c b/usr.sbin/bgpd/rde_filter.c index 5d287b63840..ddfa2ac39bb 100644 --- a/usr.sbin/bgpd/rde_filter.c +++ b/usr.sbin/bgpd/rde_filter.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rde_filter.c,v 1.99 2018/08/03 16:31:22 claudio Exp $ */ +/* $OpenBSD: rde_filter.c,v 1.100 2018/09/05 09:49:57 claudio Exp $ */ /* * Copyright (c) 2004 Claudio Jeker @@ -340,7 +340,6 @@ int rde_filter_match(struct filter_rule *f, struct rde_peer *peer, struct filterstate *state, struct prefix *p) { - u_int32_t pas; int cas, type; int64_t las, ld1, ld2; struct prefixset_item *psi; @@ -349,21 +348,17 @@ rde_filter_match(struct filter_rule *f, struct rde_peer *peer, if (state != NULL) asp = &state->aspath; - if (asp != NULL && f->match.as.type != AS_NONE) { - if (f->match.as.flags & AS_FLAG_NEIGHBORAS) - pas = peer->conf.remote_as; - else - pas = f->match.as.as; - if (aspath_match(asp->aspath->data, asp->aspath->len, - &f->match.as, pas) == 0) - return (0); - } - if (f->peer.ebgp && !peer->conf.ebgp) return (0); if (f->peer.ibgp && peer->conf.ebgp) return (0); + if (asp != NULL && f->match.as.type != AS_NONE) { + if (aspath_match(asp->aspath->data, asp->aspath->len, + &f->match.as, peer->conf.remote_as) == 0) + return (0); + } + if (asp != NULL && f->match.aslen.type != ASLEN_NONE) if (aspath_lenmatch(asp->aspath, f->match.aslen.type, f->match.aslen.aslen) == 0) diff --git a/usr.sbin/bgpd/util.c b/usr.sbin/bgpd/util.c index 3b35efc7a35..3fb491a2f70 100644 --- a/usr.sbin/bgpd/util.c +++ b/usr.sbin/bgpd/util.c @@ -1,4 +1,4 @@ -/* $OpenBSD: util.c,v 1.32 2018/09/04 12:00:29 claudio Exp $ */ +/* $OpenBSD: util.c,v 1.33 2018/09/05 09:49:57 claudio Exp $ */ /* * Copyright (c) 2006 Claudio Jeker @@ -313,22 +313,40 @@ aspath_strlen(void *data, u_int16_t len) } static int -as_compare(struct filter_as *f, u_int32_t as, u_int32_t match) -{ - if ((f->op == OP_NONE || f->op == OP_EQ) && as == match) - return (1); - else if (f->op == OP_NE && as != match) - return (1); - else if (f->op == OP_RANGE && as >= f->as_min && as <= f->as_max) - return (1); - else if (f->op == OP_XRANGE && (as < f->as_min || as > f->as_max)) - return (1); +as_compare(struct filter_as *f, u_int32_t as, u_int32_t neighas) +{ + u_int32_t match; + + if (f->flags & AS_FLAG_NEIGHBORAS) + match = neighas; + else + match = f->as_min; + + switch (f->op) { + case OP_NONE: + case OP_EQ: + if (as == match) + return (1); + break; + case OP_NE: + if (as != match) + return (1); + break; + case OP_RANGE: + if (as >= f->as_min && as <= f->as_max) + return (1); + break; + case OP_XRANGE: + if (as < f->as_min || as > f->as_max) + return (1); + break; + } return (0); } /* we need to be able to search more than one as */ int -aspath_match(void *data, u_int16_t len, struct filter_as *f, u_int32_t match) +aspath_match(void *data, u_int16_t len, struct filter_as *f, u_int32_t neighas) { u_int8_t *seg; int final; @@ -348,7 +366,7 @@ aspath_match(void *data, u_int16_t len, struct filter_as *f, u_int32_t match) /* just check the leftmost AS */ if (f->type == AS_PEER && len >= 6) { as = aspath_extract(seg, 0); - if (as_compare(f, as, match)) + if (as_compare(f, as, neighas)) return (1); else return (0); @@ -372,7 +390,7 @@ aspath_match(void *data, u_int16_t len, struct filter_as *f, u_int32_t match) /* not yet in the final segment */ if (!final) continue; - if (as_compare(f, as, match)) + if (as_compare(f, as, neighas)) return (1); else return (0); @@ -386,7 +404,7 @@ aspath_match(void *data, u_int16_t len, struct filter_as *f, u_int32_t match) if (final && i == seg_len - 1 && f->type == AS_TRANSIT) return (0); as = aspath_extract(seg, i); - if (as_compare(f, as, match)) + if (as_compare(f, as, neighas)) return (1); } }