From 0610fd84f8a5d196a481162cec484d89439963f0 Mon Sep 17 00:00:00 2001 From: Claudio Jeker Date: Wed, 28 Nov 2018 08:34:00 +0000 Subject: Adjust bgpctl to handle the community changes done in bgpd. OK job@, phessler@ --- usr.sbin/bgpctl/bgpctl.c | 41 ++++--------------- usr.sbin/bgpctl/parser.c | 103 ++++++++++++++++++----------------------------- usr.sbin/bgpctl/parser.h | 3 +- 3 files changed, 47 insertions(+), 100 deletions(-) (limited to 'usr.sbin/bgpctl') diff --git a/usr.sbin/bgpctl/bgpctl.c b/usr.sbin/bgpctl/bgpctl.c index ee67b6b7e21..81dc052e4a1 100644 --- a/usr.sbin/bgpctl/bgpctl.c +++ b/usr.sbin/bgpctl/bgpctl.c @@ -1,4 +1,4 @@ -/* $OpenBSD: bgpctl.c,v 1.223 2018/11/01 10:09:52 denis Exp $ */ +/* $OpenBSD: bgpctl.c,v 1.224 2018/11/28 08:33:59 claudio Exp $ */ /* * Copyright (c) 2003 Henning Brauer @@ -173,14 +173,7 @@ main(int argc, char *argv[]) ribreq.prefix = res->addr; ribreq.prefixlen = res->prefixlen; } - if (res->community.as != COMMUNITY_UNSET && - res->community.type != COMMUNITY_UNSET) - ribreq.community = res->community; - if (res->large_community.as != COMMUNITY_UNSET && - res->large_community.ld1 != COMMUNITY_UNSET && - res->large_community.ld2 != COMMUNITY_UNSET) - ribreq.large_community = res->large_community; - /* XXX extended communities missing? */ + /* XXX currently no communities support */ ribreq.neighbor = neighbor; ribreq.aid = res->aid; ribreq.flags = res->flags; @@ -277,30 +270,17 @@ main(int argc, char *argv[]) case SHOW_RIB: bzero(&ribreq, sizeof(ribreq)); type = IMSG_CTL_SHOW_RIB; - if (res->as.type != AS_UNDEF) { - ribreq.as = res->as; - type = IMSG_CTL_SHOW_RIB_AS; - } if (res->addr.aid) { ribreq.prefix = res->addr; ribreq.prefixlen = res->prefixlen; type = IMSG_CTL_SHOW_RIB_PREFIX; } - if (res->community.as != COMMUNITY_UNSET && - res->community.type != COMMUNITY_UNSET) { + if (res->as.type != AS_UNDEF) + ribreq.as = res->as; + if (res->community.type != COMMUNITY_TYPE_NONE) ribreq.community = res->community; - type = IMSG_CTL_SHOW_RIB_COMMUNITY; - } - if (res->extcommunity.flags == EXT_COMMUNITY_FLAG_VALID) { + if (res->extcommunity.flags == EXT_COMMUNITY_FLAG_VALID) ribreq.extcommunity = res->extcommunity; - type = IMSG_CTL_SHOW_RIB_EXTCOMMUNITY; - } - if (res->large_community.as != COMMUNITY_UNSET && - res->large_community.ld1 != COMMUNITY_UNSET && - res->large_community.ld2 != COMMUNITY_UNSET) { - ribreq.large_community = res->large_community; - type = IMSG_CTL_SHOW_RIB_LARGECOMMUNITY; - } ribreq.neighbor = neighbor; strlcpy(ribreq.rib, res->rib, sizeof(ribreq.rib)); ribreq.aid = res->aid; @@ -399,14 +379,7 @@ main(int argc, char *argv[]) ribreq.prefix = res->addr; ribreq.prefixlen = res->prefixlen; } - if (res->community.as != COMMUNITY_UNSET && - res->community.type != COMMUNITY_UNSET) - ribreq.community = res->community; - if (res->large_community.as != COMMUNITY_UNSET && - res->large_community.ld1 != COMMUNITY_UNSET && - res->large_community.ld2 != COMMUNITY_UNSET) - ribreq.large_community = res->large_community; - /* XXX ext communities missing? */ + /* XXX currently no community support */ ribreq.neighbor = neighbor; ribreq.aid = res->aid; ribreq.flags = res->flags; diff --git a/usr.sbin/bgpctl/parser.c b/usr.sbin/bgpctl/parser.c index 150a05d7a03..29eba2ef280 100644 --- a/usr.sbin/bgpctl/parser.c +++ b/usr.sbin/bgpctl/parser.c @@ -1,4 +1,4 @@ -/* $OpenBSD: parser.c,v 1.86 2018/10/03 11:36:39 denis Exp $ */ +/* $OpenBSD: parser.c,v 1.87 2018/11/28 08:33:59 claudio Exp $ */ /* * Copyright (c) 2003, 2004 Henning Brauer @@ -478,12 +478,10 @@ int parse_addr(const char *, struct bgpd_addr *); int parse_asnum(const char *, size_t, u_int32_t *); int parse_number(const char *, struct parse_result *, enum token_type); -int getcommunity(const char *); int parse_community(const char *, struct parse_result *); int parsesubtype(const char *, u_int8_t *, u_int8_t *); int parseextvalue(const char *, u_int32_t *); u_int parseextcommunity(const char *, struct parse_result *); -u_int getlargecommunity(const char *); int parse_largecommunity(const char *, struct parse_result *); int parse_nexthop(const char *, struct parse_result *); @@ -496,11 +494,6 @@ parse(int argc, char *argv[]) const struct token *match; bzero(&res, sizeof(res)); - res.community.as = COMMUNITY_UNSET; - res.community.type = COMMUNITY_UNSET; - res.large_community.as = COMMUNITY_UNSET; - res.large_community.ld1 = COMMUNITY_UNSET; - res.large_community.ld2 = COMMUNITY_UNSET; res.rtableid = getrtable(); TAILQ_INIT(&res.set); if ((res.irr_outdir = getcwd(NULL, 0)) == NULL) { @@ -1019,19 +1012,26 @@ parse_number(const char *word, struct parse_result *r, enum token_type type) return (1); } -int -getcommunity(const char *s) +static u_int32_t +getcommunity(const char *s, int large, u_int8_t *flag) { + int64_t max = USHRT_MAX; const char *errstr; - u_int16_t uval; + u_int32_t uval; + + if (strcmp(s, "*") == 0) { + *flag = COMMUNITY_ANY; + return (0); + } - if (strcmp(s, "*") == 0) - return (COMMUNITY_ANY); + if (large) + max = UINT_MAX; - uval = strtonum(s, 0, USHRT_MAX, &errstr); + uval = strtonum(s, 0, max, &errstr); if (errstr) errx(1, "Community is %s: %s", errstr, s); + *flag = 0; return (uval); } @@ -1040,7 +1040,8 @@ parse_community(const char *word, struct parse_result *r) { struct filter_set *fs; char *p; - int as, type; + u_int32_t as, type; + u_int8_t asflag, tflag; /* Well-known communities */ if (strcasecmp(word, "GRACEFUL_SHUTDOWN") == 0) { @@ -1075,33 +1076,20 @@ parse_community(const char *word, struct parse_result *r) } *p++ = 0; - as = getcommunity(word); - type = getcommunity(p); + as = getcommunity(word, 0, &asflag); + type = getcommunity(p, 0, &tflag); done: - if (as == 0) { - fprintf(stderr, "Invalid community\n"); - return (0); - } - if (as == COMMUNITY_WELLKNOWN) - switch (type) { - case COMMUNITY_GRACEFUL_SHUTDOWN: - case COMMUNITY_NO_EXPORT: - case COMMUNITY_NO_ADVERTISE: - case COMMUNITY_NO_EXPSUBCONFED: - case COMMUNITY_BLACKHOLE: - /* valid */ - break; - } - if ((fs = calloc(1, sizeof(struct filter_set))) == NULL) err(1, NULL); fs->type = ACTION_SET_COMMUNITY; - fs->action.community.as = as; - fs->action.community.type = type; + fs->action.community.type = COMMUNITY_TYPE_BASIC; + fs->action.community.data1 = as; + fs->action.community.data2 = type; + fs->action.community.dflag1 = asflag; + fs->action.community.dflag2 = tflag; - r->community.as = as; - r->community.type = type; + r->community = fs->action.community; TAILQ_INSERT_TAIL(&r->set, fs, entry); return (1); @@ -1285,22 +1273,6 @@ parseextcommunity(const char *word, struct parse_result *r) return (0); } -u_int -getlargecommunity(const char *s) -{ - const char *errstr; - u_int32_t uval; - - if (strcmp(s, "*") == 0) - return (COMMUNITY_ANY); - - uval = strtonum(s, 0, UINT_MAX, &errstr); - if (errstr) - errx(1, "Large Community is %s: %s", errstr, s); - - return (uval); -} - int parse_largecommunity(const char *word, struct parse_result *r) { @@ -1308,7 +1280,8 @@ parse_largecommunity(const char *word, struct parse_result *r) char *p, *po = strdup(word); char *array[3] = { NULL, NULL, NULL }; char *val; - int64_t as, ld1, ld2; + u_int32_t as, ld1, ld2; + u_int8_t asflag, ld1flag, ld2flag; int i = 0; p = po; @@ -1320,22 +1293,24 @@ parse_largecommunity(const char *word, struct parse_result *r) if ((p != NULL) || !(array[0] && array[1] && array[2])) errx(1, "Invalid Large-Community syntax"); - as = getlargecommunity(array[0]); - ld1 = getlargecommunity(array[1]); - ld2 = getlargecommunity(array[2]); + as = getcommunity(array[0], 1, &asflag); + ld1 = getcommunity(array[1], 1, &ld1flag); + ld2 = getcommunity(array[2], 1, &ld2flag); free(po); if ((fs = calloc(1, sizeof(struct filter_set))) == NULL) err(1, NULL); - fs->type = ACTION_SET_LARGE_COMMUNITY; - fs->action.large_community.as = as; - fs->action.large_community.ld1 = ld1; - fs->action.large_community.ld2 = ld2; - - r->large_community.as = as; - r->large_community.ld1 = ld1; - r->large_community.ld2 = ld2; + fs->type = ACTION_SET_COMMUNITY; + fs->action.community.type = COMMUNITY_TYPE_LARGE; + fs->action.community.data1 = as; + fs->action.community.data2 = ld1; + fs->action.community.data3 = ld2; + fs->action.community.dflag1 = asflag; + fs->action.community.dflag2 = ld1flag; + fs->action.community.dflag3 = ld2flag; + + r->community = fs->action.community; TAILQ_INSERT_TAIL(&r->set, fs, entry); return (1); diff --git a/usr.sbin/bgpctl/parser.h b/usr.sbin/bgpctl/parser.h index ea5d69bdbc7..6a11d6aa667 100644 --- a/usr.sbin/bgpctl/parser.h +++ b/usr.sbin/bgpctl/parser.h @@ -1,4 +1,4 @@ -/* $OpenBSD: parser.h,v 1.31 2018/10/01 23:09:53 job Exp $ */ +/* $OpenBSD: parser.h,v 1.32 2018/11/28 08:33:59 claudio Exp $ */ /* * Copyright (c) 2003, 2004 Henning Brauer @@ -64,7 +64,6 @@ struct parse_result { struct filter_set_head set; struct filter_community community; struct filter_extcommunity extcommunity; - struct filter_largecommunity large_community; char peerdesc[PEER_DESCR_LEN]; char rib[PEER_DESCR_LEN]; char shutcomm[SHUT_COMM_LEN]; -- cgit v1.2.3