summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sys/net/if_bridge.c8
-rw-r--r--sys/net/if_pfsync.c5
-rw-r--r--sys/net/if_pfsync.h4
-rw-r--r--sys/net/pfkeyv2.c100
-rw-r--r--sys/net/pfkeyv2.h7
-rw-r--r--sys/net/route.c10
-rw-r--r--sys/netinet/ip_ah.c11
-rw-r--r--sys/netinet/ip_esp.c13
-rw-r--r--sys/netinet/ip_input.c8
-rw-r--r--sys/netinet/ip_ipcomp.c8
-rw-r--r--sys/netinet/ip_ipsp.c90
-rw-r--r--sys/netinet/ip_ipsp.h23
-rw-r--r--sys/netinet/ip_output.c12
-rw-r--r--sys/netinet/ip_spd.c26
-rw-r--r--sys/netinet/ipsec_input.c25
-rw-r--r--sys/netinet/ipsec_output.c6
-rw-r--r--sys/netinet/tcp_input.c20
-rw-r--r--sys/netinet/tcp_output.c5
-rw-r--r--sys/netinet/tcp_var.h4
-rw-r--r--sys/netinet/udp_usrreq.c5
-rw-r--r--sys/netinet6/ip6_forward.c12
-rw-r--r--sys/netinet6/ip6_output.c17
22 files changed, 267 insertions, 152 deletions
diff --git a/sys/net/if_bridge.c b/sys/net/if_bridge.c
index 5dd8b2e9217..4fbe0470dbe 100644
--- a/sys/net/if_bridge.c
+++ b/sys/net/if_bridge.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: if_bridge.c,v 1.181 2010/07/02 02:40:16 blambert Exp $ */
+/* $OpenBSD: if_bridge.c,v 1.182 2010/07/09 16:58:06 reyk Exp $ */
/*
* Copyright (c) 1999, 2000 Jason L. Wright (jason@thought.net)
@@ -2402,7 +2402,7 @@ bridge_ipsec(struct bridge_softc *sc, struct ifnet *ifp,
s = spltdb();
- tdb = gettdb(spi, &dst, proto);
+ tdb = gettdb(ifp->if_rdomain, spi, &dst, proto);
if (tdb != NULL && (tdb->tdb_flags & TDBF_INVALID) == 0 &&
tdb->tdb_xform != NULL) {
if (tdb->tdb_first_use == 0) {
@@ -2457,7 +2457,7 @@ bridge_ipsec(struct bridge_softc *sc, struct ifnet *ifp,
switch (af) {
#ifdef INET
case AF_INET:
- if ((encif = enc_getif(0,
+ if ((encif = enc_getif(tdb->tdb_rdomain,
tdb->tdb_tap)) == NULL ||
pf_test(dir, encif,
&m, NULL) != PF_PASS) {
@@ -2468,7 +2468,7 @@ bridge_ipsec(struct bridge_softc *sc, struct ifnet *ifp,
#endif /* INET */
#ifdef INET6
case AF_INET6:
- if ((encif = enc_getif(0,
+ if ((encif = enc_getif(tdb->tdb_rdomain,
tdb->tdb_tap)) == NULL ||
pf_test6(dir, encif,
&m, NULL) != PF_PASS) {
diff --git a/sys/net/if_pfsync.c b/sys/net/if_pfsync.c
index 95894c3cb0c..535205daaf9 100644
--- a/sys/net/if_pfsync.c
+++ b/sys/net/if_pfsync.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: if_pfsync.c,v 1.151 2010/07/09 13:09:34 dlg Exp $ */
+/* $OpenBSD: if_pfsync.c,v 1.152 2010/07/09 16:58:06 reyk Exp $ */
/*
* Copyright (c) 2002 Michael Shalayeff
@@ -1239,7 +1239,7 @@ pfsync_update_net_tdb(struct pfsync_tdb *pt)
goto bad;
s = spltdb();
- tdb = gettdb(pt->spi, &pt->dst, pt->sproto);
+ tdb = gettdb(ntohs(pt->rdomain), pt->spi, &pt->dst, pt->sproto);
if (tdb) {
pt->rpl = ntohl(pt->rpl);
pt->cur_bytes = betoh64(pt->cur_bytes);
@@ -2162,6 +2162,7 @@ pfsync_out_tdb(struct tdb *t, void *buf)
RPL_INCR : 0));
ut->cur_bytes = htobe64(t->tdb_cur_bytes);
ut->sproto = t->tdb_sproto;
+ ut->rdomain = htons(t->tdb_rdomain);
}
void
diff --git a/sys/net/if_pfsync.h b/sys/net/if_pfsync.h
index dafe6d4e43f..ba83a6607ff 100644
--- a/sys/net/if_pfsync.h
+++ b/sys/net/if_pfsync.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: if_pfsync.h,v 1.42 2010/01/12 23:38:02 dlg Exp $ */
+/* $OpenBSD: if_pfsync.h,v 1.43 2010/07/09 16:58:06 reyk Exp $ */
/*
* Copyright (c) 2001 Michael Shalayeff
@@ -216,7 +216,7 @@ struct pfsync_tdb {
u_int64_t cur_bytes;
u_int8_t sproto;
u_int8_t updates;
- u_int8_t _pad[2];
+ u_int16_t rdomain;
} __packed;
/*
diff --git a/sys/net/pfkeyv2.c b/sys/net/pfkeyv2.c
index b5c0178406f..19568d3be13 100644
--- a/sys/net/pfkeyv2.c
+++ b/sys/net/pfkeyv2.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: pfkeyv2.c,v 1.120 2010/07/01 02:09:45 reyk Exp $ */
+/* $OpenBSD: pfkeyv2.c,v 1.121 2010/07/09 16:58:06 reyk Exp $ */
/*
* @(#)COPYRIGHT 1.1 (NRL) 17 January 1995
@@ -159,6 +159,12 @@ pfkeyv2_create(struct socket *socket)
pfkeyv2_socket->socket = socket;
pfkeyv2_socket->pid = curproc->p_pid;
+ /*
+ * XXX we should get this from the socket instead but
+ * XXX rawcb doesn't store the rdomain like inpcb does.
+ */
+ pfkeyv2_socket->rdomain = rtable_l2(curproc->p_p->ps_rtableid);
+
pfkeyv2_sockets = pfkeyv2_socket;
return (0);
@@ -201,7 +207,7 @@ pfkeyv2_release(struct socket *socket)
*/
int
pfkeyv2_sendmessage(void **headers, int mode, struct socket *socket,
- u_int8_t satype, int count)
+ u_int8_t satype, int count, u_int rdomain)
{
int i, j, rval;
void *p, *buffer = NULL;
@@ -272,7 +278,8 @@ pfkeyv2_sendmessage(void **headers, int mode, struct socket *socket,
*/
for (s = pfkeyv2_sockets; s; s = s->next)
if ((s->flags & PFKEYV2_SOCKETFLAGS_PROMISC) &&
- (s->socket != socket))
+ (s->socket != socket) &&
+ (s->rdomain == rdomain))
pfkey_sendup(s->socket, packet, 1);
/* Done, let's be a bit paranoid */
@@ -286,7 +293,8 @@ pfkeyv2_sendmessage(void **headers, int mode, struct socket *socket,
* the specified satype (e.g., all IPSEC-ESP negotiators)
*/
for (s = pfkeyv2_sockets; s; s = s->next)
- if (s->flags & PFKEYV2_SOCKETFLAGS_REGISTERED) {
+ if ((s->flags & PFKEYV2_SOCKETFLAGS_REGISTERED) &&
+ (s->rdomain == rdomain)) {
if (!satype) /* Just send to everyone registered */
pfkey_sendup(s->socket, packet, 1);
else {
@@ -316,7 +324,8 @@ pfkeyv2_sendmessage(void **headers, int mode, struct socket *socket,
/* Send to all registered promiscuous listeners */
for (s = pfkeyv2_sockets; s; s = s->next)
if ((s->flags & PFKEYV2_SOCKETFLAGS_PROMISC) &&
- !(s->flags & PFKEYV2_SOCKETFLAGS_REGISTERED))
+ !(s->flags & PFKEYV2_SOCKETFLAGS_REGISTERED) &&
+ (s->rdomain == rdomain))
pfkey_sendup(s->socket, packet, 1);
m_freem(packet);
@@ -324,9 +333,10 @@ pfkeyv2_sendmessage(void **headers, int mode, struct socket *socket,
case PFKEYV2_SENDMESSAGE_BROADCAST:
/* Send message to all sockets */
- for (s = pfkeyv2_sockets; s; s = s->next)
- pfkey_sendup(s->socket, packet, 1);
-
+ for (s = pfkeyv2_sockets; s; s = s->next) {
+ if (s->rdomain == rdomain)
+ pfkey_sendup(s->socket, packet, 1);
+ }
m_freem(packet);
break;
}
@@ -742,7 +752,8 @@ pfkeyv2_dump_walker(struct tdb *sa, void *state, int last)
/* Send the message to the specified socket */
rval = pfkeyv2_sendmessage(headers,
- PFKEYV2_SENDMESSAGE_UNICAST, dump_state->socket, 0, 0);
+ PFKEYV2_SENDMESSAGE_UNICAST, dump_state->socket, 0, 0,
+ sa->tdb_rdomain);
free(buffer, M_PFKEY);
if (rval)
@@ -859,6 +870,8 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
struct sadb_supported *ssup;
struct sadb_ident *sid;
+ u_int rdomain;
+
/* Verify that we received this over a legitimate pfkeyv2 socket */
bzero(headers, sizeof(headers));
@@ -872,6 +885,8 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
goto ret;
}
+ rdomain = pfkeyv2_socket->rdomain;
+
/* If we have any promiscuous listeners, send them a copy of the message */
if (npromisc) {
struct mbuf *packet;
@@ -899,9 +914,11 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
goto ret;
/* Send to all promiscuous listeners */
- for (so = pfkeyv2_sockets; so; so = so->next)
- if (so->flags & PFKEYV2_SOCKETFLAGS_PROMISC)
+ for (so = pfkeyv2_sockets; so; so = so->next) {
+ if ((so->flags & PFKEYV2_SOCKETFLAGS_PROMISC) &&
+ (so->rdomain == rdomain))
pfkey_sendup(so->socket, packet, 1);
+ }
/* Paranoid */
m_zero(packet);
@@ -934,9 +951,9 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
/* Find an unused SA identifier */
sprng = (struct sadb_spirange *) headers[SADB_EXT_SPIRANGE];
- sa.tdb_spi = reserve_spi(sprng->sadb_spirange_min,
- sprng->sadb_spirange_max, &sa.tdb_src, &sa.tdb_dst,
- sa.tdb_sproto, &rval);
+ sa.tdb_spi = reserve_spi(rdomain,
+ sprng->sadb_spirange_min, sprng->sadb_spirange_max,
+ &sa.tdb_src, &sa.tdb_dst, sa.tdb_sproto, &rval);
if (sa.tdb_spi == 0)
goto ret;
@@ -989,7 +1006,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
s = spltdb();
/* Find TDB */
- sa2 = gettdb(ssa->sadb_sa_spi, sunionp,
+ sa2 = gettdb(rdomain, ssa->sadb_sa_spi, sunionp,
SADB_X_GETSPROTO(smsg->sadb_msg_satype));
/* If there's no such SA, we're done */
@@ -1005,7 +1022,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
int alg;
/* Create new TDB */
- freeme = tdb_alloc();
+ freeme = tdb_alloc(rdomain);
bzero(&ii, sizeof(struct ipsecinit));
newsa = (struct tdb *) freeme;
@@ -1150,7 +1167,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
s = spltdb();
- sa2 = gettdb(ssa->sadb_sa_spi, sunionp,
+ sa2 = gettdb(rdomain, ssa->sadb_sa_spi, sunionp,
SADB_X_GETSPROTO(smsg->sadb_msg_satype));
/* We can't add an existing SA! */
@@ -1166,7 +1183,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
}
/* Allocate and initialize new TDB */
- freeme = tdb_alloc();
+ freeme = tdb_alloc(rdomain);
{
struct tdb *newsa = (struct tdb *) freeme;
@@ -1262,7 +1279,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
sizeof(struct sadb_address));
s = spltdb();
- sa2 = gettdb(ssa->sadb_sa_spi, sunionp,
+ sa2 = gettdb(rdomain, ssa->sadb_sa_spi, sunionp,
SADB_X_GETSPROTO(smsg->sadb_msg_satype));
if (sa2 == NULL) {
rval = ESRCH;
@@ -1298,7 +1315,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
s = spltdb();
- sa2 = gettdb(ssa->sadb_sa_spi, sunionp,
+ sa2 = gettdb(rdomain, ssa->sadb_sa_spi, sunionp,
SADB_X_GETSPROTO(smsg->sadb_msg_satype));
if (sa2 == NULL) {
rval = ESRCH;
@@ -1398,7 +1415,8 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
for (ipo = TAILQ_FIRST(&ipsec_policy_head);
ipo != NULL; ipo = tmpipo) {
tmpipo = TAILQ_NEXT(ipo, ipo_list);
- if (!(ipo->ipo_flags & IPSP_POLICY_SOCKET))
+ if (!(ipo->ipo_flags & IPSP_POLICY_SOCKET) &&
+ ipo->ipo_rdomain == rdomain)
ipsec_delete_policy(ipo);
}
splx(s);
@@ -1412,7 +1430,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
#endif /* TCP_SIGNATURE */
s = spltdb();
- tdb_walk(pfkeyv2_flush_walker,
+ tdb_walk(rdomain, pfkeyv2_flush_walker,
(u_int8_t *) &(smsg->sadb_msg_satype));
splx(s);
@@ -1431,7 +1449,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
dump_state.socket = socket;
s = spltdb();
- rval = tdb_walk(pfkeyv2_dump_walker, &dump_state);
+ rval = tdb_walk(rdomain, pfkeyv2_dump_walker, &dump_state);
splx(s);
if (!rval)
@@ -1453,7 +1471,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
s = spltdb();
- tdb1 = gettdb(ssa->sadb_sa_spi, sunionp,
+ tdb1 = gettdb(rdomain, ssa->sadb_sa_spi, sunionp,
SADB_X_GETSPROTO(smsg->sadb_msg_satype));
if (tdb1 == NULL) {
rval = ESRCH;
@@ -1465,7 +1483,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
sizeof(struct sadb_address));
sa_proto = ((struct sadb_protocol *) headers[SADB_X_EXT_PROTOCOL]);
- tdb2 = gettdb(ssa->sadb_sa_spi, sunionp,
+ tdb2 = gettdb(rdomain, ssa->sadb_sa_spi, sunionp,
SADB_X_GETSPROTO(sa_proto->sadb_protocol_proto));
if (tdb2 == NULL) {
rval = ESRCH;
@@ -1544,6 +1562,9 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
s = spltdb();
+ /* Set the rdomain that was obtained from the socket */
+ re.re_tableid = rdomain;
+
rtalloc((struct route *) &re);
if (re.re_rt != NULL) {
ipo = ((struct sockaddr_encap *) re.re_rt->rt_gateway)->sen_ipsp;
@@ -1617,6 +1638,8 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
sizeof(struct sockaddr_encap));
bcopy(&encapnetmask, &ipo->ipo_mask,
sizeof(struct sockaddr_encap));
+
+ ipo->ipo_rdomain = rdomain;
}
switch (((struct sadb_protocol *) headers[SADB_X_EXT_FLOW_TYPE])->sadb_protocol_proto) {
@@ -1744,7 +1767,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
(struct sockaddr *)&encapnetmask;
info.rti_flags = RTF_UP | RTF_GATEWAY | RTF_STATIC;
if ((rval = rtrequest1(RTM_ADD, &info, RTP_DEFAULT,
- NULL, 0)) != 0) {
+ NULL, rdomain)) != 0) {
/* Remove from linked list of policies on TDB */
if (ipo->ipo_tdb)
TAILQ_REMOVE(&ipo->ipo_tdb->tdb_policy_head,
@@ -1779,6 +1802,7 @@ pfkeyv2_send(struct socket *socket, void *message, int len)
for (so = pfkeyv2_sockets; so; so = so->next)
if ((so != pfkeyv2_socket) &&
+ (so->rdomain == rdomain) &&
(!smsg->sadb_msg_seq ||
(smsg->sadb_msg_seq == pfkeyv2_socket->pid)))
pfkey_sendup(so->socket, packet, 1);
@@ -1840,7 +1864,7 @@ ret:
goto realret;
}
- rval = pfkeyv2_sendmessage(headers, mode, socket, 0, 0);
+ rval = pfkeyv2_sendmessage(headers, mode, socket, 0, 0, rdomain);
realret:
if (freeme)
@@ -2121,8 +2145,8 @@ pfkeyv2_acquire(struct ipsec_policy *ipo, union sockaddr_union *gw,
/* Send the ACQUIRE message to all compliant registered listeners. */
if ((rval = pfkeyv2_sendmessage(headers,
- PFKEYV2_SENDMESSAGE_REGISTERED, NULL, smsg->sadb_msg_satype, 0))
- != 0)
+ PFKEYV2_SENDMESSAGE_REGISTERED, NULL, smsg->sadb_msg_satype, 0,
+ ipo->ipo_rdomain)) != 0)
goto ret;
rval = 0;
@@ -2203,7 +2227,7 @@ pfkeyv2_expire(struct tdb *sa, u_int16_t type)
export_address(&p, (struct sockaddr *) &sa->tdb_dst);
if ((rval = pfkeyv2_sendmessage(headers, PFKEYV2_SENDMESSAGE_BROADCAST,
- NULL, 0, 0)) != 0)
+ NULL, 0, 0, sa->tdb_rdomain)) != 0)
goto ret;
rval = 0;
@@ -2415,13 +2439,17 @@ ret:
* Caller is responsible for setting at least spltdb().
*/
int
-pfkeyv2_ipo_walk(int (*walker)(struct ipsec_policy *, void *), void *arg)
+pfkeyv2_ipo_walk(u_int rdomain, int (*walker)(struct ipsec_policy *, void *),
+ void *arg)
{
int rval = 0;
struct ipsec_policy *ipo;
- TAILQ_FOREACH(ipo, &ipsec_policy_head, ipo_list)
+ TAILQ_FOREACH(ipo, &ipsec_policy_head, ipo_list) {
+ if (ipo->ipo_rdomain != rdomain)
+ continue;
rval = walker(ipo, (void *)arg);
+ }
return (rval);
}
@@ -2494,6 +2522,7 @@ pfkeyv2_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp,
{
struct pfkeyv2_sysctl_walk w;
int s, error = EINVAL;
+ u_int rdomain;
if (new)
return (EPERM);
@@ -2504,12 +2533,14 @@ pfkeyv2_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp,
w.w_where = oldp;
w.w_len = oldp ? *oldlenp : 0;
+ rdomain = rtable_l2(curproc->p_p->ps_rtableid);
+
switch(w.w_op) {
case NET_KEY_SADB_DUMP:
if ((error = suser(curproc, 0)) != 0)
return (error);
s = spltdb();
- error = tdb_walk(pfkeyv2_sysctl_walker, &w);
+ error = tdb_walk(rdomain, pfkeyv2_sysctl_walker, &w);
splx(s);
if (oldp)
*oldlenp = w.w_where - oldp;
@@ -2519,7 +2550,8 @@ pfkeyv2_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp,
case NET_KEY_SPD_DUMP:
s = spltdb();
- error = pfkeyv2_ipo_walk(pfkeyv2_sysctl_policydumper, &w);
+ error = pfkeyv2_ipo_walk(rdomain,
+ pfkeyv2_sysctl_policydumper, &w);
splx(s);
if (oldp)
*oldlenp = w.w_where - oldp;
diff --git a/sys/net/pfkeyv2.h b/sys/net/pfkeyv2.h
index 6e4d146b374..efe79a1ab1a 100644
--- a/sys/net/pfkeyv2.h
+++ b/sys/net/pfkeyv2.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: pfkeyv2.h,v 1.57 2010/07/01 02:09:45 reyk Exp $ */
+/* $OpenBSD: pfkeyv2.h,v 1.58 2010/07/09 16:58:06 reyk Exp $ */
/*
* @(#)COPYRIGHT 1.1 (NRL) January 1998
*
@@ -412,6 +412,7 @@ struct pfkeyv2_socket
int flags;
uint32_t pid;
uint32_t registration; /* Increase size if SATYPE_MAX > 31 */
+ uint rdomain;
};
struct dump_state
@@ -436,14 +437,14 @@ int pfkeyv2_get(struct tdb *, void **, void **, int *);
int pfkeyv2_policy(struct ipsec_acquire *, void **, void **);
int pfkeyv2_release(struct socket *);
int pfkeyv2_send(struct socket *, void *, int);
-int pfkeyv2_sendmessage(void **, int, struct socket *, u_int8_t, int);
+int pfkeyv2_sendmessage(void **, int, struct socket *, u_int8_t, int, u_int);
int pfkeyv2_dump_policy(struct ipsec_policy *, void **, void **, int *);
int pfkeyv2_dump_walker(struct tdb *, void *, int);
int pfkeyv2_flush_walker(struct tdb *, void *, int);
int pfkeyv2_get_proto_alg(u_int8_t, u_int8_t *, int *);
int pfkeyv2_sysctl(int *, u_int, void *, size_t *, void *, size_t);
int pfkeyv2_sysctl_walker(struct tdb *, void *, int);
-int pfkeyv2_ipo_walk(int (*)(struct ipsec_policy *, void *), void *);
+int pfkeyv2_ipo_walk(u_int, int (*)(struct ipsec_policy *, void *), void *);
int pfkeyv2_sysctl_dump(void *);
int pfkeyv2_sysctl_policydumper(struct ipsec_policy *, void *);
diff --git a/sys/net/route.c b/sys/net/route.c
index 07ae9d72d30..6f5541bcd55 100644
--- a/sys/net/route.c
+++ b/sys/net/route.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: route.c,v 1.124 2010/07/09 15:44:20 claudio Exp $ */
+/* $OpenBSD: route.c,v 1.125 2010/07/09 16:58:06 reyk Exp $ */
/* $NetBSD: route.c,v 1.14 1996/02/13 22:00:46 christos Exp $ */
/*
@@ -129,7 +129,7 @@
#include <netinet/ip_ipsp.h>
#include <net/if_enc.h>
-struct ifaddr *encap_findgwifa(struct sockaddr *);
+struct ifaddr *encap_findgwifa(struct sockaddr *, u_int);
#endif
#define SA(p) ((struct sockaddr *)(p))
@@ -165,11 +165,11 @@ TAILQ_HEAD(rt_labels, rt_label) rt_labels = TAILQ_HEAD_INITIALIZER(rt_labels);
#ifdef IPSEC
struct ifaddr *
-encap_findgwifa(struct sockaddr *gw)
+encap_findgwifa(struct sockaddr *gw, u_int rdomain)
{
struct ifnet *encif;
- if ((encif = enc_getif(0, 0)) == NULL)
+ if ((encif = enc_getif(rdomain, 0)) == NULL)
return (NULL);
return (TAILQ_FIRST(&encif->if_addrlist));
@@ -624,7 +624,7 @@ ifa_ifwithroute(int flags, struct sockaddr *dst, struct sockaddr *gateway,
* enc0.
*/
if (dst && (dst->sa_family == PF_KEY))
- return (encap_findgwifa(gateway));
+ return (encap_findgwifa(gateway, rtableid));
#endif
if ((flags & RTF_GATEWAY) == 0) {
diff --git a/sys/netinet/ip_ah.c b/sys/netinet/ip_ah.c
index 1a9bf0cbd95..eae796f36af 100644
--- a/sys/netinet/ip_ah.c
+++ b/sys/netinet/ip_ah.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_ah.c,v 1.96 2010/07/02 02:40:16 blambert Exp $ */
+/* $OpenBSD: ip_ah.c,v 1.97 2010/07/09 16:58:06 reyk Exp $ */
/*
* The authors of this code are John Ioannidis (ji@tla.org),
* Angelos D. Keromytis (kermit@csd.uch.gr) and
@@ -662,6 +662,7 @@ ah_input(struct mbuf *m, struct tdb *tdb, int skip, int protoff)
tdbi = (struct tdb_ident *) (mtag + 1);
if (tdbi->proto == tdb->tdb_sproto &&
tdbi->spi == tdb->tdb_spi &&
+ tdbi->rdomain == tdb->tdb_rdomain &&
!bcmp(&tdbi->dst, &tdb->tdb_dst,
sizeof(union sockaddr_union)))
break;
@@ -721,6 +722,7 @@ ah_input(struct mbuf *m, struct tdb *tdb, int skip, int protoff)
tc->tc_spi = tdb->tdb_spi;
tc->tc_proto = tdb->tdb_sproto;
tc->tc_ptr = (caddr_t) mtag; /* Save the mtag we've identified. */
+ tc->tc_rdomain = tdb->tdb_rdomain;
bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union));
if (mtag == NULL)
@@ -767,7 +769,7 @@ ah_input_cb(void *op)
s = spltdb();
- tdb = gettdb(tc->tc_spi, &tc->tc_dst, tc->tc_proto);
+ tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto);
if (tdb == NULL) {
free(tc, M_XDATA);
ahstat.ahs_notdb++;
@@ -988,7 +990,7 @@ ah_output(struct mbuf *m, struct tdb *tdb, struct mbuf **mp, int skip,
#if NBPFILTER > 0
struct ifnet *encif;
- if ((encif = enc_getif(0, tdb->tdb_tap)) != NULL) {
+ if ((encif = enc_getif(tdb->tdb_rdomain, tdb->tdb_tap)) != NULL) {
encif->if_opackets++;
encif->if_obytes += m->m_pkthdr.len;
@@ -1249,6 +1251,7 @@ ah_output(struct mbuf *m, struct tdb *tdb, struct mbuf **mp, int skip,
tc->tc_protoff = protoff;
tc->tc_spi = tdb->tdb_spi;
tc->tc_proto = tdb->tdb_sproto;
+ tc->tc_rdomain = tdb->tdb_rdomain;
bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union));
if ((tdb->tdb_flags & TDBF_SKIPCRYPTO) == 0)
@@ -1289,7 +1292,7 @@ ah_output_cb(void *op)
s = spltdb();
- tdb = gettdb(tc->tc_spi, &tc->tc_dst, tc->tc_proto);
+ tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto);
if (tdb == NULL) {
free(tc, M_XDATA);
ahstat.ahs_notdb++;
diff --git a/sys/netinet/ip_esp.c b/sys/netinet/ip_esp.c
index 1ca5f791e7e..66f50499e50 100644
--- a/sys/netinet/ip_esp.c
+++ b/sys/netinet/ip_esp.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_esp.c,v 1.109 2010/07/02 02:40:16 blambert Exp $ */
+/* $OpenBSD: ip_esp.c,v 1.110 2010/07/09 16:58:06 reyk Exp $ */
/*
* The authors of this code are John Ioannidis (ji@tla.org),
* Angelos D. Keromytis (kermit@csd.uch.gr) and
@@ -386,7 +386,8 @@ esp_input(struct mbuf *m, struct tdb *tdb, int skip, int protoff)
tdbi = (struct tdb_ident *) (mtag + 1);
if (tdbi->proto == tdb->tdb_sproto && tdbi->spi == tdb->tdb_spi &&
- !bcmp(&tdbi->dst, &tdb->tdb_dst, sizeof(union sockaddr_union)))
+ tdbi->rdomain == tdb->tdb_rdomain && !bcmp(&tdbi->dst,
+ &tdb->tdb_dst, sizeof(union sockaddr_union)))
break;
}
#else
@@ -449,6 +450,7 @@ esp_input(struct mbuf *m, struct tdb *tdb, int skip, int protoff)
tc->tc_protoff = protoff;
tc->tc_spi = tdb->tdb_spi;
tc->tc_proto = tdb->tdb_sproto;
+ tc->tc_rdomain = tdb->tdb_rdomain;
bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union));
/* Decryption descriptor */
@@ -516,7 +518,7 @@ esp_input_cb(void *op)
s = spltdb();
- tdb = gettdb(tc->tc_spi, &tc->tc_dst, tc->tc_proto);
+ tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto);
if (tdb == NULL) {
free(tc, M_XDATA);
espstat.esps_notdb++;
@@ -733,7 +735,7 @@ esp_output(struct mbuf *m, struct tdb *tdb, struct mbuf **mp, int skip,
#if NBPFILTER > 0
struct ifnet *encif;
- if ((encif = enc_getif(0, tdb->tdb_tap)) != NULL) {
+ if ((encif = enc_getif(tdb->tdb_rdomain, tdb->tdb_tap)) != NULL) {
encif->if_opackets++;
encif->if_obytes += m->m_pkthdr.len;
@@ -963,6 +965,7 @@ esp_output(struct mbuf *m, struct tdb *tdb, struct mbuf **mp, int skip,
tc->tc_spi = tdb->tdb_spi;
tc->tc_proto = tdb->tdb_sproto;
+ tc->tc_rdomain = tdb->tdb_rdomain;
bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union));
/* Crypto operation descriptor. */
@@ -1019,7 +1022,7 @@ esp_output_cb(void *op)
s = spltdb();
- tdb = gettdb(tc->tc_spi, &tc->tc_dst, tc->tc_proto);
+ tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto);
if (tdb == NULL) {
free(tc, M_XDATA);
espstat.esps_notdb++;
diff --git a/sys/netinet/ip_input.c b/sys/netinet/ip_input.c
index e8177a35e42..c2d4d2400e5 100644
--- a/sys/netinet/ip_input.c
+++ b/sys/netinet/ip_input.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_input.c,v 1.181 2010/06/07 13:26:35 henning Exp $ */
+/* $OpenBSD: ip_input.c,v 1.182 2010/07/09 16:58:06 reyk Exp $ */
/* $NetBSD: ip_input.c,v 1.30 1996/03/16 23:53:58 christos Exp $ */
/*
@@ -490,7 +490,8 @@ ipv4_input(m)
s = splnet();
if (mtag != NULL) {
tdbi = (struct tdb_ident *)(mtag + 1);
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi,
+ &tdbi->dst, tdbi->proto);
} else
tdb = NULL;
ipsp_spd_lookup(m, AF_INET, hlen, &error,
@@ -649,7 +650,8 @@ found:
s = splnet();
if (mtag) {
tdbi = (struct tdb_ident *)(mtag + 1);
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi, &tdbi->dst,
+ tdbi->proto);
} else
tdb = NULL;
ipsp_spd_lookup(m, AF_INET, hlen, &error, IPSP_DIRECTION_IN,
diff --git a/sys/netinet/ip_ipcomp.c b/sys/netinet/ip_ipcomp.c
index af855f0d7cb..fff0dbfe999 100644
--- a/sys/netinet/ip_ipcomp.c
+++ b/sys/netinet/ip_ipcomp.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_ipcomp.c,v 1.26 2010/07/02 02:40:16 blambert Exp $ */
+/* $OpenBSD: ip_ipcomp.c,v 1.27 2010/07/09 16:58:06 reyk Exp $ */
/*
* Copyright (c) 2001 Jean-Jacques Bernard-Gundol (jj@wabbitt.org)
@@ -195,6 +195,7 @@ ipcomp_input(m, tdb, skip, protoff)
tc->tc_protoff = protoff;
tc->tc_spi = tdb->tdb_spi;
tc->tc_proto = IPPROTO_IPCOMP;
+ tc->tc_rdomain = tdb->tdb_rdomain;
bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union));
return crypto_dispatch(crp);
@@ -234,7 +235,7 @@ ipcomp_input_cb(op)
s = spltdb();
- tdb = gettdb(tc->tc_spi, &tc->tc_dst, tc->tc_proto);
+ tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto);
if (tdb == NULL) {
free(tc, M_XDATA);
ipcompstat.ipcomps_notdb++;
@@ -526,6 +527,7 @@ ipcomp_output(m, tdb, mp, skip, protoff)
tc->tc_spi = tdb->tdb_spi;
tc->tc_proto = tdb->tdb_sproto;
tc->tc_skip = skip;
+ tc->tc_rdomain = tdb->tdb_rdomain;
bcopy(&tdb->tdb_dst, &tc->tc_dst, sizeof(union sockaddr_union));
/* Crypto operation descriptor */
@@ -577,7 +579,7 @@ ipcomp_output_cb(cp)
s = spltdb();
- tdb = gettdb(tc->tc_spi, &tc->tc_dst, tc->tc_proto);
+ tdb = gettdb(tc->tc_rdomain, tc->tc_spi, &tc->tc_dst, tc->tc_proto);
if (tdb == NULL) {
free(tc, M_XDATA);
ipcompstat.ipcomps_notdb++;
diff --git a/sys/netinet/ip_ipsp.c b/sys/netinet/ip_ipsp.c
index 40df7b69f7b..93c18ee3a5d 100644
--- a/sys/netinet/ip_ipsp.c
+++ b/sys/netinet/ip_ipsp.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_ipsp.c,v 1.180 2010/04/20 22:05:43 tedu Exp $ */
+/* $OpenBSD: ip_ipsp.c,v 1.181 2010/07/09 16:58:06 reyk Exp $ */
/*
* The authors of this code are John Ioannidis (ji@tla.org),
* Angelos D. Keromytis (kermit@csd.uch.gr),
@@ -94,7 +94,7 @@ void tdb_timeout(void *v);
void tdb_firstuse(void *v);
void tdb_soft_timeout(void *v);
void tdb_soft_firstuse(void *v);
-int tdb_hash(u_int32_t, union sockaddr_union *, u_int8_t);
+int tdb_hash(u_int, u_int32_t, union sockaddr_union *, u_int8_t);
extern int ipsec_auth_default_level;
extern int ipsec_esp_trans_default_level;
@@ -155,7 +155,8 @@ static int tdb_count;
* so we cannot be DoS-attacked via choosing of the data to hash.
*/
int
-tdb_hash(u_int32_t spi, union sockaddr_union *dst, u_int8_t proto)
+tdb_hash(u_int rdomain, u_int32_t spi, union sockaddr_union *dst,
+ u_int8_t proto)
{
static u_int32_t mult1 = 0, mult2 = 0;
u_int8_t *ptr = (u_int8_t *) dst;
@@ -168,7 +169,7 @@ tdb_hash(u_int32_t spi, union sockaddr_union *dst, u_int8_t proto)
while (mult2 == 0)
mult2 = arc4random();
- hash = (spi ^ proto) * mult1;
+ hash = (spi ^ proto ^ rdomain) * mult1;
for (i = 0; i < SA_LEN(&dst->sa); i++) {
val32 = (val32 << 8) | ptr[i];
if (i % 4 == 3) {
@@ -192,8 +193,9 @@ tdb_hash(u_int32_t spi, union sockaddr_union *dst, u_int8_t proto)
* an error return value.
*/
u_int32_t
-reserve_spi(u_int32_t sspi, u_int32_t tspi, union sockaddr_union *src,
- union sockaddr_union *dst, u_int8_t sproto, int *errval)
+reserve_spi(u_int rdomain, u_int32_t sspi, u_int32_t tspi,
+ union sockaddr_union *src, union sockaddr_union *dst,
+ u_int8_t sproto, int *errval)
{
struct tdb *tdbp;
u_int32_t spi;
@@ -248,13 +250,13 @@ reserve_spi(u_int32_t sspi, u_int32_t tspi, union sockaddr_union *src,
/* Check whether we're using this SPI already. */
s = spltdb();
- tdbp = gettdb(spi, dst, sproto);
+ tdbp = gettdb(rdomain, spi, dst, sproto);
splx(s);
if (tdbp != (struct tdb *) NULL)
continue;
- tdbp = tdb_alloc();
+ tdbp = tdb_alloc(rdomain);
tdbp->tdb_spi = spi;
bcopy(&dst->sa, &tdbp->tdb_dst.sa, SA_LEN(&dst->sa));
@@ -289,7 +291,7 @@ reserve_spi(u_int32_t sspi, u_int32_t tspi, union sockaddr_union *src,
* Caller is responsible for setting at least spltdb().
*/
struct tdb *
-gettdb(u_int32_t spi, union sockaddr_union *dst, u_int8_t proto)
+gettdb(u_int rdomain, u_int32_t spi, union sockaddr_union *dst, u_int8_t proto)
{
u_int32_t hashval;
struct tdb *tdbp;
@@ -297,10 +299,11 @@ gettdb(u_int32_t spi, union sockaddr_union *dst, u_int8_t proto)
if (tdbh == NULL)
return (struct tdb *) NULL;
- hashval = tdb_hash(spi, dst, proto);
+ hashval = tdb_hash(rdomain, spi, dst, proto);
for (tdbp = tdbh[hashval]; tdbp != NULL; tdbp = tdbp->tdb_hnext)
if ((tdbp->tdb_spi == spi) && (tdbp->tdb_sproto == proto) &&
+ (tdbp->tdb_rdomain == rdomain) &&
!bcmp(&tdbp->tdb_dst, dst, SA_LEN(&dst->sa)))
break;
@@ -313,7 +316,7 @@ gettdb(u_int32_t spi, union sockaddr_union *dst, u_int8_t proto)
* matches all SPIs.
*/
struct tdb *
-gettdbbysrcdst(u_int32_t spi, union sockaddr_union *src,
+gettdbbysrcdst(u_int rdomain, u_int32_t spi, union sockaddr_union *src,
union sockaddr_union *dst, u_int8_t proto)
{
u_int32_t hashval;
@@ -323,11 +326,12 @@ gettdbbysrcdst(u_int32_t spi, union sockaddr_union *src,
if (tdbsrc == NULL)
return (struct tdb *) NULL;
- hashval = tdb_hash(0, src, proto);
+ hashval = tdb_hash(rdomain, 0, src, proto);
for (tdbp = tdbsrc[hashval]; tdbp != NULL; tdbp = tdbp->tdb_snext)
if (tdbp->tdb_sproto == proto &&
(spi == 0 || tdbp->tdb_spi == spi) &&
+ (tdbp->tdb_rdomain == rdomain) &&
((tdbp->tdb_flags & TDBF_INVALID) == 0) &&
(tdbp->tdb_dst.sa.sa_family == AF_UNSPEC ||
!bcmp(&tdbp->tdb_dst, dst, SA_LEN(&dst->sa))) &&
@@ -339,11 +343,12 @@ gettdbbysrcdst(u_int32_t spi, union sockaddr_union *src,
bzero(&su_null, sizeof(su_null));
su_null.sa.sa_len = sizeof(struct sockaddr);
- hashval = tdb_hash(0, &su_null, proto);
+ hashval = tdb_hash(rdomain, 0, &su_null, proto);
for (tdbp = tdbsrc[hashval]; tdbp != NULL; tdbp = tdbp->tdb_snext)
if (tdbp->tdb_sproto == proto &&
(spi == 0 || tdbp->tdb_spi == spi) &&
+ (tdbp->tdb_rdomain == rdomain) &&
((tdbp->tdb_flags & TDBF_INVALID) == 0) &&
(tdbp->tdb_dst.sa.sa_family == AF_UNSPEC ||
!bcmp(&tdbp->tdb_dst, dst, SA_LEN(&dst->sa))) &&
@@ -412,7 +417,7 @@ ipsp_aux_match(struct tdb *tdb,
* the desired IDs.
*/
struct tdb *
-gettdbbyaddr(union sockaddr_union *dst, u_int8_t sproto,
+gettdbbyaddr(u_int rdomain, union sockaddr_union *dst, u_int8_t sproto,
struct ipsec_ref *srcid, struct ipsec_ref *dstid,
struct ipsec_ref *local_cred, struct mbuf *m, int af,
struct sockaddr_encap *filter, struct sockaddr_encap *filtermask)
@@ -423,10 +428,11 @@ gettdbbyaddr(union sockaddr_union *dst, u_int8_t sproto,
if (tdbaddr == NULL)
return (struct tdb *) NULL;
- hashval = tdb_hash(0, dst, sproto);
+ hashval = tdb_hash(rdomain, 0, dst, sproto);
for (tdbp = tdbaddr[hashval]; tdbp != NULL; tdbp = tdbp->tdb_anext)
if ((tdbp->tdb_sproto == sproto) &&
+ (tdbp->tdb_rdomain == rdomain) &&
((tdbp->tdb_flags & TDBF_INVALID) == 0) &&
(!bcmp(&tdbp->tdb_dst, dst, SA_LEN(&dst->sa)))) {
/* Do IDs and local credentials match ? */
@@ -444,7 +450,7 @@ gettdbbyaddr(union sockaddr_union *dst, u_int8_t sproto,
* the desired IDs.
*/
struct tdb *
-gettdbbysrc(union sockaddr_union *src, u_int8_t sproto,
+gettdbbysrc(u_int rdomain, union sockaddr_union *src, u_int8_t sproto,
struct ipsec_ref *srcid, struct ipsec_ref *dstid,
struct mbuf *m, int af, struct sockaddr_encap *filter,
struct sockaddr_encap *filtermask)
@@ -455,10 +461,11 @@ gettdbbysrc(union sockaddr_union *src, u_int8_t sproto,
if (tdbsrc == NULL)
return (struct tdb *) NULL;
- hashval = tdb_hash(0, src, sproto);
+ hashval = tdb_hash(rdomain, 0, src, sproto);
for (tdbp = tdbsrc[hashval]; tdbp != NULL; tdbp = tdbp->tdb_snext)
if ((tdbp->tdb_sproto == sproto) &&
+ (tdbp->tdb_rdomain == rdomain) &&
((tdbp->tdb_flags & TDBF_INVALID) == 0) &&
(!bcmp(&tdbp->tdb_src, src, SA_LEN(&src->sa)))) {
/* Check whether IDs match */
@@ -506,7 +513,7 @@ tdb_hashstats(void)
* Caller is responsible for setting at least spltdb().
*/
int
-tdb_walk(int (*walker)(struct tdb *, void *, int), void *arg)
+tdb_walk(u_int rdomain, int (*walker)(struct tdb *, void *, int), void *arg)
{
int i, rval = 0;
struct tdb *tdbp, *next;
@@ -517,6 +524,10 @@ tdb_walk(int (*walker)(struct tdb *, void *, int), void *arg)
for (i = 0; i <= tdb_hashmask; i++)
for (tdbp = tdbh[i]; rval == 0 && tdbp != NULL; tdbp = next) {
next = tdbp->tdb_hnext;
+
+ if (rdomain != tdbp->tdb_rdomain)
+ continue;
+
if (i == tdb_hashmask && next == NULL)
rval = walker(tdbp, (void *)arg, 1);
else
@@ -606,7 +617,8 @@ tdb_rehash(void)
for (i = 0; i <= old_hashmask; i++) {
for (tdbp = tdbh[i]; tdbp != NULL; tdbp = tdbnp) {
tdbnp = tdbp->tdb_hnext;
- hashval = tdb_hash(tdbp->tdb_spi, &tdbp->tdb_dst,
+ hashval = tdb_hash(tdbp->tdb_rdomain,
+ tdbp->tdb_spi, &tdbp->tdb_dst,
tdbp->tdb_sproto);
tdbp->tdb_hnext = new_tdbh[hashval];
new_tdbh[hashval] = tdbp;
@@ -614,7 +626,8 @@ tdb_rehash(void)
for (tdbp = tdbaddr[i]; tdbp != NULL; tdbp = tdbnp) {
tdbnp = tdbp->tdb_anext;
- hashval = tdb_hash(0, &tdbp->tdb_dst,
+ hashval = tdb_hash(tdbp->tdb_rdomain,
+ 0, &tdbp->tdb_dst,
tdbp->tdb_sproto);
tdbp->tdb_anext = new_tdbaddr[hashval];
new_tdbaddr[hashval] = tdbp;
@@ -622,7 +635,8 @@ tdb_rehash(void)
for (tdbp = tdbsrc[i]; tdbp != NULL; tdbp = tdbnp) {
tdbnp = tdbp->tdb_snext;
- hashval = tdb_hash(0, &tdbp->tdb_src,
+ hashval = tdb_hash(tdbp->tdb_rdomain,
+ 0, &tdbp->tdb_src,
tdbp->tdb_sproto);
tdbp->tdb_snext = new_srcaddr[hashval];
new_srcaddr[hashval] = tdbp;
@@ -657,7 +671,8 @@ puttdb(struct tdb *tdbp)
M_TDB, M_WAITOK | M_ZERO);
}
- hashval = tdb_hash(tdbp->tdb_spi, &tdbp->tdb_dst, tdbp->tdb_sproto);
+ hashval = tdb_hash(tdbp->tdb_rdomain, tdbp->tdb_spi,
+ &tdbp->tdb_dst, tdbp->tdb_sproto);
/*
* Rehash if this tdb would cause a bucket to have more than
@@ -670,18 +685,20 @@ puttdb(struct tdb *tdbp)
if (tdbh[hashval] != NULL && tdbh[hashval]->tdb_hnext != NULL &&
tdb_count * 10 > tdb_hashmask + 1) {
tdb_rehash();
- hashval = tdb_hash(tdbp->tdb_spi, &tdbp->tdb_dst,
- tdbp->tdb_sproto);
+ hashval = tdb_hash(tdbp->tdb_rdomain, tdbp->tdb_spi,
+ &tdbp->tdb_dst, tdbp->tdb_sproto);
}
tdbp->tdb_hnext = tdbh[hashval];
tdbh[hashval] = tdbp;
- hashval = tdb_hash(0, &tdbp->tdb_dst, tdbp->tdb_sproto);
+ hashval = tdb_hash(tdbp->tdb_rdomain, 0, &tdbp->tdb_dst,
+ tdbp->tdb_sproto);
tdbp->tdb_anext = tdbaddr[hashval];
tdbaddr[hashval] = tdbp;
- hashval = tdb_hash(0, &tdbp->tdb_src, tdbp->tdb_sproto);
+ hashval = tdb_hash(tdbp->tdb_rdomain, 0, &tdbp->tdb_src,
+ tdbp->tdb_sproto);
tdbp->tdb_snext = tdbsrc[hashval];
tdbsrc[hashval] = tdbp;
@@ -705,7 +722,8 @@ tdb_delete(struct tdb *tdbp)
if (tdbh == NULL)
return;
- hashval = tdb_hash(tdbp->tdb_spi, &tdbp->tdb_dst, tdbp->tdb_sproto);
+ hashval = tdb_hash(tdbp->tdb_rdomain, tdbp->tdb_spi,
+ &tdbp->tdb_dst, tdbp->tdb_sproto);
s = spltdb();
if (tdbh[hashval] == tdbp) {
@@ -722,7 +740,8 @@ tdb_delete(struct tdb *tdbp)
tdbp->tdb_hnext = NULL;
- hashval = tdb_hash(0, &tdbp->tdb_dst, tdbp->tdb_sproto);
+ hashval = tdb_hash(tdbp->tdb_rdomain, 0, &tdbp->tdb_dst,
+ tdbp->tdb_sproto);
if (tdbaddr[hashval] == tdbp) {
tdbaddr[hashval] = tdbp->tdb_anext;
@@ -736,7 +755,8 @@ tdb_delete(struct tdb *tdbp)
}
}
- hashval = tdb_hash(0, &tdbp->tdb_src, tdbp->tdb_sproto);
+ hashval = tdb_hash(tdbp->tdb_rdomain, 0, &tdbp->tdb_src,
+ tdbp->tdb_sproto);
if (tdbsrc[hashval] == tdbp) {
tdbsrc[hashval] = tdbp->tdb_snext;
@@ -762,7 +782,7 @@ tdb_delete(struct tdb *tdbp)
* Allocate a TDB and initialize a few basic fields.
*/
struct tdb *
-tdb_alloc(void)
+tdb_alloc(u_int rdomain)
{
struct tdb *tdbp;
@@ -777,6 +797,9 @@ tdb_alloc(void)
/* Record establishment time. */
tdbp->tdb_established = time_second;
+ /* Save routing domain */
+ tdbp->tdb_rdomain = rdomain;
+
/* Initialize timeouts. */
timeout_set(&tdbp->tdb_timer_tmo, tdb_timeout, tdbp);
timeout_set(&tdbp->tdb_first_tmo, tdb_firstuse, tdbp);
@@ -1041,7 +1064,7 @@ ipsp_skipcrypto_mark(struct tdb_ident *tdbi)
struct tdb *tdb;
int s = spltdb();
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi, &tdbi->dst, tdbi->proto);
if (tdb != NULL) {
tdb->tdb_flags |= TDBF_SKIPCRYPTO;
tdb->tdb_last_marked = time_second;
@@ -1056,7 +1079,7 @@ ipsp_skipcrypto_unmark(struct tdb_ident *tdbi)
struct tdb *tdb;
int s = spltdb();
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi, &tdbi->dst, tdbi->proto);
if (tdb != NULL) {
tdb->tdb_flags &= ~TDBF_SKIPCRYPTO;
tdb->tdb_last_marked = time_second;
@@ -1163,6 +1186,8 @@ ipsp_parse_headers(struct mbuf *m, int off, u_int8_t proto)
tdbi->dst.sin6.sin6_len =
sizeof(struct sockaddr_in6);
tdbi->dst.sin6.sin6_addr = ip6_dst;
+ tdbi->rdomain =
+ rtable_l2(m->m_pkthdr.rdomain);
SLIST_INSERT_HEAD(&tags,
mtag, m_tag_link);
}
@@ -1270,6 +1295,7 @@ ipsp_parse_headers(struct mbuf *m, int off, u_int8_t proto)
(caddr_t) &tdbi->spi);
tdbi->proto = proto; /* AH or ESP */
+ tdbi->rdomain = rtable_l2(m->m_pkthdr.rdomain);
#ifdef INET
/* Last network header was IPv4. */
diff --git a/sys/netinet/ip_ipsp.h b/sys/netinet/ip_ipsp.h
index 3bfad3ee55c..d0cbe90d1ee 100644
--- a/sys/netinet/ip_ipsp.h
+++ b/sys/netinet/ip_ipsp.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_ipsp.h,v 1.143 2010/07/01 02:09:45 reyk Exp $ */
+/* $OpenBSD: ip_ipsp.h,v 1.144 2010/07/09 16:58:06 reyk Exp $ */
/*
* The authors of this code are John Ioannidis (ji@tla.org),
* Angelos D. Keromytis (kermit@csd.uch.gr),
@@ -201,6 +201,7 @@ struct ipsec_policy {
u_int8_t ipo_flags; /* See IPSP_POLICY_* definitions */
u_int8_t ipo_type; /* USE/ACQUIRE/... */
u_int8_t ipo_sproto; /* ESP/AH; if zero, use system dflts */
+ u_int ipo_rdomain;
int ipo_ref_count;
@@ -374,6 +375,8 @@ struct tdb { /* tunnel descriptor block */
u_int16_t tdb_tag; /* Packet filter tag */
u_int32_t tdb_tap; /* Alternate enc(4) interface */
+ u_int tdb_rdomain; /* Routing domain */
+
struct sockaddr_encap tdb_filter; /* What traffic is acceptable */
struct sockaddr_encap tdb_filtermask; /* And the mask */
@@ -387,6 +390,7 @@ struct tdb_ident {
u_int32_t spi;
union sockaddr_union dst;
u_int8_t proto;
+ u_int rdomain;
};
struct tdb_crypto {
@@ -396,6 +400,7 @@ struct tdb_crypto {
int tc_protoff;
int tc_skip;
caddr_t tc_ptr;
+ u_int tc_rdomain;
};
struct ipsecinit {
@@ -511,23 +516,23 @@ extern char *ipsp_address(union sockaddr_union);
/* TDB management routines */
extern void tdb_add_inp(struct tdb *, struct inpcb *, int);
-extern u_int32_t reserve_spi(u_int32_t, u_int32_t, union sockaddr_union *,
- union sockaddr_union *, u_int8_t, int *);
-extern struct tdb *gettdb(u_int32_t, union sockaddr_union *, u_int8_t);
-extern struct tdb *gettdbbyaddr(union sockaddr_union *, u_int8_t,
+extern u_int32_t reserve_spi(u_int, u_int32_t, u_int32_t,
+ union sockaddr_union *, union sockaddr_union *, u_int8_t, int *);
+extern struct tdb *gettdb(u_int, u_int32_t, union sockaddr_union *, u_int8_t);
+extern struct tdb *gettdbbyaddr(u_int, union sockaddr_union *, u_int8_t,
struct ipsec_ref *, struct ipsec_ref *, struct ipsec_ref *,
struct mbuf *, int, struct sockaddr_encap *, struct sockaddr_encap *);
-extern struct tdb *gettdbbysrc(union sockaddr_union *, u_int8_t,
+extern struct tdb *gettdbbysrc(u_int, union sockaddr_union *, u_int8_t,
struct ipsec_ref *, struct ipsec_ref *, struct mbuf *, int,
struct sockaddr_encap *, struct sockaddr_encap *);
-extern struct tdb *gettdbbysrcdst(u_int32_t, union sockaddr_union *,
+extern struct tdb *gettdbbysrcdst(u_int, u_int32_t, union sockaddr_union *,
union sockaddr_union *, u_int8_t);
extern void puttdb(struct tdb *);
extern void tdb_delete(struct tdb *);
-extern struct tdb *tdb_alloc(void);
+extern struct tdb *tdb_alloc(u_int);
extern void tdb_free(struct tdb *);
extern int tdb_init(struct tdb *, u_int16_t, struct ipsecinit *);
-extern int tdb_walk(int (*)(struct tdb *, void *, int), void *);
+extern int tdb_walk(u_int, int (*)(struct tdb *, void *, int), void *);
/* XF_IP4 */
extern int ipe4_attach(void);
diff --git a/sys/netinet/ip_output.c b/sys/netinet/ip_output.c
index 8dca59f9b4d..63a1cb2a020 100644
--- a/sys/netinet/ip_output.c
+++ b/sys/netinet/ip_output.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_output.c,v 1.209 2010/07/03 04:44:51 guenther Exp $ */
+/* $OpenBSD: ip_output.c,v 1.210 2010/07/09 16:58:06 reyk Exp $ */
/* $NetBSD: ip_output.c,v 1.28 1996/02/13 23:43:07 christos Exp $ */
/*
@@ -272,7 +272,8 @@ reroute:
mtag->m_tag_len, sizeof (struct tdb_ident));
#endif
tdbi = (struct tdb_ident *)(mtag + 1);
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain,
+ tdbi->spi, &tdbi->dst, tdbi->proto);
if (tdb == NULL)
error = -EINVAL;
m_tag_delete(m, mtag);
@@ -315,6 +316,7 @@ reroute:
tdbi = (struct tdb_ident *)(mtag + 1);
if (tdbi->spi == tdb->tdb_spi &&
tdbi->proto == tdb->tdb_sproto &&
+ tdbi->rdomain == tdb->tdb_rdomain &&
!bcmp(&tdbi->dst, &tdb->tdb_dst,
sizeof(union sockaddr_union))) {
splx(s);
@@ -586,7 +588,8 @@ sendit:
if (sproto != 0) {
s = splnet();
- tdb = gettdb(sspi, &sdst, sproto);
+ tdb = gettdb(rtable_l2(m->m_pkthdr.rdomain),
+ sspi, &sdst, sproto);
if (tdb == NULL) {
DPRINTF(("ip_output: unknown TDB"));
error = EHOSTUNREACH;
@@ -599,7 +602,8 @@ sendit:
* Packet filter
*/
#if NPF > 0
- if ((encif = enc_getif(0, tdb->tdb_tap)) == NULL ||
+ if ((encif = enc_getif(tdb->tdb_rdomain,
+ tdb->tdb_tap)) == NULL ||
pf_test(PF_OUT, encif, &m, NULL) != PF_PASS) {
error = EHOSTUNREACH;
splx(s);
diff --git a/sys/netinet/ip_spd.c b/sys/netinet/ip_spd.c
index e3fd6117317..6d4a8572454 100644
--- a/sys/netinet/ip_spd.c
+++ b/sys/netinet/ip_spd.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip_spd.c,v 1.61 2010/07/02 03:58:48 david Exp $ */
+/* $OpenBSD: ip_spd.c,v 1.62 2010/07/09 16:58:06 reyk Exp $ */
/*
* The author of this code is Angelos D. Keromytis (angelos@cis.upenn.edu)
*
@@ -86,6 +86,7 @@ ipsp_spd_lookup(struct mbuf *m, int af, int hlen, int *error, int direction,
struct sockaddr_encap *ddst;
struct ipsec_policy *ipo;
int signore = 0, dignore = 0;
+ u_int rdomain = rtable_l2(m->m_pkthdr.rdomain);
/*
* If there are no flows in place, there's no point
@@ -231,6 +232,9 @@ ipsp_spd_lookup(struct mbuf *m, int af, int hlen, int *error, int direction,
return NULL;
}
+ /* Set the rdomain that was obtained from the mbuf */
+ re->re_tableid = rdomain;
+
/* Actual SPD lookup. */
rtalloc((struct route *) re);
if (re->re_rt == NULL) {
@@ -391,7 +395,8 @@ ipsp_spd_lookup(struct mbuf *m, int af, int hlen, int *error, int direction,
/* Find an appropriate SA from the existing ones. */
ipo->ipo_tdb =
- gettdbbyaddr(dignore ? &sdst : &ipo->ipo_dst,
+ gettdbbyaddr(rdomain,
+ dignore ? &sdst : &ipo->ipo_dst,
ipo->ipo_sproto, ipo->ipo_srcid,
ipo->ipo_dstid, ipo->ipo_local_cred, m, af,
&ipo->ipo_addr, &ipo->ipo_mask);
@@ -504,7 +509,8 @@ ipsp_spd_lookup(struct mbuf *m, int af, int hlen, int *error, int direction,
ipo->ipo_last_searched = time_second;
ipo->ipo_tdb =
- gettdbbysrc(dignore ? &ssrc : &ipo->ipo_dst,
+ gettdbbysrc(rdomain,
+ dignore ? &ssrc : &ipo->ipo_dst,
ipo->ipo_sproto, ipo->ipo_srcid,
ipo->ipo_dstid, m, af, &ipo->ipo_addr,
&ipo->ipo_mask);
@@ -579,7 +585,8 @@ ipsec_delete_policy(struct ipsec_policy *ipo)
info.rti_info[RTAX_NETMASK] = (struct sockaddr *)&ipo->ipo_mask;
/* XXX other tables? */
- err = rtrequest1(RTM_DELETE, &info, RTP_DEFAULT, NULL, 0);
+ err = rtrequest1(RTM_DELETE, &info, RTP_DEFAULT, NULL,
+ ipo->ipo_rdomain);
}
if (ipo->ipo_tdb != NULL)
TAILQ_REMOVE(&ipo->ipo_tdb->tdb_policy_head, ipo,
@@ -635,6 +642,7 @@ ipsec_add_policy(struct inpcb *inp, int af, int direction)
* policies (for tunnel/transport and ESP/AH), as needed.
*/
ipon->ipo_sproto = IPPROTO_ESP;
+ ipon->ipo_rdomain = rtable_l2(inp->inp_rtableid);
TAILQ_INIT(&ipon->ipo_acquires);
TAILQ_INSERT_HEAD(&ipsec_policy_head, ipon, ipo_list);
@@ -1001,7 +1009,8 @@ ipsp_spd_inp(struct mbuf *m, int af, int hlen, int *error, int direction,
inp->inp_ipo->ipo_last_searched = time_second;
/* Do we have an SA already established ? */
- if (gettdbbysrc(&inp->inp_ipo->ipo_dst,
+ if (gettdbbysrc(rtable_l2(inp->inp_rtableid),
+ &inp->inp_ipo->ipo_dst,
inp->inp_ipo->ipo_sproto,
inp->inp_ipo->ipo_srcid,
inp->inp_ipo->ipo_dstid, m, af,
@@ -1057,7 +1066,8 @@ ipsp_spd_inp(struct mbuf *m, int af, int hlen, int *error, int direction,
ipsec_update_policy(inp, inp->inp_ipo, af,
IPSP_DIRECTION_OUT);
- tdb = gettdbbyaddr(&inp->inp_ipo->ipo_dst,
+ tdb = gettdbbyaddr(rtable_l2(inp->inp_rtableid),
+ &inp->inp_ipo->ipo_dst,
inp->inp_ipo->ipo_sproto,
inp->inp_ipo->ipo_srcid,
inp->inp_ipo->ipo_dstid,
@@ -1073,7 +1083,8 @@ ipsp_spd_inp(struct mbuf *m, int af, int hlen, int *error, int direction,
ipsec_update_policy(inp, &sipon, af,
IPSP_DIRECTION_OUT);
- tdb = gettdbbyaddr(&sipon.ipo_dst, IPPROTO_ESP, NULL,
+ tdb = gettdbbyaddr(rtable_l2(inp->inp_rtableid),
+ &sipon.ipo_dst, IPPROTO_ESP, NULL,
NULL, NULL, m, af, &sipon.ipo_addr,
&sipon.ipo_mask);
}
@@ -1143,6 +1154,7 @@ ipsp_spd_inp(struct mbuf *m, int af, int hlen, int *error, int direction,
tdbi = (struct tdb_ident *)(mtag + 1);
tdbi->spi = ipo->ipo_tdb->tdb_spi;
tdbi->proto = ipo->ipo_tdb->tdb_sproto;
+ tdbi->rdomain = rtable_l2(inp->inp_rtableid);
bcopy(&ipo->ipo_tdb->tdb_dst, &tdbi->dst,
ipo->ipo_tdb->tdb_dst.sa.sa_len);
m_tag_prepend(m, mtag);
diff --git a/sys/netinet/ipsec_input.c b/sys/netinet/ipsec_input.c
index f646902ad05..f9e1b1ee14d 100644
--- a/sys/netinet/ipsec_input.c
+++ b/sys/netinet/ipsec_input.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ipsec_input.c,v 1.97 2010/07/01 02:09:45 reyk Exp $ */
+/* $OpenBSD: ipsec_input.c,v 1.98 2010/07/09 16:58:06 reyk Exp $ */
/*
* The authors of this code are John Ioannidis (ji@tla.org),
* Angelos D. Keromytis (kermit@csd.uch.gr) and
@@ -81,7 +81,7 @@
#include "bpfilter.h"
-void *ipsec_common_ctlinput(int, struct sockaddr *, void *, int);
+void *ipsec_common_ctlinput(u_int, int, struct sockaddr *, void *, int);
#ifdef ENCDEBUG
#define DPRINTF(x) if (encdebug) printf x
@@ -201,7 +201,8 @@ ipsec_common_input(struct mbuf *m, int skip, int protoff, int af, int sproto,
}
s = spltdb();
- tdbp = gettdb(spi, &dst_address, sproto);
+ tdbp = gettdb(rtable_l2(m->m_pkthdr.rdomain),
+ spi, &dst_address, sproto);
if (tdbp == NULL) {
splx(s);
DPRINTF(("ipsec_common_input(): could not find SA for "
@@ -240,7 +241,8 @@ ipsec_common_input(struct mbuf *m, int skip, int protoff, int af, int sproto,
}
if (sproto != IPPROTO_IPCOMP) {
- if ((encif = enc_getif(0, tdbp->tdb_tap)) == NULL) {
+ if ((encif = enc_getif(tdbp->tdb_rdomain,
+ tdbp->tdb_tap)) == NULL) {
splx(s);
DPRINTF(("ipsec_common_input(): "
"no enc%u interface for SA %s/%08x/%u\n",
@@ -554,6 +556,7 @@ ipsec_common_input_cb(struct mbuf *m, struct tdb *tdbp, int skip, int protoff,
sizeof(union sockaddr_union));
tdbi->proto = tdbp->tdb_sproto;
tdbi->spi = tdbp->tdb_spi;
+ tdbi->rdomain = tdbp->tdb_rdomain;
m_tag_prepend(m, mtag);
}
@@ -580,7 +583,7 @@ ipsec_common_input_cb(struct mbuf *m, struct tdb *tdbp, int skip, int protoff,
m->m_flags |= M_TUNNEL;
#if NBPFILTER > 0
- if ((encif = enc_getif(0, tdbp->tdb_tap)) != NULL) {
+ if ((encif = enc_getif(tdbp->tdb_rdomain, tdbp->tdb_tap)) != NULL) {
encif->if_ipackets++;
encif->if_ibytes += m->m_pkthdr.len;
@@ -772,7 +775,7 @@ ah4_ctlinput(int cmd, struct sockaddr *sa, u_int rdomain, void *v)
sa->sa_len != sizeof(struct sockaddr_in))
return (NULL);
- return (ipsec_common_ctlinput(cmd, sa, v, IPPROTO_AH));
+ return (ipsec_common_ctlinput(rdomain, cmd, sa, v, IPPROTO_AH));
}
/* IPv4 ESP wrapper. */
@@ -861,7 +864,8 @@ ipcomp4_input_cb(struct mbuf *m, ...)
}
void *
-ipsec_common_ctlinput(int cmd, struct sockaddr *sa, void *v, int proto)
+ipsec_common_ctlinput(u_int rdomain, int cmd, struct sockaddr *sa,
+ void *v, int proto)
{
extern u_int ip_mtudisc_timeout;
struct ip *ip = v;
@@ -895,7 +899,8 @@ ipsec_common_ctlinput(int cmd, struct sockaddr *sa, void *v, int proto)
bcopy((caddr_t)ip + hlen, &spi, sizeof(u_int32_t));
s = spltdb();
- tdbp = gettdb(spi, (union sockaddr_union *)&dst, proto);
+ tdbp = gettdb(rdomain, spi, (union sockaddr_union *)&dst,
+ proto);
if (tdbp == NULL || tdbp->tdb_flags & TDBF_INVALID) {
splx(s);
return (NULL);
@@ -961,7 +966,7 @@ udpencap_ctlinput(int cmd, struct sockaddr *sa, u_int rdomain, void *v)
su_src = (union sockaddr_union *)&src;
s = spltdb();
- tdbp = gettdbbysrcdst(0, su_src, su_dst, IPPROTO_ESP);
+ tdbp = gettdbbysrcdst(rdomain, 0, su_src, su_dst, IPPROTO_ESP);
for (; tdbp != NULL; tdbp = tdbp->tdb_snext) {
if (tdbp->tdb_sproto == IPPROTO_ESP &&
@@ -993,7 +998,7 @@ esp4_ctlinput(int cmd, struct sockaddr *sa, u_int rdomain, void *v)
sa->sa_len != sizeof(struct sockaddr_in))
return (NULL);
- return (ipsec_common_ctlinput(cmd, sa, v, IPPROTO_ESP));
+ return (ipsec_common_ctlinput(rdomain, cmd, sa, v, IPPROTO_ESP));
}
#endif /* INET */
diff --git a/sys/netinet/ipsec_output.c b/sys/netinet/ipsec_output.c
index 232f3e4d438..13601532e09 100644
--- a/sys/netinet/ipsec_output.c
+++ b/sys/netinet/ipsec_output.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ipsec_output.c,v 1.42 2010/01/10 12:43:07 markus Exp $ */
+/* $OpenBSD: ipsec_output.c,v 1.43 2010/07/09 16:58:06 reyk Exp $ */
/*
* The author of this code is Angelos D. Keromytis (angelos@cis.upenn.edu)
*
@@ -490,6 +490,7 @@ ipsp_process_done(struct mbuf *m, struct tdb *tdb)
bcopy(&tdb->tdb_dst, &tdbi->dst, sizeof(union sockaddr_union));
tdbi->proto = tdb->tdb_sproto;
tdbi->spi = tdb->tdb_spi;
+ tdbi->rdomain = tdb->tdb_rdomain;
m_tag_prepend(m, mtag);
@@ -605,7 +606,8 @@ ipsec_adjust_mtu(struct mbuf *m, u_int32_t mtu)
for (mtag = m_tag_find(m, PACKET_TAG_IPSEC_OUT_DONE, NULL); mtag;
mtag = m_tag_find(m, PACKET_TAG_IPSEC_OUT_DONE, mtag)) {
tdbi = (struct tdb_ident *)(mtag + 1);
- tdbp = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdbp = gettdb(tdbi->rdomain, tdbi->spi, &tdbi->dst,
+ tdbi->proto);
if (tdbp == NULL)
break;
diff --git a/sys/netinet/tcp_input.c b/sys/netinet/tcp_input.c
index a9716a68433..3516af7deb8 100644
--- a/sys/netinet/tcp_input.c
+++ b/sys/netinet/tcp_input.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: tcp_input.c,v 1.233 2010/07/03 04:44:51 guenther Exp $ */
+/* $OpenBSD: tcp_input.c,v 1.234 2010/07/09 16:58:06 reyk Exp $ */
/* $NetBSD: tcp_input.c,v 1.23 1996/02/13 23:43:44 christos Exp $ */
/*
@@ -893,7 +893,8 @@ after_listen:
s = splnet();
if (mtag != NULL) {
tdbi = (struct tdb_ident *)(mtag + 1);
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi,
+ &tdbi->dst, tdbi->proto);
} else
tdb = NULL;
ipsp_spd_lookup(m, af, iphlen, &error, IPSP_DIRECTION_IN,
@@ -962,7 +963,8 @@ after_listen:
#else
if (optp)
#endif
- if (tcp_dooptions(tp, optp, optlen, th, m, iphlen, &opti))
+ if (tcp_dooptions(tp, optp, optlen, th, m, iphlen, &opti,
+ m->m_pkthdr.rdomain))
goto drop;
if (opti.ts_present && opti.ts_ecr) {
@@ -2256,7 +2258,8 @@ drop:
int
tcp_dooptions(struct tcpcb *tp, u_char *cp, int cnt, struct tcphdr *th,
- struct mbuf *m, int iphlen, struct tcp_opt_info *oi)
+ struct mbuf *m, int iphlen, struct tcp_opt_info *oi,
+ u_int rtableid)
{
u_int16_t mss = 0;
int opt, optlen;
@@ -2388,7 +2391,8 @@ tcp_dooptions(struct tcpcb *tp, u_char *cp, int cnt, struct tcphdr *th,
#endif /* INET6 */
}
- tdb = gettdbbysrcdst(0, &src, &dst, IPPROTO_TCP);
+ tdb = gettdbbysrcdst(rtable_l2(rtableid),
+ 0, &src, &dst, IPPROTO_TCP);
/*
* We don't have an SA for this peer, so we turn off
@@ -3982,7 +3986,8 @@ syn_cache_add(struct sockaddr *src, struct sockaddr *dst, struct tcphdr *th,
tb.t_flags |= TF_SIGNATURE;
#endif
tb.t_state = TCPS_LISTEN;
- if (tcp_dooptions(&tb, optp, optlen, th, m, iphlen, oi))
+ if (tcp_dooptions(&tb, optp, optlen, th, m, iphlen, oi,
+ sotoinpcb(so)->inp_rtableid))
return (0);
} else
tb.t_flags = 0;
@@ -4267,7 +4272,8 @@ syn_cache_respond(struct syn_cache *sc, struct mbuf *m)
#endif /* INET6 */
}
- tdb = gettdbbysrcdst(0, &src, &dst, IPPROTO_TCP);
+ tdb = gettdbbysrcdst(rtable_l2(sc->sc_rtableid),
+ 0, &src, &dst, IPPROTO_TCP);
if (tdb == NULL) {
if (m)
m_freem(m);
diff --git a/sys/netinet/tcp_output.c b/sys/netinet/tcp_output.c
index cb9964e9e32..58de7ef9557 100644
--- a/sys/netinet/tcp_output.c
+++ b/sys/netinet/tcp_output.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: tcp_output.c,v 1.89 2010/07/03 04:44:51 guenther Exp $ */
+/* $OpenBSD: tcp_output.c,v 1.90 2010/07/09 16:58:06 reyk Exp $ */
/* $NetBSD: tcp_output.c,v 1.16 1997/06/03 16:17:09 kml Exp $ */
/*
@@ -924,7 +924,8 @@ send:
/* XXX gettdbbysrcdst() should really be called at spltdb(). */
/* XXX this is splsoftnet(), currently they are the same. */
- tdb = gettdbbysrcdst(0, &src, &dst, IPPROTO_TCP);
+ tdb = gettdbbysrcdst(rtable_l2(tp->t_inpcb->inp_rtableid),
+ 0, &src, &dst, IPPROTO_TCP);
if (tdb == NULL)
return (EPERM);
diff --git a/sys/netinet/tcp_var.h b/sys/netinet/tcp_var.h
index 57cd44fd8ef..1558747c0fd 100644
--- a/sys/netinet/tcp_var.h
+++ b/sys/netinet/tcp_var.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: tcp_var.h,v 1.94 2010/07/03 04:44:51 guenther Exp $ */
+/* $OpenBSD: tcp_var.h,v 1.95 2010/07/09 16:58:06 reyk Exp $ */
/* $NetBSD: tcp_var.h,v 1.17 1996/02/13 23:44:24 christos Exp $ */
/*
@@ -565,7 +565,7 @@ struct tcpcb *
struct tcpcb *
tcp_drop(struct tcpcb *, int);
int tcp_dooptions(struct tcpcb *, u_char *, int, struct tcphdr *,
- struct mbuf *, int, struct tcp_opt_info *);
+ struct mbuf *, int, struct tcp_opt_info *, u_int);
void tcp_init(void);
#if defined(INET6) && !defined(TCP6)
int tcp6_input(struct mbuf **, int *, int);
diff --git a/sys/netinet/udp_usrreq.c b/sys/netinet/udp_usrreq.c
index 55bfe45b7ab..707ec2d32b0 100644
--- a/sys/netinet/udp_usrreq.c
+++ b/sys/netinet/udp_usrreq.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: udp_usrreq.c,v 1.135 2010/07/03 04:44:51 guenther Exp $ */
+/* $OpenBSD: udp_usrreq.c,v 1.136 2010/07/09 16:58:06 reyk Exp $ */
/* $NetBSD: udp_usrreq.c,v 1.28 1996/03/16 23:54:03 christos Exp $ */
/*
@@ -616,7 +616,8 @@ udp_input(struct mbuf *m, ...)
s = splnet();
if (mtag != NULL) {
tdbi = (struct tdb_ident *)(mtag + 1);
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi,
+ &tdbi->dst, tdbi->proto);
} else
tdb = NULL;
ipsp_spd_lookup(m, srcsa.sa.sa_family, iphlen, &error,
diff --git a/sys/netinet6/ip6_forward.c b/sys/netinet6/ip6_forward.c
index d08183d9e08..7904a23581c 100644
--- a/sys/netinet6/ip6_forward.c
+++ b/sys/netinet6/ip6_forward.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip6_forward.c,v 1.48 2010/07/01 02:09:45 reyk Exp $ */
+/* $OpenBSD: ip6_forward.c,v 1.49 2010/07/09 16:58:06 reyk Exp $ */
/* $KAME: ip6_forward.c,v 1.75 2001/06/29 12:42:13 jinmei Exp $ */
/*
@@ -164,7 +164,8 @@ reroute:
mtag->m_tag_len, sizeof (struct tdb_ident));
#endif
tdbi = (struct tdb_ident *)(mtag + 1);
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi, &tdbi->dst,
+ tdbi->proto);
if (tdb == NULL)
error = -EINVAL;
m_tag_delete(m, mtag);
@@ -205,6 +206,7 @@ reroute:
tdbi = (struct tdb_ident *)(mtag + 1);
if (tdbi->spi == tdb->tdb_spi &&
tdbi->proto == tdb->tdb_sproto &&
+ tdbi->rdomain == tdb->tdb_rdomain &&
!bcmp(&tdbi->dst, &tdb->tdb_dst,
sizeof(union sockaddr_union))) {
splx(s);
@@ -337,7 +339,8 @@ reroute:
if (sproto != 0) {
s = splnet();
- tdb = gettdb(sspi, &sdst, sproto);
+ tdb = gettdb(rtable_l2(m->m_pkthdr.rdomain),
+ sspi, &sdst, sproto);
if (tdb == NULL) {
splx(s);
error = EHOSTUNREACH;
@@ -346,7 +349,8 @@ reroute:
}
#if NPF > 0
- if ((encif = enc_getif(0, tdb->tdb_tap)) == NULL ||
+ if ((encif = enc_getif(tdb->tdb_rdomain,
+ tdb->tdb_tap)) == NULL ||
pf_test6(PF_OUT, encif, &m, NULL) != PF_PASS) {
splx(s);
error = EHOSTUNREACH;
diff --git a/sys/netinet6/ip6_output.c b/sys/netinet6/ip6_output.c
index 4e993ffc8d0..216bc10ec4c 100644
--- a/sys/netinet6/ip6_output.c
+++ b/sys/netinet6/ip6_output.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: ip6_output.c,v 1.115 2010/07/08 19:42:46 jsg Exp $ */
+/* $OpenBSD: ip6_output.c,v 1.116 2010/07/09 16:58:06 reyk Exp $ */
/* $KAME: ip6_output.c,v 1.172 2001/03/25 09:55:56 itojun Exp $ */
/*
@@ -242,7 +242,7 @@ ip6_output(struct mbuf *m0, struct ip6_pktopts *opt, struct route_in6 *ro,
mtag->m_tag_len, sizeof (struct tdb_ident));
#endif
tdbi = (struct tdb_ident *)(mtag + 1);
- tdb = gettdb(tdbi->spi, &tdbi->dst, tdbi->proto);
+ tdb = gettdb(tdbi->rdomain, tdbi->spi, &tdbi->dst, tdbi->proto);
if (tdb == NULL)
error = -EINVAL;
m_tag_delete(m, mtag);
@@ -283,6 +283,7 @@ ip6_output(struct mbuf *m0, struct ip6_pktopts *opt, struct route_in6 *ro,
tdbi = (struct tdb_ident *)(mtag + 1);
if (tdbi->spi == tdb->tdb_spi &&
tdbi->proto == tdb->tdb_sproto &&
+ tdbi->rdomain == tdb->tdb_rdomain &&
!bcmp(&tdbi->dst, &tdb->tdb_dst,
sizeof(union sockaddr_union))) {
splx(s);
@@ -509,7 +510,8 @@ reroute:
* packet gets tunneled?
*/
- tdb = gettdb(sspi, &sdst, sproto);
+ tdb = gettdb(rtable_l2(m->m_pkthdr.rdomain),
+ sspi, &sdst, sproto);
if (tdb == NULL) {
splx(s);
error = EHOSTUNREACH;
@@ -518,7 +520,8 @@ reroute:
}
#if NPF > 0
- if ((encif = enc_getif(0, tdb->tdb_tap)) == NULL ||
+ if ((encif = enc_getif(tdb->tdb_rdomain,
+ tdb->tdb_tap)) == NULL ||
pf_test6(PF_OUT, encif, &m, NULL) != PF_PASS) {
splx(s);
error = EHOSTUNREACH;
@@ -1636,8 +1639,8 @@ do { \
}
tdbip = mtod(m, struct tdb_ident *);
s = spltdb();
- tdb = gettdb(tdbip->spi, &tdbip->dst,
- tdbip->proto);
+ tdb = gettdb(tdbip->rdomain, tdbip->spi,
+ &tdbip->dst, tdbip->proto);
if (tdb == NULL)
error = ESRCH;
else
@@ -1908,6 +1911,8 @@ do { \
tdbi.spi = inp->inp_tdb_out->tdb_spi;
tdbi.dst = inp->inp_tdb_out->tdb_dst;
tdbi.proto = inp->inp_tdb_out->tdb_sproto;
+ tdbi.rdomain =
+ inp->inp_tdb_out->tdb_rdomain;
*mp = m = m_get(M_WAIT, MT_SOOPTS);
m->m_len = sizeof(tdbi);
bcopy((caddr_t)&tdbi, mtod(m, caddr_t),