Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/netinet Add inet4 part of the rfc6056 code contributed b...
details: https://anonhg.NetBSD.org/src/rev/b1916524837e
branches: trunk
changeset: 769823:b1916524837e
user: christos <christos%NetBSD.org@localhost>
date: Sat Sep 24 17:18:17 2011 +0000
description:
Add inet4 part of the rfc6056 code contributed by Vlad Balan as part of
Google SoC-2011
diffstat:
sys/netinet/files.netinet | 3 +-
sys/netinet/in_pcb.c | 64 +-
sys/netinet/in_pcb.h | 4 +-
sys/netinet/in_pcb_hdr.h | 3 +-
sys/netinet/rfc6056.c | 952 ++++++++++++++++++++++++++++++++++++++++++++++
sys/netinet/rfc6056.h | 54 ++
sys/netinet/udp.h | 5 +-
sys/netinet/udp_usrreq.c | 36 +-
sys/netinet/udp_var.h | 6 +-
9 files changed, 1077 insertions(+), 50 deletions(-)
diffs (truncated from 1323 to 300 lines):
diff -r cdbdc13c58ec -r b1916524837e sys/netinet/files.netinet
--- a/sys/netinet/files.netinet Sat Sep 24 17:09:29 2011 +0000
+++ b/sys/netinet/files.netinet Sat Sep 24 17:18:17 2011 +0000
@@ -1,4 +1,4 @@
-# $NetBSD: files.netinet,v 1.22 2011/05/03 18:28:45 dyoung Exp $
+# $NetBSD: files.netinet,v 1.23 2011/09/24 17:18:17 christos Exp $
defflag opt_tcp_debug.h TCP_DEBUG
defparam opt_tcp_debug.h TCP_NDEBUG
@@ -43,3 +43,4 @@
file netinet/tcp_vtw.c inet | inet6
file netinet/udp_usrreq.c inet | inet6
+file netinet/rfc6056.c inet | inet6
diff -r cdbdc13c58ec -r b1916524837e sys/netinet/in_pcb.c
--- a/sys/netinet/in_pcb.c Sat Sep 24 17:09:29 2011 +0000
+++ b/sys/netinet/in_pcb.c Sat Sep 24 17:18:17 2011 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: in_pcb.c,v 1.138 2011/05/03 18:28:45 dyoung Exp $ */
+/* $NetBSD: in_pcb.c,v 1.139 2011/09/24 17:18:17 christos Exp $ */
/*
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
@@ -93,7 +93,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: in_pcb.c,v 1.138 2011/05/03 18:28:45 dyoung Exp $");
+__KERNEL_RCSID(0, "$NetBSD: in_pcb.c,v 1.139 2011/09/24 17:18:17 christos Exp $");
#include "opt_inet.h"
#include "opt_ipsec.h"
@@ -124,6 +124,7 @@
#include <netinet/in_pcb.h>
#include <netinet/in_var.h>
#include <netinet/ip_var.h>
+#include <netinet/rfc6056.h>
#ifdef INET6
#include <netinet/ip6.h>
@@ -202,11 +203,13 @@
splx(s);
if (inp == NULL)
return (ENOBUFS);
- memset((void *)inp, 0, sizeof(*inp));
+ memset(inp, 0, sizeof(*inp));
inp->inp_af = AF_INET;
inp->inp_table = table;
inp->inp_socket = so;
inp->inp_errormtu = -1;
+ inp->inp_rfc6056algo = RFC6056_ALGO_DEFAULT;
+ inp->inp_bindportonsend = false;
#if defined(IPSEC) || defined(FAST_IPSEC)
error = ipsec_init_pcbpolicy(so, &inp->inp_sp);
if (error != 0) {
@@ -232,8 +235,6 @@
{
struct inpcbtable *table = inp->inp_table;
struct socket *so = inp->inp_socket;
- int cnt;
- u_int16_t mymin, mymax;
u_int16_t *lastport;
u_int16_t lport = 0;
enum kauth_network_req req;
@@ -246,14 +247,10 @@
req = KAUTH_REQ_NETWORK_BIND_PORT;
#endif
- mymin = lowportmin;
- mymax = lowportmax;
lastport = &table->inpt_lastlow;
} else {
req = KAUTH_REQ_NETWORK_BIND_PORT;
- mymin = anonportmin;
- mymax = anonportmax;
lastport = &table->inpt_lastport;
}
@@ -263,38 +260,13 @@
if (error)
return (EACCES);
- if (mymin > mymax) { /* sanity check */
- u_int16_t swp;
-
- swp = mymin;
- mymin = mymax;
- mymax = swp;
- }
-
- lport = *lastport - 1;
- for (cnt = mymax - mymin + 1; cnt; cnt--, lport--) {
- vestigial_inpcb_t vestigial;
+ /*
+ * Use RFC6056 randomized port selection
+ */
+ error = rfc6056_randport(&lport, &inp->inp_head, cred);
+ if (error)
+ return error;
- if (lport < mymin || lport > mymax)
- lport = mymax;
- if (!in_pcblookup_port(table, sin->sin_addr, htons(lport), 1,
- &vestigial) && !vestigial.valid) {
- /* We have a free port, check with the secmodel(s). */
- sin->sin_port = lport;
- error = kauth_authorize_network(cred,
- KAUTH_NETWORK_BIND, req, so, sin, NULL);
- if (error) {
- /* Secmodel says no. Keep looking. */
- continue;
- }
-
- goto found;
- }
- }
-
- return (EAGAIN);
-
- found:
inp->inp_flags |= INP_ANONPORT;
*lastport = lport;
lport = htons(lport);
@@ -569,6 +541,18 @@
}
inp->inp_faddr = sin->sin_addr;
inp->inp_fport = sin->sin_port;
+
+ /* Late bind, if needed */
+ if (inp->inp_bindportonsend) {
+ struct sockaddr_in lsin = *((const struct sockaddr_in *)
+ inp->inp_socket->so_proto->pr_domain->dom_sa_any);
+ lsin.sin_addr = inp->inp_laddr;
+ lsin.sin_port = 0;
+
+ if ((error = in_pcbbind_port(inp, &lsin, l->l_cred)) != 0)
+ return error;
+ }
+
in_pcbstate(inp, INP_CONNECTED);
#if defined(IPSEC) || defined(FAST_IPSEC)
if (inp->inp_socket->so_type == SOCK_STREAM)
diff -r cdbdc13c58ec -r b1916524837e sys/netinet/in_pcb.h
--- a/sys/netinet/in_pcb.h Sat Sep 24 17:09:29 2011 +0000
+++ b/sys/netinet/in_pcb.h Sat Sep 24 17:18:17 2011 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: in_pcb.h,v 1.48 2011/05/03 18:28:45 dyoung Exp $ */
+/* $NetBSD: in_pcb.h,v 1.49 2011/09/24 17:18:17 christos Exp $ */
/*
* Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
@@ -80,6 +80,7 @@
#define inp_af inp_head.inph_af
#define inp_ppcb inp_head.inph_ppcb
#define inp_state inp_head.inph_state
+#define inp_rfc6056algo inp_head.inph_rfc6056algo
#define inp_socket inp_head.inph_socket
#define inp_table inp_head.inph_table
#define inp_sp inp_head.inph_sp
@@ -92,6 +93,7 @@
struct ip_moptions *inp_moptions; /* IP multicast options */
int inp_errormtu; /* MTU of last xmit status = EMSGSIZE */
uint8_t inp_ip_minttl;
+ bool inp_bindportonsend;
};
#define inp_faddr inp_ip.ip_dst
diff -r cdbdc13c58ec -r b1916524837e sys/netinet/in_pcb_hdr.h
--- a/sys/netinet/in_pcb_hdr.h Sat Sep 24 17:09:29 2011 +0000
+++ b/sys/netinet/in_pcb_hdr.h Sat Sep 24 17:18:17 2011 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: in_pcb_hdr.h,v 1.6 2011/05/03 18:28:45 dyoung Exp $ */
+/* $NetBSD: in_pcb_hdr.h,v 1.7 2011/09/24 17:18:17 christos Exp $ */
/*
* Copyright (C) 2003 WIDE Project.
@@ -77,6 +77,7 @@
int inph_af; /* address family - AF_INET */
void * inph_ppcb; /* pointer to per-protocol pcb */
int inph_state; /* bind/connect state */
+ int inph_rfc6056algo;
struct socket *inph_socket; /* back pointer to socket */
struct inpcbtable *inph_table;
#if 1 /* IPSEC */
diff -r cdbdc13c58ec -r b1916524837e sys/netinet/rfc6056.c
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/sys/netinet/rfc6056.c Sat Sep 24 17:18:17 2011 +0000
@@ -0,0 +1,952 @@
+/* $NetBSD: rfc6056.c,v 1.1 2011/09/24 17:18:17 christos Exp $ */
+
+/*
+ * Copyright 2011 Vlad Balan
+ *
+ * Written by Vlad Balan for the NetBSD Foundation.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ */
+
+#include <sys/cdefs.h>
+__KERNEL_RCSID(0, "$NetBSD: rfc6056.c,v 1.1 2011/09/24 17:18:17 christos Exp $");
+
+#include "opt_inet.h"
+
+#include <sys/param.h>
+#include <sys/errno.h>
+#include <sys/kauth.h>
+#include <sys/uidinfo.h>
+#include <sys/domain.h>
+#include <sys/md5.h>
+
+#include <net/if.h>
+#include <net/route.h>
+
+#include <netinet/in.h>
+#include <netinet/in_systm.h>
+#include <netinet/ip.h>
+#include <netinet/in_pcb.h>
+#include <netinet/in_var.h>
+#include <netinet/ip_var.h>
+
+#ifdef INET6
+#include <netinet/ip6.h>
+#include <netinet6/ip6_var.h>
+#include <netinet6/in6_pcb.h>
+#endif
+
+#include <netinet/tcp_vtw.h>
+
+#include "rfc6056.h"
+
+#define NPROTO 2
+#define RFC6056_TCP 0
+#define RFC6056_UDP 1
+
+#define NAF 2
+#define RFC6056_IPV4 0
+#define RFC6056_IPV6 1
+
+#define NRANGES 2
+#define RFC6056_LOWPORT 0
+#define RFC6056_HIGHPORT 1
+
+#define RFC6056_DEBUG 1
+
+#if RFC6056_DEBUG
+static bool rfc6056_debug = true;
+#define DPRINTF if (rfc6056_debug) printf
+#else
+#define DPRINTF while (/*CONSTCOND*/0) printf
+#endif
+
+#ifdef INET
+static int inet4_rfc6056algo = RFC6056_ALGO_BSD;
+#endif
+#ifdef INET6
+static int inet6_rfc6056algo = RFC6056_ALGO_BSD;
+#endif
+
+typedef struct {
+ const char *name;
+ int (*func)(int, uint16_t *, struct inpcb_hdr *, kauth_cred_t);
+} rfc6056_algorithm_t;
+
+static int algo_bsd(int, uint16_t *, struct inpcb_hdr *, kauth_cred_t);
+static int algo_random_start(int, uint16_t *, struct inpcb_hdr *, kauth_cred_t);
+static int algo_random_pick(int, uint16_t *, struct inpcb_hdr *, kauth_cred_t);
+static int algo_hash(int, uint16_t *, struct inpcb_hdr *, kauth_cred_t);
+static int algo_doublehash(int, uint16_t *, struct inpcb_hdr *, kauth_cred_t);
+static int algo_randinc(int, uint16_t *, struct inpcb_hdr *, kauth_cred_t);
+
+static const rfc6056_algorithm_t algos[] = {
+ {
+ .name = "bsd",
+ .func = algo_bsd
+ },
+ {
+ .name = "random_start",
+ .func = algo_random_start
+ },
Home |
Main Index |
Thread Index |
Old Index