aboutsummaryrefslogtreecommitdiff
path: root/sys/netinet/ip_input.c
diff options
context:
space:
mode:
Diffstat (limited to 'sys/netinet/ip_input.c')
-rw-r--r--sys/netinet/ip_input.c289
1 files changed, 119 insertions, 170 deletions
diff --git a/sys/netinet/ip_input.c b/sys/netinet/ip_input.c
index 44500c46b0d8..82d7acdd0710 100644
--- a/sys/netinet/ip_input.c
+++ b/sys/netinet/ip_input.c
@@ -27,18 +27,16 @@
* 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.
- *
- * @(#)ip_input.c 8.2 (Berkeley) 1/4/94
*/
#include <sys/cdefs.h>
-__FBSDID("$FreeBSD$");
-
#include "opt_bootp.h"
+#include "opt_inet.h"
#include "opt_ipstealth.h"
#include "opt_ipsec.h"
#include "opt_route.h"
#include "opt_rss.h"
+#include "opt_sctp.h"
#include <sys/param.h>
#include <sys/systm.h>
@@ -61,6 +59,7 @@ __FBSDID("$FreeBSD$");
#include <net/if_types.h>
#include <net/if_var.h>
#include <net/if_dl.h>
+#include <net/if_private.h>
#include <net/pfil.h>
#include <net/route.h>
#include <net/route/nhop.h>
@@ -76,13 +75,17 @@ __FBSDID("$FreeBSD$");
#include <netinet/in_fib.h>
#include <netinet/in_pcb.h>
#include <netinet/ip_var.h>
+#include <netinet/ip_encap.h>
#include <netinet/ip_fw.h>
#include <netinet/ip_icmp.h>
+#include <netinet/igmp_var.h>
#include <netinet/ip_options.h>
#include <machine/in_cksum.h>
#include <netinet/ip_carp.h>
#include <netinet/in_rss.h>
-#include <netinet/ip_mroute.h>
+#ifdef SCTP
+#include <netinet/sctp_var.h>
+#endif
#include <netipsec/ipsec_support.h>
@@ -96,8 +99,7 @@ CTASSERT(sizeof(struct ip) == 20);
/* IP reassembly functions are defined in ip_reass.c. */
extern void ipreass_init(void);
-extern void ipreass_drain(void);
-extern void ipreass_slowtimo(void);
+extern void ipreass_vnet_init(void);
#ifdef VIMAGE
extern void ipreass_destroy(void);
#endif
@@ -130,7 +132,9 @@ SYSCTL_BOOL(_net_inet_ip, OID_AUTO, source_address_validation,
CTLFLAG_VNET | CTLFLAG_RW, &VNET_NAME(ip_sav), true,
"Drop incoming packets with source address that is a local address");
-VNET_DEFINE(pfil_head_t, inet_pfil_head); /* Packet filter hooks */
+/* Packet filter hooks */
+VNET_DEFINE(pfil_head_t, inet_pfil_head);
+VNET_DEFINE(pfil_head_t, inet_local_pfil_head);
static struct netisr_handler ip_nh = {
.nh_name = "ip",
@@ -163,9 +167,11 @@ static struct netisr_handler ip_direct_nh = {
};
#endif
-extern struct domain inetdomain;
-extern struct protosw inetsw[];
-u_char ip_protox[IPPROTO_MAX];
+ipproto_input_t *ip_protox[IPPROTO_MAX] = {
+ [0 ... IPPROTO_MAX - 1] = rip_input };
+ipproto_ctlinput_t *ip_ctlprotox[IPPROTO_MAX] = {
+ [0 ... IPPROTO_MAX - 1] = rip_ctlinput };
+
VNET_DEFINE(struct in_ifaddrhead, in_ifaddrhead); /* first inet address */
VNET_DEFINE(struct in_ifaddrhashhead *, in_ifaddrhashtbl); /* inet addr hash table */
VNET_DEFINE(u_long, in_ifaddrhmask); /* mask for hash table */
@@ -301,18 +307,16 @@ SYSCTL_PROC(_net_inet_ip, IPCTL_INTRDQDROPS, intr_direct_queue_drops,
* IP initialization: fill in IP protocol switch table.
* All protocols not implemented in kernel go to raw IP protocol handler.
*/
-void
-ip_init(void)
+static void
+ip_vnet_init(void *arg __unused)
{
struct pfil_head_args args;
- struct protosw *pr;
- int i;
CK_STAILQ_INIT(&V_in_ifaddrhead);
V_in_ifaddrhashtbl = hashinit(INADDR_NHASH, M_IFADDR, &V_in_ifaddrhmask);
/* Initialize IP reassembly queue. */
- ipreass_init();
+ ipreass_vnet_init();
/* Initialize packet filter hooks. */
args.pa_version = PFIL_VERSION;
@@ -321,6 +325,10 @@ ip_init(void)
args.pa_headname = PFIL_INET_NAME;
V_inet_pfil_head = pfil_head_register(&args);
+ args.pa_flags = PFIL_OUT;
+ args.pa_headname = PFIL_INET_LOCAL_NAME;
+ V_inet_local_pfil_head = pfil_head_register(&args);
+
if (hhook_head_register(HHOOK_TYPE_IPSEC_IN, AF_INET,
&V_ipsec_hhh_in[HHOOK_IPSEC_INET],
HHOOK_WAITOK | HHOOK_HEADISINVNET) != 0)
@@ -332,42 +340,45 @@ ip_init(void)
printf("%s: WARNING: unable to register output helper hook\n",
__func__);
- /* Skip initialization of globals for non-default instances. */
#ifdef VIMAGE
- if (!IS_DEFAULT_VNET(curvnet)) {
- netisr_register_vnet(&ip_nh);
+ netisr_register_vnet(&ip_nh);
#ifdef RSS
- netisr_register_vnet(&ip_direct_nh);
+ netisr_register_vnet(&ip_direct_nh);
#endif
- return;
- }
#endif
+}
+VNET_SYSINIT(ip_vnet_init, SI_SUB_PROTO_DOMAIN, SI_ORDER_FOURTH,
+ ip_vnet_init, NULL);
- pr = pffindproto(PF_INET, IPPROTO_RAW, SOCK_RAW);
- if (pr == NULL)
- panic("ip_init: PF_INET not found");
+static void
+ip_init(const void *unused __unused)
+{
+
+ ipreass_init();
- /* Initialize the entire ip_protox[] array to IPPROTO_RAW. */
- for (i = 0; i < IPPROTO_MAX; i++)
- ip_protox[i] = pr - inetsw;
/*
- * Cycle through IP protocols and put them into the appropriate place
- * in ip_protox[].
+ * Register statically compiled protocols, that are unlikely to
+ * ever become dynamic.
*/
- for (pr = inetdomain.dom_protosw;
- pr < inetdomain.dom_protoswNPROTOSW; pr++)
- if (pr->pr_domain->dom_family == PF_INET &&
- pr->pr_protocol && pr->pr_protocol != IPPROTO_RAW) {
- /* Be careful to only index valid IP protocols. */
- if (pr->pr_protocol < IPPROTO_MAX)
- ip_protox[pr->pr_protocol] = pr - inetsw;
- }
+ IPPROTO_REGISTER(IPPROTO_ICMP, icmp_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_IGMP, igmp_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_RSVP, rsvp_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_IPV4, encap4_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_MOBILE, encap4_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_ETHERIP, encap4_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_GRE, encap4_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_IPV6, encap4_input, NULL);
+ IPPROTO_REGISTER(IPPROTO_PIM, encap4_input, NULL);
+#ifdef SCTP /* XXX: has a loadable & static version */
+ IPPROTO_REGISTER(IPPROTO_SCTP, sctp_input, sctp_ctlinput);
+#endif
netisr_register(&ip_nh);
#ifdef RSS
netisr_register(&ip_direct_nh);
#endif
}
+SYSINIT(ip_init, SI_SUB_PROTO_DOMAIN, SI_ORDER_THIRD, ip_init, NULL);
#ifdef VIMAGE
static void
@@ -433,8 +444,7 @@ ip_direct_input(struct mbuf *m)
}
#endif /* IPSEC */
IPSTAT_INC(ips_delivered);
- (*inetsw[ip_protox[ip->ip_p]].pr_input)(&m, &hlen, ip->ip_p);
- return;
+ ip_protox[ip->ip_p](&m, &hlen, ip->ip_p);
}
#endif
@@ -445,7 +455,6 @@ ip_direct_input(struct mbuf *m)
void
ip_input(struct mbuf *m)
{
- MROUTER_RLOCK_TRACKER;
struct ip *ip = NULL;
struct in_ifaddr *ia = NULL;
struct ifaddr *ifa;
@@ -512,6 +521,11 @@ ip_input(struct mbuf *m)
goto bad;
}
}
+ /* The unspecified address can appear only as a src address - RFC1122 */
+ if (__predict_false(ntohl(ip->ip_dst.s_addr) == INADDR_ANY)) {
+ IPSTAT_INC(ips_badaddr);
+ goto bad;
+ }
if (m->m_pkthdr.csum_flags & CSUM_IP_CHECKED) {
sum = !(m->m_pkthdr.csum_flags & CSUM_IP_VALID);
@@ -527,12 +541,6 @@ ip_input(struct mbuf *m)
goto bad;
}
-#ifdef ALTQ
- if (altq_input != NULL && (*altq_input)(m, AF_INET) == 0)
- /* packet is dropped by traffic conditioner */
- return;
-#endif
-
ip_len = ntohs(ip->ip_len);
if (__predict_false(ip_len < hlen)) {
IPSTAT_INC(ips_badlen);
@@ -560,8 +568,9 @@ tooshort:
/*
* Try to forward the packet, but if we fail continue.
- * ip_tryforward() does not generate redirects, so fall
- * through to normal processing if redirects are required.
+ * ip_tryforward() may generate redirects these days.
+ * XXX the logic below falling through to normal processing
+ * if redirects are required should be revisited as well.
* ip_tryforward() does inbound and outbound packet firewall
* processing. If firewall has decided that destination becomes
* our local address, it sets M_FASTFWD_OURS flag. In this
@@ -574,6 +583,10 @@ tooshort:
IPSEC_CAPS(ipv4, m, IPSEC_CAP_OPERABLE) == 0)
#endif
) {
+ /*
+ * ip_dooptions() was run so we can ignore the source route (or
+ * any IP options case) case for redirects in ip_tryforward().
+ */
if ((m = ip_tryforward(m)) == NULL)
return;
if (m->m_flags & M_FASTFWD_OURS) {
@@ -605,11 +618,9 @@ tooshort:
goto passin;
odst = ip->ip_dst;
- if (pfil_run_hooks(V_inet_pfil_head, &m, ifp, PFIL_IN, NULL) !=
+ if (pfil_mbuf_in(V_inet_pfil_head, &m, ifp, NULL) !=
PFIL_PASS)
return;
- if (m == NULL) /* consumed by filter */
- return;
ip = mtod(m, struct ip *);
dchg = (odst.s_addr != ip->ip_dst.s_addr);
@@ -736,7 +747,6 @@ passin:
ia = NULL;
}
if (IN_MULTICAST(ntohl(ip->ip_dst.s_addr))) {
- MROUTER_RLOCK();
/*
* RFC 3927 2.7: Do not forward multicast packets from
* IN_LINKLOCAL.
@@ -751,7 +761,6 @@ passin:
* must be discarded, else it may be accepted below.
*/
if (ip_mforward && ip_mforward(ip, ifp, m, 0) != 0) {
- MROUTER_RUNLOCK();
IPSTAT_INC(ips_cantforward);
m_freem(m);
return;
@@ -763,12 +772,10 @@ passin:
* host belongs to their destination groups.
*/
if (ip->ip_p == IPPROTO_IGMP) {
- MROUTER_RUNLOCK();
goto ours;
}
IPSTAT_INC(ips_forward);
}
- MROUTER_RUNLOCK();
/*
* Assume the packet is for us, to avoid prematurely taking
* a lock on the in_multi hash. Protocols must perform
@@ -810,6 +817,18 @@ ours:
#endif /* IPSTEALTH */
/*
+ * We are going to ship the packet to the local protocol stack. Call the
+ * filter again for this 'output' action, allowing redirect-like rules
+ * to adjust the source address.
+ */
+ if (PFIL_HOOKED_OUT(V_inet_local_pfil_head)) {
+ if (pfil_mbuf_out(V_inet_local_pfil_head, &m, V_loif, NULL) !=
+ PFIL_PASS)
+ return;
+ ip = mtod(m, struct ip *);
+ }
+
+ /*
* Attempt reassembly; if it succeeds, proceed.
* ip_reass() will return a different mbuf.
*/
@@ -835,110 +854,44 @@ ours:
*/
IPSTAT_INC(ips_delivered);
- (*inetsw[ip_protox[ip->ip_p]].pr_input)(&m, &hlen, ip->ip_p);
+ ip_protox[ip->ip_p](&m, &hlen, ip->ip_p);
return;
bad:
m_freem(m);
}
-/*
- * IP timer processing;
- * if a timer expires on a reassembly
- * queue, discard it.
- */
-void
-ip_slowtimo(void)
-{
- VNET_ITERATOR_DECL(vnet_iter);
-
- VNET_LIST_RLOCK_NOSLEEP();
- VNET_FOREACH(vnet_iter) {
- CURVNET_SET(vnet_iter);
- ipreass_slowtimo();
- CURVNET_RESTORE();
- }
- VNET_LIST_RUNLOCK_NOSLEEP();
-}
-
-void
-ip_drain(void)
-{
- VNET_ITERATOR_DECL(vnet_iter);
-
- VNET_LIST_RLOCK_NOSLEEP();
- VNET_FOREACH(vnet_iter) {
- CURVNET_SET(vnet_iter);
- ipreass_drain();
- CURVNET_RESTORE();
- }
- VNET_LIST_RUNLOCK_NOSLEEP();
-}
-
-/*
- * The protocol to be inserted into ip_protox[] must be already registered
- * in inetsw[], either statically or through pf_proto_register().
- */
int
-ipproto_register(short ipproto)
+ipproto_register(uint8_t proto, ipproto_input_t input, ipproto_ctlinput_t ctl)
{
- struct protosw *pr;
- /* Sanity checks. */
- if (ipproto <= 0 || ipproto >= IPPROTO_MAX)
- return (EPROTONOSUPPORT);
+ MPASS(proto > 0);
/*
* The protocol slot must not be occupied by another protocol
- * already. An index pointing to IPPROTO_RAW is unused.
+ * already. An index pointing to rip_input() is unused.
*/
- pr = pffindproto(PF_INET, IPPROTO_RAW, SOCK_RAW);
- if (pr == NULL)
- return (EPFNOSUPPORT);
- if (ip_protox[ipproto] != pr - inetsw) /* IPPROTO_RAW */
+ if (ip_protox[proto] == rip_input) {
+ ip_protox[proto] = input;
+ ip_ctlprotox[proto] = ctl;
+ return (0);
+ } else
return (EEXIST);
-
- /* Find the protocol position in inetsw[] and set the index. */
- for (pr = inetdomain.dom_protosw;
- pr < inetdomain.dom_protoswNPROTOSW; pr++) {
- if (pr->pr_domain->dom_family == PF_INET &&
- pr->pr_protocol && pr->pr_protocol == ipproto) {
- ip_protox[pr->pr_protocol] = pr - inetsw;
- return (0);
- }
- }
- return (EPROTONOSUPPORT);
}
int
-ipproto_unregister(short ipproto)
+ipproto_unregister(uint8_t proto)
{
- struct protosw *pr;
- /* Sanity checks. */
- if (ipproto <= 0 || ipproto >= IPPROTO_MAX)
- return (EPROTONOSUPPORT);
+ MPASS(proto > 0);
- /* Check if the protocol was indeed registered. */
- pr = pffindproto(PF_INET, IPPROTO_RAW, SOCK_RAW);
- if (pr == NULL)
- return (EPFNOSUPPORT);
- if (ip_protox[ipproto] == pr - inetsw) /* IPPROTO_RAW */
+ if (ip_protox[proto] != rip_input) {
+ ip_protox[proto] = rip_input;
+ ip_ctlprotox[proto] = rip_ctlinput;
+ return (0);
+ } else
return (ENOENT);
-
- /* Reset the protocol slot to IPPROTO_RAW. */
- ip_protox[ipproto] = pr - inetsw;
- return (0);
}
-u_char inetctlerrmap[PRC_NCMDS] = {
- 0, 0, 0, 0,
- 0, EMSGSIZE, EHOSTDOWN, EHOSTUNREACH,
- EHOSTUNREACH, EHOSTUNREACH, ECONNREFUSED, ECONNREFUSED,
- EMSGSIZE, EHOSTUNREACH, 0, 0,
- 0, 0, EHOSTUNREACH, 0,
- ENOPROTOOPT, ECONNREFUSED
-};
-
/*
* Forward a packet. If some error occurs return the sender
* an icmp packet. Note we can't always generate a meaningful
@@ -1165,8 +1118,8 @@ ip_savecontrol(struct inpcb *inp, struct mbuf **mp, struct ip *ip,
} else {
bintime(&bt);
}
- *mp = sbcreatecontrol((caddr_t)&bt, sizeof(bt),
- SCM_BINTIME, SOL_SOCKET);
+ *mp = sbcreatecontrol(&bt, sizeof(bt), SCM_BINTIME,
+ SOL_SOCKET, M_NOWAIT);
if (*mp != NULL) {
mp = &(*mp)->m_next;
stamped = true;
@@ -1187,8 +1140,8 @@ ip_savecontrol(struct inpcb *inp, struct mbuf **mp, struct ip *ip,
} else {
microtime(&tv);
}
- *mp = sbcreatecontrol((caddr_t)&tv, sizeof(tv),
- SCM_TIMESTAMP, SOL_SOCKET);
+ *mp = sbcreatecontrol((caddr_t)&tv, sizeof(tv), SCM_TIMESTAMP,
+ SOL_SOCKET, M_NOWAIT);
if (*mp != NULL) {
mp = &(*mp)->m_next;
stamped = true;
@@ -1206,8 +1159,8 @@ ip_savecontrol(struct inpcb *inp, struct mbuf **mp, struct ip *ip,
} else {
nanotime(&ts);
}
- *mp = sbcreatecontrol((caddr_t)&ts, sizeof(ts),
- SCM_REALTIME, SOL_SOCKET);
+ *mp = sbcreatecontrol(&ts, sizeof(ts), SCM_REALTIME,
+ SOL_SOCKET, M_NOWAIT);
if (*mp != NULL) {
mp = &(*mp)->m_next;
stamped = true;
@@ -1220,8 +1173,8 @@ ip_savecontrol(struct inpcb *inp, struct mbuf **mp, struct ip *ip,
mbuf_tstmp2timespec(m, &ts);
else
nanouptime(&ts);
- *mp = sbcreatecontrol((caddr_t)&ts, sizeof(ts),
- SCM_MONOTONIC, SOL_SOCKET);
+ *mp = sbcreatecontrol(&ts, sizeof(ts), SCM_MONOTONIC,
+ SOL_SOCKET, M_NOWAIT);
if (*mp != NULL) {
mp = &(*mp)->m_next;
stamped = true;
@@ -1235,20 +1188,20 @@ ip_savecontrol(struct inpcb *inp, struct mbuf **mp, struct ip *ip,
sti.st_info_flags = ST_INFO_HW;
if ((m->m_flags & M_TSTMP_HPREC) != 0)
sti.st_info_flags |= ST_INFO_HW_HPREC;
- *mp = sbcreatecontrol((caddr_t)&sti, sizeof(sti), SCM_TIME_INFO,
- SOL_SOCKET);
+ *mp = sbcreatecontrol(&sti, sizeof(sti), SCM_TIME_INFO,
+ SOL_SOCKET, M_NOWAIT);
if (*mp != NULL)
mp = &(*mp)->m_next;
}
if (inp->inp_flags & INP_RECVDSTADDR) {
- *mp = sbcreatecontrol((caddr_t)&ip->ip_dst,
- sizeof(struct in_addr), IP_RECVDSTADDR, IPPROTO_IP);
+ *mp = sbcreatecontrol(&ip->ip_dst, sizeof(struct in_addr),
+ IP_RECVDSTADDR, IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
if (inp->inp_flags & INP_RECVTTL) {
- *mp = sbcreatecontrol((caddr_t)&ip->ip_ttl,
- sizeof(u_char), IP_RECVTTL, IPPROTO_IP);
+ *mp = sbcreatecontrol(&ip->ip_ttl, sizeof(u_char), IP_RECVTTL,
+ IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
@@ -1259,15 +1212,15 @@ ip_savecontrol(struct inpcb *inp, struct mbuf **mp, struct ip *ip,
*/
/* options were tossed already */
if (inp->inp_flags & INP_RECVOPTS) {
- *mp = sbcreatecontrol((caddr_t)opts_deleted_above,
- sizeof(struct in_addr), IP_RECVOPTS, IPPROTO_IP);
+ *mp = sbcreatecontrol(opts_deleted_above,
+ sizeof(struct in_addr), IP_RECVOPTS, IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
/* ip_srcroute doesn't do what we want here, need to fix */
if (inp->inp_flags & INP_RECVRETOPTS) {
- *mp = sbcreatecontrol((caddr_t)ip_srcroute(m),
- sizeof(struct in_addr), IP_RECVRETOPTS, IPPROTO_IP);
+ *mp = sbcreatecontrol(ip_srcroute(m), sizeof(struct in_addr),
+ IP_RECVRETOPTS, IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
@@ -1299,14 +1252,14 @@ makedummy:
sdl2->sdl_index = 0;
sdl2->sdl_nlen = sdl2->sdl_alen = sdl2->sdl_slen = 0;
}
- *mp = sbcreatecontrol((caddr_t)sdl2, sdl2->sdl_len,
- IP_RECVIF, IPPROTO_IP);
+ *mp = sbcreatecontrol(sdl2, sdl2->sdl_len, IP_RECVIF,
+ IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
if (inp->inp_flags & INP_RECVTOS) {
- *mp = sbcreatecontrol((caddr_t)&ip->ip_tos,
- sizeof(u_char), IP_RECVTOS, IPPROTO_IP);
+ *mp = sbcreatecontrol(&ip->ip_tos, sizeof(u_char), IP_RECVTOS,
+ IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
@@ -1321,12 +1274,12 @@ makedummy:
* XXX should handle the failure of one or the
* other - don't populate both?
*/
- *mp = sbcreatecontrol((caddr_t) &flowid,
- sizeof(uint32_t), IP_FLOWID, IPPROTO_IP);
+ *mp = sbcreatecontrol(&flowid, sizeof(uint32_t), IP_FLOWID,
+ IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
- *mp = sbcreatecontrol((caddr_t) &flow_type,
- sizeof(uint32_t), IP_FLOWTYPE, IPPROTO_IP);
+ *mp = sbcreatecontrol(&flow_type, sizeof(uint32_t),
+ IP_FLOWTYPE, IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
@@ -1340,8 +1293,8 @@ makedummy:
flow_type = M_HASHTYPE_GET(m);
if (rss_hash2bucket(flowid, flow_type, &rss_bucketid) == 0) {
- *mp = sbcreatecontrol((caddr_t) &rss_bucketid,
- sizeof(uint32_t), IP_RSSBUCKETID, IPPROTO_IP);
+ *mp = sbcreatecontrol(&rss_bucketid, sizeof(uint32_t),
+ IP_RSSBUCKETID, IPPROTO_IP, M_NOWAIT);
if (*mp)
mp = &(*mp)->m_next;
}
@@ -1364,10 +1317,6 @@ int
ip_rsvp_init(struct socket *so)
{
- if (so->so_type != SOCK_RAW ||
- so->so_proto->pr_protocol != IPPROTO_RSVP)
- return EOPNOTSUPP;
-
if (V_ip_rsvpd != NULL)
return EADDRINUSE;