summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorglebius <glebius@FreeBSD.org>2011-10-15 18:41:25 +0000
committerglebius <glebius@FreeBSD.org>2011-10-15 18:41:25 +0000
commit5bfe25432f47fc51db50d501a15474b6dadf73af (patch)
tree8a8e9ef47b842a0c52b223d99126fb3279f32d6f
parent2eb352ca19c8bd71bd1bfcce26479b057e8b2d10 (diff)
downloadFreeBSD-src-5bfe25432f47fc51db50d501a15474b6dadf73af.zip
FreeBSD-src-5bfe25432f47fc51db50d501a15474b6dadf73af.tar.gz
Add support for IPv4 /31 prefixes, as described in RFC3021.
To run a /31 network, participating hosts MUST drop support for directed broadcasts, and treat the first and last addresses on subnet as unicast. The broadcast address for the prefix should be the link local broadcast address, INADDR_BROADCAST.
-rw-r--r--sys/netinet/in.c13
-rw-r--r--sys/netinet/in.h2
2 files changed, 11 insertions, 4 deletions
diff --git a/sys/netinet/in.c b/sys/netinet/in.c
index d0be11f..bba364d 100644
--- a/sys/netinet/in.c
+++ b/sys/netinet/in.c
@@ -897,8 +897,11 @@ in_ifinit(struct ifnet *ifp, struct in_ifaddr *ia, struct sockaddr_in *sin,
*/
ia->ia_ifa.ifa_metric = ifp->if_metric;
if (ifp->if_flags & IFF_BROADCAST) {
- ia->ia_broadaddr.sin_addr.s_addr =
- htonl(ia->ia_subnet | ~ia->ia_subnetmask);
+ if (ia->ia_subnetmask == IN_RFC3021_MASK)
+ ia->ia_broadaddr.sin_addr.s_addr = INADDR_BROADCAST;
+ else
+ ia->ia_broadaddr.sin_addr.s_addr =
+ htonl(ia->ia_subnet | ~ia->ia_subnetmask);
} else if (ifp->if_flags & IFF_LOOPBACK) {
ia->ia_dstaddr = ia->ia_addr;
flags |= RTF_HOST;
@@ -1230,9 +1233,11 @@ in_broadcast(struct in_addr in, struct ifnet *ifp)
if (ifa->ifa_addr->sa_family == AF_INET &&
(in.s_addr == ia->ia_broadaddr.sin_addr.s_addr ||
/*
- * Check for old-style (host 0) broadcast.
+ * Check for old-style (host 0) broadcast, but
+ * taking into account that RFC 3021 obsoletes it.
*/
- t == ia->ia_subnet) &&
+ (ia->ia_subnetmask != IN_RFC3021_MASK &&
+ t == ia->ia_subnet)) &&
/*
* Check for an all one subnetmask. These
* only exist when an interface gets a secondary
diff --git a/sys/netinet/in.h b/sys/netinet/in.h
index d5e4290..52844f0 100644
--- a/sys/netinet/in.h
+++ b/sys/netinet/in.h
@@ -392,6 +392,8 @@ __END_DECLS
#define IN_LOOPBACKNET 127 /* official! */
+#define IN_RFC3021_MASK (u_int32_t)0xfffffffe
+
/*
* Options for use with [gs]etsockopt at the IP level.
* First word of comment is data type; bool is stored in int.
OpenPOWER on IntegriCloud