summaryrefslogtreecommitdiff
path: root/usr.sbin/bgpd
diff options
context:
space:
mode:
Diffstat (limited to 'usr.sbin/bgpd')
-rw-r--r--usr.sbin/bgpd/bgpd.h6
-rw-r--r--usr.sbin/bgpd/rde.c5
-rw-r--r--usr.sbin/bgpd/rde.h8
-rw-r--r--usr.sbin/bgpd/rde_attr.c63
-rw-r--r--usr.sbin/bgpd/rde_filter.c5
-rw-r--r--usr.sbin/bgpd/rde_rib.c62
-rw-r--r--usr.sbin/bgpd/util.c123
7 files changed, 136 insertions, 136 deletions
diff --git a/usr.sbin/bgpd/bgpd.h b/usr.sbin/bgpd/bgpd.h
index 1626f0aca12..80e7e407522 100644
--- a/usr.sbin/bgpd/bgpd.h
+++ b/usr.sbin/bgpd/bgpd.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: bgpd.h,v 1.266 2011/09/19 11:18:11 claudio Exp $ */
+/* $OpenBSD: bgpd.h,v 1.267 2011/09/20 21:19:06 claudio Exp $ */
/*
* Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org>
@@ -986,6 +986,10 @@ const char *log_ext_subtype(u_int8_t);
int aspath_snprint(char *, size_t, void *, u_int16_t);
int aspath_asprint(char **, void *, u_int16_t);
size_t aspath_strlen(void *, u_int16_t);
+int aspath_match(void *, u_int16_t, enum as_spec, u_int32_t);
+u_int32_t aspath_extract(const void *, int);
+int prefix_compare(const struct bgpd_addr *,
+ const struct bgpd_addr *, int);
in_addr_t prefixlen2mask(u_int8_t);
void inet6applymask(struct in6_addr *, const struct in6_addr *,
int);
diff --git a/usr.sbin/bgpd/rde.c b/usr.sbin/bgpd/rde.c
index be5e4f91750..46d140ba97a 100644
--- a/usr.sbin/bgpd/rde.c
+++ b/usr.sbin/bgpd/rde.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: rde.c,v 1.310 2011/09/19 11:18:11 claudio Exp $ */
+/* $OpenBSD: rde.c,v 1.311 2011/09/20 21:19:06 claudio Exp $ */
/*
* Copyright (c) 2003, 2004 Henning Brauer <henning@openbsd.org>
@@ -2184,7 +2184,8 @@ rde_dump_filter(struct prefix *p, struct ctl_show_rib_request *req)
if (req->peerid && req->peerid != p->aspath->peer->conf.id)
return;
if (req->type == IMSG_CTL_SHOW_RIB_AS &&
- !aspath_match(p->aspath->aspath, req->as.type, req->as.as))
+ !aspath_match(p->aspath->aspath->data,
+ p->aspath->aspath->len, req->as.type, req->as.as))
return;
if (req->type == IMSG_CTL_SHOW_RIB_COMMUNITY &&
!community_match(p->aspath, req->community.as,
diff --git a/usr.sbin/bgpd/rde.h b/usr.sbin/bgpd/rde.h
index 1e4b3ca378b..38b8363b08e 100644
--- a/usr.sbin/bgpd/rde.h
+++ b/usr.sbin/bgpd/rde.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: rde.h,v 1.140 2011/09/18 09:31:25 claudio Exp $ */
+/* $OpenBSD: rde.h,v 1.141 2011/09/20 21:19:06 claudio Exp $ */
/*
* Copyright (c) 2003, 2004 Claudio Jeker <claudio@openbsd.org> and
@@ -355,7 +355,6 @@ u_int32_t aspath_neighbor(struct aspath *);
int aspath_loopfree(struct aspath *, u_int32_t);
int aspath_compare(struct aspath *, struct aspath *);
u_char *aspath_prepend(struct aspath *, u_int32_t, int, u_int16_t *);
-int aspath_match(struct aspath *, enum as_spec, u_int32_t);
int aspath_lenmatch(struct aspath *, enum aslen_spec, u_int);
int community_match(struct rde_aspath *, int, int);
int community_set(struct rde_aspath *, int, int);
@@ -434,8 +433,6 @@ struct rde_aspath *path_get(void);
void path_put(struct rde_aspath *);
#define PREFIX_SIZE(x) (((x) + 7) / 8 + 1)
-int prefix_compare(const struct bgpd_addr *,
- const struct bgpd_addr *, int);
struct prefix *prefix_get(struct rib *, struct rde_peer *,
struct bgpd_addr *, int, u_int32_t);
int prefix_add(struct rib *, struct rde_aspath *,
@@ -482,7 +479,4 @@ u_char *up_dump_mp_unreach(u_char *, u_int16_t *, struct rde_peer *,
int up_dump_mp_reach(u_char *, u_int16_t *, struct rde_peer *,
u_int8_t);
-/* util.c */
-u_int32_t aspath_extract(const void *, int);
-
#endif /* __RDE_H__ */
diff --git a/usr.sbin/bgpd/rde_attr.c b/usr.sbin/bgpd/rde_attr.c
index 097472a877a..1e2b1915b33 100644
--- a/usr.sbin/bgpd/rde_attr.c
+++ b/usr.sbin/bgpd/rde_attr.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: rde_attr.c,v 1.88 2010/12/31 21:22:42 guenther Exp $ */
+/* $OpenBSD: rde_attr.c,v 1.89 2011/09/20 21:19:06 claudio Exp $ */
/*
* Copyright (c) 2004 Claudio Jeker <claudio@openbsd.org>
@@ -923,67 +923,6 @@ aspath_prepend(struct aspath *asp, u_int32_t as, int quantum, u_int16_t *len)
return (p);
}
-/* we need to be able to search more than one as */
-int
-aspath_match(struct aspath *a, enum as_spec type, u_int32_t as)
-{
- u_int8_t *seg;
- int final;
- u_int16_t len, seg_size;
- u_int8_t i, seg_type, seg_len;
-
- if (type == AS_EMPTY) {
- if (a->len == 0)
- return (1);
- else
- return (0);
- }
-
- final = 0;
- seg = a->data;
- for (len = a->len; len > 0; len -= seg_size, seg += seg_size) {
- seg_type = seg[0];
- seg_len = seg[1];
- seg_size = 2 + sizeof(u_int32_t) * seg_len;
-
- final = (len == seg_size);
-
- /* just check the first (leftmost) AS */
- if (type == AS_PEER) {
- if (as == aspath_extract(seg, 0))
- return (1);
- else
- return (0);
- }
- /* just check the final (rightmost) AS */
- if (type == AS_SOURCE) {
- /* not yet in the final segment */
- if (!final)
- continue;
-
- if (as == aspath_extract(seg, seg_len - 1))
- return (1);
- else
- return (0);
- }
-
- /* AS_TRANSIT or AS_ALL */
- for (i = 0; i < seg_len; i++) {
- if (as == aspath_extract(seg, i)) {
- /*
- * the source (rightmost) AS is excluded from
- * AS_TRANSIT matches.
- */
- if (final && i == seg_len - 1 &&
- type == AS_TRANSIT)
- return (0);
- return (1);
- }
- }
- }
- return (0);
-}
-
int
aspath_lenmatch(struct aspath *a, enum aslen_spec type, u_int aslen)
{
diff --git a/usr.sbin/bgpd/rde_filter.c b/usr.sbin/bgpd/rde_filter.c
index 24d97cc6946..d2f630155c4 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.66 2011/05/01 12:56:04 claudio Exp $ */
+/* $OpenBSD: rde_filter.c,v 1.67 2011/09/20 21:19:06 claudio Exp $ */
/*
* Copyright (c) 2004 Claudio Jeker <claudio@openbsd.org>
@@ -277,7 +277,8 @@ rde_filter_match(struct filter_rule *f, struct rde_aspath *asp,
pas = peer->conf.remote_as;
else
pas = f->match.as.as;
- if (aspath_match(asp->aspath, f->match.as.type, pas) == 0)
+ if (aspath_match(asp->aspath->data, asp->aspath->len,
+ f->match.as.type, pas) == 0)
return (0);
}
diff --git a/usr.sbin/bgpd/rde_rib.c b/usr.sbin/bgpd/rde_rib.c
index a7297ca6004..bbd472dfd1e 100644
--- a/usr.sbin/bgpd/rde_rib.c
+++ b/usr.sbin/bgpd/rde_rib.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: rde_rib.c,v 1.129 2011/09/17 16:29:44 claudio Exp $ */
+/* $OpenBSD: rde_rib.c,v 1.130 2011/09/20 21:19:06 claudio Exp $ */
/*
* Copyright (c) 2003, 2004 Claudio Jeker <claudio@openbsd.org>
@@ -627,66 +627,6 @@ static void prefix_link(struct prefix *, struct rib_entry *,
struct rde_aspath *);
static void prefix_unlink(struct prefix *);
-int
-prefix_compare(const struct bgpd_addr *a, const struct bgpd_addr *b,
- int prefixlen)
-{
- in_addr_t mask, aa, ba;
- int i;
- u_int8_t m;
-
- if (a->aid != b->aid)
- return (a->aid - b->aid);
-
- switch (a->aid) {
- case AID_INET:
- if (prefixlen > 32)
- fatalx("prefix_cmp: bad IPv4 prefixlen");
- mask = htonl(prefixlen2mask(prefixlen));
- aa = ntohl(a->v4.s_addr & mask);
- ba = ntohl(b->v4.s_addr & mask);
- if (aa != ba)
- return (aa - ba);
- return (0);
- case AID_INET6:
- if (prefixlen > 128)
- fatalx("prefix_cmp: bad IPv6 prefixlen");
- for (i = 0; i < prefixlen / 8; i++)
- if (a->v6.s6_addr[i] != b->v6.s6_addr[i])
- return (a->v6.s6_addr[i] - b->v6.s6_addr[i]);
- i = prefixlen % 8;
- if (i) {
- m = 0xff00 >> i;
- if ((a->v6.s6_addr[prefixlen / 8] & m) !=
- (b->v6.s6_addr[prefixlen / 8] & m))
- return ((a->v6.s6_addr[prefixlen / 8] & m) -
- (b->v6.s6_addr[prefixlen / 8] & m));
- }
- return (0);
- case AID_VPN_IPv4:
- if (prefixlen > 32)
- fatalx("prefix_cmp: bad IPv4 VPN prefixlen");
- if (betoh64(a->vpn4.rd) > betoh64(b->vpn4.rd))
- return (1);
- if (betoh64(a->vpn4.rd) < betoh64(b->vpn4.rd))
- return (-1);
- mask = htonl(prefixlen2mask(prefixlen));
- aa = ntohl(a->vpn4.addr.s_addr & mask);
- ba = ntohl(b->vpn4.addr.s_addr & mask);
- if (aa != ba)
- return (aa - ba);
- if (a->vpn4.labellen > b->vpn4.labellen)
- return (1);
- if (a->vpn4.labellen < b->vpn4.labellen)
- return (-1);
- return (memcmp(a->vpn4.labelstack, b->vpn4.labelstack,
- a->vpn4.labellen));
- default:
- fatalx("prefix_cmp: unknown af");
- }
- return (-1);
-}
-
/*
* search for specified prefix of a peer. Returns NULL if not found.
*/
diff --git a/usr.sbin/bgpd/util.c b/usr.sbin/bgpd/util.c
index 412bf3b3345..0f6a799d2e6 100644
--- a/usr.sbin/bgpd/util.c
+++ b/usr.sbin/bgpd/util.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: util.c,v 1.13 2010/11/18 12:18:31 claudio Exp $ */
+/* $OpenBSD: util.c,v 1.14 2011/09/20 21:19:07 claudio Exp $ */
/*
* Copyright (c) 2006 Claudio Jeker <claudio@openbsd.org>
@@ -332,6 +332,67 @@ aspath_strlen(void *data, u_int16_t len)
return (total_size);
}
+/* we need to be able to search more than one as */
+int
+aspath_match(void *data, u_int16_t len, enum as_spec type, u_int32_t as)
+{
+ u_int8_t *seg;
+ int final;
+ u_int16_t seg_size;
+ u_int8_t i, seg_type, seg_len;
+
+ if (type == AS_EMPTY) {
+ if (len == 0)
+ return (1);
+ else
+ return (0);
+ }
+
+ final = 0;
+ seg = data;
+ for (; len > 0; len -= seg_size, seg += seg_size) {
+ seg_type = seg[0];
+ seg_len = seg[1];
+ seg_size = 2 + sizeof(u_int32_t) * seg_len;
+
+ final = (len == seg_size);
+
+ /* just check the first (leftmost) AS */
+ if (type == AS_PEER) {
+ if (as == aspath_extract(seg, 0))
+ return (1);
+ else
+ return (0);
+ }
+ /* just check the final (rightmost) AS */
+ if (type == AS_SOURCE) {
+ /* not yet in the final segment */
+ if (!final)
+ continue;
+
+ if (as == aspath_extract(seg, seg_len - 1))
+ return (1);
+ else
+ return (0);
+ }
+
+ /* AS_TRANSIT or AS_ALL */
+ for (i = 0; i < seg_len; i++) {
+ if (as == aspath_extract(seg, i)) {
+ /*
+ * the source (rightmost) AS is excluded from
+ * AS_TRANSIT matches.
+ */
+ if (final && i == seg_len - 1 &&
+ type == AS_TRANSIT)
+ return (0);
+ return (1);
+ }
+ }
+ }
+ return (0);
+}
+
/*
* Extract the asnum out of the as segment at the specified position.
* Direct access is not possible because of non-aligned reads.
@@ -348,6 +409,66 @@ aspath_extract(const void *seg, int pos)
return (ntohl(as));
}
+int
+prefix_compare(const struct bgpd_addr *a, const struct bgpd_addr *b,
+ int prefixlen)
+{
+ in_addr_t mask, aa, ba;
+ int i;
+ u_int8_t m;
+
+ if (a->aid != b->aid)
+ return (a->aid - b->aid);
+
+ switch (a->aid) {
+ case AID_INET:
+ if (prefixlen > 32)
+ fatalx("prefix_cmp: bad IPv4 prefixlen");
+ mask = htonl(prefixlen2mask(prefixlen));
+ aa = ntohl(a->v4.s_addr & mask);
+ ba = ntohl(b->v4.s_addr & mask);
+ if (aa != ba)
+ return (aa - ba);
+ return (0);
+ case AID_INET6:
+ if (prefixlen > 128)
+ fatalx("prefix_cmp: bad IPv6 prefixlen");
+ for (i = 0; i < prefixlen / 8; i++)
+ if (a->v6.s6_addr[i] != b->v6.s6_addr[i])
+ return (a->v6.s6_addr[i] - b->v6.s6_addr[i]);
+ i = prefixlen % 8;
+ if (i) {
+ m = 0xff00 >> i;
+ if ((a->v6.s6_addr[prefixlen / 8] & m) !=
+ (b->v6.s6_addr[prefixlen / 8] & m))
+ return ((a->v6.s6_addr[prefixlen / 8] & m) -
+ (b->v6.s6_addr[prefixlen / 8] & m));
+ }
+ return (0);
+ case AID_VPN_IPv4:
+ if (prefixlen > 32)
+ fatalx("prefix_cmp: bad IPv4 VPN prefixlen");
+ if (betoh64(a->vpn4.rd) > betoh64(b->vpn4.rd))
+ return (1);
+ if (betoh64(a->vpn4.rd) < betoh64(b->vpn4.rd))
+ return (-1);
+ mask = htonl(prefixlen2mask(prefixlen));
+ aa = ntohl(a->vpn4.addr.s_addr & mask);
+ ba = ntohl(b->vpn4.addr.s_addr & mask);
+ if (aa != ba)
+ return (aa - ba);
+ if (a->vpn4.labellen > b->vpn4.labellen)
+ return (1);
+ if (a->vpn4.labellen < b->vpn4.labellen)
+ return (-1);
+ return (memcmp(a->vpn4.labelstack, b->vpn4.labelstack,
+ a->vpn4.labellen));
+ default:
+ fatalx("prefix_cmp: unknown af");
+ }
+ return (-1);
+}
+
in_addr_t
prefixlen2mask(u_int8_t prefixlen)
{