udp6_usrreq.c revision 1.130
1/*	$NetBSD: udp6_usrreq.c,v 1.130 2017/07/06 17:08:57 christos Exp $	*/
2/*	$KAME: udp6_usrreq.c,v 1.86 2001/05/27 17:33:00 itojun Exp $	*/
3
4/*
5 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
6 * All rights reserved.
7 *
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
10 * are met:
11 * 1. Redistributions of source code must retain the above copyright
12 *    notice, this list of conditions and the following disclaimer.
13 * 2. Redistributions in binary form must reproduce the above copyright
14 *    notice, this list of conditions and the following disclaimer in the
15 *    documentation and/or other materials provided with the distribution.
16 * 3. Neither the name of the project nor the names of its contributors
17 *    may be used to endorse or promote products derived from this software
18 *    without specific prior written permission.
19 *
20 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
21 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
24 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
25 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
26 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
27 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
28 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
29 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
30 * SUCH DAMAGE.
31 */
32
33/*
34 * Copyright (c) 1982, 1986, 1989, 1993
35 *	The Regents of the University of California.  All rights reserved.
36 *
37 * Redistribution and use in source and binary forms, with or without
38 * modification, are permitted provided that the following conditions
39 * are met:
40 * 1. Redistributions of source code must retain the above copyright
41 *    notice, this list of conditions and the following disclaimer.
42 * 2. Redistributions in binary form must reproduce the above copyright
43 *    notice, this list of conditions and the following disclaimer in the
44 *    documentation and/or other materials provided with the distribution.
45 * 3. Neither the name of the University nor the names of its contributors
46 *    may be used to endorse or promote products derived from this software
47 *    without specific prior written permission.
48 *
49 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
50 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
51 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
52 * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
53 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
54 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
55 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
56 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
57 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
58 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
59 * SUCH DAMAGE.
60 *
61 *	@(#)udp_var.h	8.1 (Berkeley) 6/10/93
62 */
63
64#include <sys/cdefs.h>
65__KERNEL_RCSID(0, "$NetBSD: udp6_usrreq.c,v 1.130 2017/07/06 17:08:57 christos Exp $");
66
67#ifdef _KERNEL_OPT
68#include "opt_inet.h"
69#include "opt_inet_csum.h"
70#include "opt_ipsec.h"
71#include "opt_net_mpsafe.h"
72#endif
73
74#include <sys/param.h>
75#include <sys/mbuf.h>
76#include <sys/protosw.h>
77#include <sys/socket.h>
78#include <sys/socketvar.h>
79#include <sys/systm.h>
80#include <sys/proc.h>
81#include <sys/syslog.h>
82#include <sys/domain.h>
83#include <sys/sysctl.h>
84
85#include <net/if.h>
86#include <net/if_types.h>
87
88#include <netinet/in.h>
89#include <netinet/in_var.h>
90#include <netinet/in_systm.h>
91#include <netinet/in_offload.h>
92#include <netinet/ip.h>
93#include <netinet/ip_var.h>
94#include <netinet/in_pcb.h>
95#include <netinet/udp.h>
96#include <netinet/udp_var.h>
97#include <netinet/udp_private.h>
98
99#include <netinet/ip6.h>
100#include <netinet/icmp6.h>
101#include <netinet6/ip6_var.h>
102#include <netinet6/ip6_private.h>
103#include <netinet6/in6_pcb.h>
104#include <netinet6/udp6_var.h>
105#include <netinet6/udp6_private.h>
106#include <netinet6/ip6protosw.h>
107#include <netinet6/scope6_var.h>
108
109#ifdef IPSEC
110#include <netipsec/ipsec.h>
111#include <netipsec/ipsec_var.h>
112#include <netipsec/ipsec_private.h>
113#ifdef INET6
114#include <netipsec/ipsec6.h>
115#endif
116#endif	/* IPSEC */
117
118#include "faith.h"
119#if defined(NFAITH) && NFAITH > 0
120#include <net/if_faith.h>
121#endif
122
123/*
124 * UDP protocol implementation.
125 * Per RFC 768, August, 1980.
126 */
127
128extern struct inpcbtable udbtable;
129
130percpu_t *udp6stat_percpu;
131
132/* UDP on IP6 parameters */
133static int	udp6_sendspace = 9216;	/* really max datagram size */
134static int	udp6_recvspace = 40 * (1024 + sizeof(struct sockaddr_in6));
135					/* 40 1K datagrams */
136
137static	void udp6_notify(struct in6pcb *, int);
138static	void sysctl_net_inet6_udp6_setup(struct sysctllog **);
139
140#ifdef UDP_CSUM_COUNTERS
141#include <sys/device.h>
142struct evcnt udp6_hwcsum_bad = EVCNT_INITIALIZER(EVCNT_TYPE_MISC,
143    NULL, "udp6", "hwcsum bad");
144struct evcnt udp6_hwcsum_ok = EVCNT_INITIALIZER(EVCNT_TYPE_MISC,
145    NULL, "udp6", "hwcsum ok");
146struct evcnt udp6_hwcsum_data = EVCNT_INITIALIZER(EVCNT_TYPE_MISC,
147    NULL, "udp6", "hwcsum data");
148struct evcnt udp6_swcsum = EVCNT_INITIALIZER(EVCNT_TYPE_MISC,
149    NULL, "udp6", "swcsum");
150
151EVCNT_ATTACH_STATIC(udp6_hwcsum_bad);
152EVCNT_ATTACH_STATIC(udp6_hwcsum_ok);
153EVCNT_ATTACH_STATIC(udp6_hwcsum_data);
154EVCNT_ATTACH_STATIC(udp6_swcsum);
155
156#define	UDP_CSUM_COUNTER_INCR(ev)	(ev)->ev_count++
157#else
158#define	UDP_CSUM_COUNTER_INCR(ev)	/* nothing */
159#endif
160
161void
162udp6_init(void)
163{
164	sysctl_net_inet6_udp6_setup(NULL);
165	udp6stat_percpu = percpu_alloc(sizeof(uint64_t) * UDP6_NSTATS);
166
167	udp_init_common();
168}
169
170/*
171 * Notify a udp user of an asynchronous error;
172 * just wake up so that he can collect error status.
173 */
174static	void
175udp6_notify(struct in6pcb *in6p, int errno)
176{
177	in6p->in6p_socket->so_error = errno;
178	sorwakeup(in6p->in6p_socket);
179	sowwakeup(in6p->in6p_socket);
180}
181
182void *
183udp6_ctlinput(int cmd, const struct sockaddr *sa, void *d)
184{
185	struct udphdr uh;
186	struct ip6_hdr *ip6;
187	const struct sockaddr_in6 *sa6 = (const struct sockaddr_in6 *)sa;
188	struct mbuf *m;
189	int off;
190	void *cmdarg;
191	struct ip6ctlparam *ip6cp = NULL;
192	const struct sockaddr_in6 *sa6_src = NULL;
193	void (*notify)(struct in6pcb *, int) = udp6_notify;
194	struct udp_portonly {
195		u_int16_t uh_sport;
196		u_int16_t uh_dport;
197	} *uhp;
198
199	if (sa->sa_family != AF_INET6 ||
200	    sa->sa_len != sizeof(struct sockaddr_in6))
201		return NULL;
202
203	if ((unsigned)cmd >= PRC_NCMDS)
204		return NULL;
205	if (PRC_IS_REDIRECT(cmd))
206		notify = in6_rtchange, d = NULL;
207	else if (cmd == PRC_HOSTDEAD)
208		d = NULL;
209	else if (cmd == PRC_MSGSIZE) {
210		/* special code is present, see below */
211		notify = in6_rtchange;
212	}
213	else if (inet6ctlerrmap[cmd] == 0)
214		return NULL;
215
216	/* if the parameter is from icmp6, decode it. */
217	if (d != NULL) {
218		ip6cp = (struct ip6ctlparam *)d;
219		m = ip6cp->ip6c_m;
220		ip6 = ip6cp->ip6c_ip6;
221		off = ip6cp->ip6c_off;
222		cmdarg = ip6cp->ip6c_cmdarg;
223		sa6_src = ip6cp->ip6c_src;
224	} else {
225		m = NULL;
226		ip6 = NULL;
227		cmdarg = NULL;
228		sa6_src = &sa6_any;
229		off = 0;
230	}
231
232	if (ip6) {
233		/*
234		 * XXX: We assume that when IPV6 is non NULL,
235		 * M and OFF are valid.
236		 */
237
238		/* check if we can safely examine src and dst ports */
239		if (m->m_pkthdr.len < off + sizeof(*uhp)) {
240			if (cmd == PRC_MSGSIZE)
241				icmp6_mtudisc_update((struct ip6ctlparam *)d, 0);
242			return NULL;
243		}
244
245		memset(&uh, 0, sizeof(uh));
246		m_copydata(m, off, sizeof(*uhp), (void *)&uh);
247
248		if (cmd == PRC_MSGSIZE) {
249			int valid = 0;
250
251			/*
252			 * Check to see if we have a valid UDP socket
253			 * corresponding to the address in the ICMPv6 message
254			 * payload.
255			 */
256			if (in6_pcblookup_connect(&udbtable, &sa6->sin6_addr,
257			    uh.uh_dport, (const struct in6_addr *)&sa6_src->sin6_addr,
258						  uh.uh_sport, 0, 0))
259				valid++;
260#if 0
261			/*
262			 * As the use of sendto(2) is fairly popular,
263			 * we may want to allow non-connected pcb too.
264			 * But it could be too weak against attacks...
265			 * We should at least check if the local address (= s)
266			 * is really ours.
267			 */
268			else if (in6_pcblookup_bind(&udbtable, &sa6->sin6_addr,
269			    uh.uh_dport, 0))
270				valid++;
271#endif
272
273			/*
274			 * Depending on the value of "valid" and routing table
275			 * size (mtudisc_{hi,lo}wat), we will:
276			 * - recalculate the new MTU and create the
277			 *   corresponding routing entry, or
278			 * - ignore the MTU change notification.
279			 */
280			icmp6_mtudisc_update((struct ip6ctlparam *)d, valid);
281
282			/*
283			 * regardless of if we called
284			 * icmp6_mtudisc_update(), we need to call
285			 * in6_pcbnotify(), to notify path MTU change
286			 * to the userland (RFC3542), because some
287			 * unconnected sockets may share the same
288			 * destination and want to know the path MTU.
289			 */
290		}
291
292		(void) in6_pcbnotify(&udbtable, sa, uh.uh_dport,
293		    sin6tocsa(sa6_src), uh.uh_sport, cmd, cmdarg,
294		    notify);
295	} else {
296		(void) in6_pcbnotify(&udbtable, sa, 0,
297		    sin6tocsa(sa6_src), 0, cmd, cmdarg, notify);
298	}
299	return NULL;
300}
301
302int
303udp6_ctloutput(int op, struct socket *so, struct sockopt *sopt)
304{
305	int s;
306	int error = 0;
307	int family;
308
309	family = so->so_proto->pr_domain->dom_family;
310
311	s = splsoftnet();
312	switch (family) {
313#ifdef INET
314	case PF_INET:
315		if (sopt->sopt_level != IPPROTO_UDP) {
316			error = ip_ctloutput(op, so, sopt);
317			goto end;
318		}
319		break;
320#endif
321#ifdef INET6
322	case PF_INET6:
323		if (sopt->sopt_level != IPPROTO_UDP) {
324			error = ip6_ctloutput(op, so, sopt);
325			goto end;
326		}
327		break;
328#endif
329	default:
330		error = EAFNOSUPPORT;
331		goto end;
332	}
333	error = EINVAL;
334
335end:
336	splx(s);
337	return error;
338}
339
340static void
341udp6_sendup(struct mbuf *m, int off /* offset of data portion */,
342	struct sockaddr *src, struct socket *so)
343{
344	struct mbuf *opts = NULL;
345	struct mbuf *n;
346	struct in6pcb *in6p;
347
348	KASSERT(so != NULL);
349	KASSERT(so->so_proto->pr_domain->dom_family == AF_INET6);
350	in6p = sotoin6pcb(so);
351	KASSERT(in6p != NULL);
352
353#if defined(IPSEC)
354	/* check AH/ESP integrity. */
355	if (ipsec_used && ipsec6_in_reject(m, in6p)) {
356		IPSEC6_STATINC(IPSEC_STAT_IN_POLVIO);
357		if ((n = m_copypacket(m, M_DONTWAIT)) != NULL)
358			icmp6_error(n, ICMP6_DST_UNREACH,
359			    ICMP6_DST_UNREACH_ADMIN, 0);
360		return;
361	}
362#endif /*IPSEC*/
363
364	if ((n = m_copypacket(m, M_DONTWAIT)) != NULL) {
365		if (in6p->in6p_flags & IN6P_CONTROLOPTS
366		    || SOOPT_TIMESTAMP(in6p->in6p_socket->so_options)) {
367			struct ip6_hdr *ip6 = mtod(n, struct ip6_hdr *);
368			ip6_savecontrol(in6p, &opts, ip6, n);
369		}
370
371		m_adj(n, off);
372		if (sbappendaddr(&so->so_rcv, src, n, opts) == 0) {
373			m_freem(n);
374			if (opts)
375				m_freem(opts);
376			so->so_rcv.sb_overflowed++;
377			UDP6_STATINC(UDP6_STAT_FULLSOCK);
378		} else
379			sorwakeup(so);
380	}
381}
382
383int
384udp6_realinput(int af, struct sockaddr_in6 *src, struct sockaddr_in6 *dst,
385	struct mbuf *m, int off)
386{
387	u_int16_t sport, dport;
388	int rcvcnt;
389	struct in6_addr src6, *dst6;
390	const struct in_addr *dst4;
391	struct inpcb_hdr *inph;
392	struct in6pcb *in6p;
393
394	rcvcnt = 0;
395	off += sizeof(struct udphdr);	/* now, offset of payload */
396
397	if (af != AF_INET && af != AF_INET6)
398		goto bad;
399	if (src->sin6_family != AF_INET6 || dst->sin6_family != AF_INET6)
400		goto bad;
401
402	src6 = src->sin6_addr;
403	if (sa6_recoverscope(src) != 0) {
404		/* XXX: should be impossible. */
405		goto bad;
406	}
407	sport = src->sin6_port;
408
409	dport = dst->sin6_port;
410	dst4 = (struct in_addr *)&dst->sin6_addr.s6_addr[12];
411	dst6 = &dst->sin6_addr;
412
413	if (IN6_IS_ADDR_MULTICAST(dst6) ||
414	    (af == AF_INET && IN_MULTICAST(dst4->s_addr))) {
415		/*
416		 * Deliver a multicast or broadcast datagram to *all* sockets
417		 * for which the local and remote addresses and ports match
418		 * those of the incoming datagram.  This allows more than
419		 * one process to receive multi/broadcasts on the same port.
420		 * (This really ought to be done for unicast datagrams as
421		 * well, but that would cause problems with existing
422		 * applications that open both address-specific sockets and
423		 * a wildcard socket listening to the same port -- they would
424		 * end up receiving duplicates of every unicast datagram.
425		 * Those applications open the multiple sockets to overcome an
426		 * inadequacy of the UDP socket interface, but for backwards
427		 * compatibility we avoid the problem here rather than
428		 * fixing the interface.  Maybe 4.5BSD will remedy this?)
429		 */
430
431		/*
432		 * KAME note: traditionally we dropped udpiphdr from mbuf here.
433		 * we need udpiphdr for IPsec processing so we do that later.
434		 */
435		/*
436		 * Locate pcb(s) for datagram.
437		 */
438		TAILQ_FOREACH(inph, &udbtable.inpt_queue, inph_queue) {
439			in6p = (struct in6pcb *)inph;
440			if (in6p->in6p_af != AF_INET6)
441				continue;
442
443			if (in6p->in6p_lport != dport)
444				continue;
445			if (!IN6_IS_ADDR_UNSPECIFIED(&in6p->in6p_laddr)) {
446				if (!IN6_ARE_ADDR_EQUAL(&in6p->in6p_laddr,
447				    dst6))
448					continue;
449			} else {
450				if (IN6_IS_ADDR_V4MAPPED(dst6) &&
451				    (in6p->in6p_flags & IN6P_IPV6_V6ONLY))
452					continue;
453			}
454			if (!IN6_IS_ADDR_UNSPECIFIED(&in6p->in6p_faddr)) {
455				if (!IN6_ARE_ADDR_EQUAL(&in6p->in6p_faddr,
456				    &src6) || in6p->in6p_fport != sport)
457					continue;
458			} else {
459				if (IN6_IS_ADDR_V4MAPPED(&src6) &&
460				    (in6p->in6p_flags & IN6P_IPV6_V6ONLY))
461					continue;
462			}
463
464			udp6_sendup(m, off, sin6tosa(src), in6p->in6p_socket);
465			rcvcnt++;
466
467			/*
468			 * Don't look for additional matches if this one does
469			 * not have either the SO_REUSEPORT or SO_REUSEADDR
470			 * socket options set.  This heuristic avoids searching
471			 * through all pcbs in the common case of a non-shared
472			 * port.  It assumes that an application will never
473			 * clear these options after setting them.
474			 */
475			if ((in6p->in6p_socket->so_options &
476			    (SO_REUSEPORT|SO_REUSEADDR)) == 0)
477				break;
478		}
479	} else {
480		/*
481		 * Locate pcb for datagram.
482		 */
483		in6p = in6_pcblookup_connect(&udbtable, &src6, sport, dst6,
484					     dport, 0, 0);
485		if (in6p == 0) {
486			UDP_STATINC(UDP_STAT_PCBHASHMISS);
487			in6p = in6_pcblookup_bind(&udbtable, dst6, dport, 0);
488			if (in6p == 0)
489				return rcvcnt;
490		}
491
492		udp6_sendup(m, off, sin6tosa(src), in6p->in6p_socket);
493		rcvcnt++;
494	}
495
496bad:
497	return rcvcnt;
498}
499
500int
501udp6_input_checksum(struct mbuf *m, const struct udphdr *uh, int off, int len)
502{
503
504	/*
505	 * XXX it's better to record and check if this mbuf is
506	 * already checked.
507	 */
508
509	if (__predict_false((m->m_flags & M_LOOP) && !udp_do_loopback_cksum)) {
510		goto good;
511	}
512	if (uh->uh_sum == 0) {
513		UDP6_STATINC(UDP6_STAT_NOSUM);
514		goto bad;
515	}
516
517	switch (m->m_pkthdr.csum_flags &
518	    ((m_get_rcvif_NOMPSAFE(m)->if_csum_flags_rx & M_CSUM_UDPv6) |
519	    M_CSUM_TCP_UDP_BAD | M_CSUM_DATA)) {
520	case M_CSUM_UDPv6|M_CSUM_TCP_UDP_BAD:
521		UDP_CSUM_COUNTER_INCR(&udp6_hwcsum_bad);
522		UDP6_STATINC(UDP6_STAT_BADSUM);
523		goto bad;
524
525#if 0 /* notyet */
526	case M_CSUM_UDPv6|M_CSUM_DATA:
527#endif
528
529	case M_CSUM_UDPv6:
530		/* Checksum was okay. */
531		UDP_CSUM_COUNTER_INCR(&udp6_hwcsum_ok);
532		break;
533
534	default:
535		/*
536		 * Need to compute it ourselves.  Maybe skip checksum
537		 * on loopback interfaces.
538		 */
539		UDP_CSUM_COUNTER_INCR(&udp6_swcsum);
540		if (in6_cksum(m, IPPROTO_UDP, off, len) != 0) {
541			UDP6_STATINC(UDP6_STAT_BADSUM);
542			goto bad;
543		}
544	}
545
546good:
547	return 0;
548bad:
549	return -1;
550}
551
552int
553udp6_input(struct mbuf **mp, int *offp, int proto)
554{
555	struct mbuf *m = *mp;
556	int off = *offp;
557	struct sockaddr_in6 src, dst;
558	struct ip6_hdr *ip6;
559	struct udphdr *uh;
560	u_int32_t plen, ulen;
561
562	ip6 = mtod(m, struct ip6_hdr *);
563
564#if defined(NFAITH) && 0 < NFAITH
565	if (faithprefix(&ip6->ip6_dst)) {
566		/* send icmp6 host unreach? */
567		m_freem(m);
568		return IPPROTO_DONE;
569	}
570#endif
571
572	UDP6_STATINC(UDP6_STAT_IPACKETS);
573
574	/* check for jumbogram is done in ip6_input.  we can trust pkthdr.len */
575	plen = m->m_pkthdr.len - off;
576	IP6_EXTHDR_GET(uh, struct udphdr *, m, off, sizeof(struct udphdr));
577	if (uh == NULL) {
578		IP6_STATINC(IP6_STAT_TOOSHORT);
579		return IPPROTO_DONE;
580	}
581	/*
582	 * Enforce alignment requirements that are violated in
583	 * some cases, see kern/50766 for details.
584	 */
585        if (UDP_HDR_ALIGNED_P(uh) == 0) {
586                m = m_copyup(m, off + sizeof(struct udphdr), 0);
587                if (m == NULL) {
588                        IP6_STATINC(IP6_STAT_TOOSHORT);
589                        return IPPROTO_DONE;
590                }
591		ip6 = mtod(m, struct ip6_hdr *);
592                uh = (struct udphdr *)(mtod(m, char *) + off);
593        }
594	KASSERT(UDP_HDR_ALIGNED_P(uh));
595	ulen = ntohs((u_short)uh->uh_ulen);
596	/*
597	 * RFC2675 section 4: jumbograms will have 0 in the UDP header field,
598	 * iff payload length > 0xffff.
599	 */
600	if (ulen == 0 && plen > 0xffff)
601		ulen = plen;
602
603	if (plen != ulen) {
604		UDP6_STATINC(UDP6_STAT_BADLEN);
605		goto bad;
606	}
607
608	/* destination port of 0 is illegal, based on RFC768. */
609	if (uh->uh_dport == 0)
610		goto bad;
611
612	/* Be proactive about malicious use of IPv4 mapped address */
613	if (IN6_IS_ADDR_V4MAPPED(&ip6->ip6_src) ||
614	    IN6_IS_ADDR_V4MAPPED(&ip6->ip6_dst)) {
615		/* XXX stat */
616		goto bad;
617	}
618
619	/*
620	 * Checksum extended UDP header and data.  Maybe skip checksum
621	 * on loopback interfaces.
622	 */
623	if (udp6_input_checksum(m, uh, off, ulen))
624		goto bad;
625
626	/*
627	 * Construct source and dst sockaddrs.
628	 */
629	memset(&src, 0, sizeof(src));
630	src.sin6_family = AF_INET6;
631	src.sin6_len = sizeof(struct sockaddr_in6);
632	src.sin6_addr = ip6->ip6_src;
633	src.sin6_port = uh->uh_sport;
634	memset(&dst, 0, sizeof(dst));
635	dst.sin6_family = AF_INET6;
636	dst.sin6_len = sizeof(struct sockaddr_in6);
637	dst.sin6_addr = ip6->ip6_dst;
638	dst.sin6_port = uh->uh_dport;
639
640	if (udp6_realinput(AF_INET6, &src, &dst, m, off) == 0) {
641		if (m->m_flags & M_MCAST) {
642			UDP6_STATINC(UDP6_STAT_NOPORTMCAST);
643			goto bad;
644		}
645		UDP6_STATINC(UDP6_STAT_NOPORT);
646		icmp6_error(m, ICMP6_DST_UNREACH, ICMP6_DST_UNREACH_NOPORT, 0);
647		m = NULL;
648	}
649
650bad:
651	if (m)
652		m_freem(m);
653	return IPPROTO_DONE;
654}
655
656static int
657udp6_attach(struct socket *so, int proto)
658{
659	struct in6pcb *in6p;
660	int s, error;
661
662	KASSERT(sotoin6pcb(so) == NULL);
663	sosetlock(so);
664
665	/*
666	 * MAPPED_ADDR implementation spec:
667	 *  Always attach for IPv6, and only when necessary for IPv4.
668	 */
669	s = splsoftnet();
670	error = in6_pcballoc(so, &udbtable);
671	splx(s);
672	if (error) {
673		return error;
674	}
675	error = soreserve(so, udp6_sendspace, udp6_recvspace);
676	if (error) {
677		return error;
678	}
679	in6p = sotoin6pcb(so);
680	in6p->in6p_cksum = -1;	/* just to be sure */
681
682	KASSERT(solocked(so));
683	return 0;
684}
685
686static void
687udp6_detach(struct socket *so)
688{
689	struct in6pcb *in6p = sotoin6pcb(so);
690	int s;
691
692	KASSERT(solocked(so));
693	KASSERT(in6p != NULL);
694
695	s = splsoftnet();
696	in6_pcbdetach(in6p);
697	splx(s);
698}
699
700static int
701udp6_accept(struct socket *so, struct sockaddr *nam)
702{
703	KASSERT(solocked(so));
704
705	return EOPNOTSUPP;
706}
707
708static int
709udp6_bind(struct socket *so, struct sockaddr *nam, struct lwp *l)
710{
711	struct in6pcb *in6p = sotoin6pcb(so);
712	struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)nam;
713	int error = 0;
714	int s;
715
716	KASSERT(solocked(so));
717	KASSERT(in6p != NULL);
718
719	s = splsoftnet();
720	error = in6_pcbbind(in6p, sin6, l);
721	splx(s);
722	return error;
723}
724
725static int
726udp6_listen(struct socket *so, struct lwp *l)
727{
728	KASSERT(solocked(so));
729
730	return EOPNOTSUPP;
731}
732
733static int
734udp6_connect(struct socket *so, struct sockaddr *nam, struct lwp *l)
735{
736	struct in6pcb *in6p = sotoin6pcb(so);
737	int error = 0;
738	int s;
739
740	KASSERT(solocked(so));
741	KASSERT(in6p != NULL);
742
743	if (!IN6_IS_ADDR_UNSPECIFIED(&in6p->in6p_faddr))
744		return EISCONN;
745	s = splsoftnet();
746	error = in6_pcbconnect(in6p, (struct sockaddr_in6 *)nam, l);
747	splx(s);
748	if (error == 0)
749		soisconnected(so);
750
751	return error;
752}
753
754static int
755udp6_connect2(struct socket *so, struct socket *so2)
756{
757	KASSERT(solocked(so));
758
759	return EOPNOTSUPP;
760}
761
762static int
763udp6_disconnect(struct socket *so)
764{
765	struct in6pcb *in6p = sotoin6pcb(so);
766	int s;
767
768	KASSERT(solocked(so));
769	KASSERT(in6p != NULL);
770
771	if (IN6_IS_ADDR_UNSPECIFIED(&in6p->in6p_faddr))
772		return ENOTCONN;
773
774	s = splsoftnet();
775	in6_pcbdisconnect(in6p);
776	memset((void *)&in6p->in6p_laddr, 0, sizeof(in6p->in6p_laddr));
777	splx(s);
778
779	so->so_state &= ~SS_ISCONNECTED;	/* XXX */
780	in6_pcbstate(in6p, IN6P_BOUND);		/* XXX */
781	return 0;
782}
783
784static int
785udp6_shutdown(struct socket *so)
786{
787	int s;
788
789	s = splsoftnet();
790	socantsendmore(so);
791	splx(s);
792
793	return 0;
794}
795
796static int
797udp6_abort(struct socket *so)
798{
799	int s;
800
801	KASSERT(solocked(so));
802	KASSERT(sotoin6pcb(so) != NULL);
803
804	s = splsoftnet();
805	soisdisconnected(so);
806	in6_pcbdetach(sotoin6pcb(so));
807	splx(s);
808
809	return 0;
810}
811
812static int
813udp6_ioctl(struct socket *so, u_long cmd, void *addr6, struct ifnet *ifp)
814{
815	/*
816	 * MAPPED_ADDR implementation info:
817	 *  Mapped addr support for PRU_CONTROL is not necessary.
818	 *  Because typical user of PRU_CONTROL is such as ifconfig,
819	 *  and they don't associate any addr to their socket.  Then
820	 *  socket family is only hint about the PRU_CONTROL'ed address
821	 *  family, especially when getting addrs from kernel.
822	 *  So AF_INET socket need to be used to control AF_INET addrs,
823	 *  and AF_INET6 socket for AF_INET6 addrs.
824	 */
825	return in6_control(so, cmd, addr6, ifp);
826}
827
828static int
829udp6_stat(struct socket *so, struct stat *ub)
830{
831	KASSERT(solocked(so));
832
833	/* stat: don't bother with a blocksize */
834	return 0;
835}
836
837static int
838udp6_peeraddr(struct socket *so, struct sockaddr *nam)
839{
840	KASSERT(solocked(so));
841	KASSERT(sotoin6pcb(so) != NULL);
842	KASSERT(nam != NULL);
843
844	in6_setpeeraddr(sotoin6pcb(so), (struct sockaddr_in6 *)nam);
845	return 0;
846}
847
848static int
849udp6_sockaddr(struct socket *so, struct sockaddr *nam)
850{
851	KASSERT(solocked(so));
852	KASSERT(sotoin6pcb(so) != NULL);
853	KASSERT(nam != NULL);
854
855	in6_setsockaddr(sotoin6pcb(so), (struct sockaddr_in6 *)nam);
856	return 0;
857}
858
859static int
860udp6_rcvd(struct socket *so, int flags, struct lwp *l)
861{
862	KASSERT(solocked(so));
863
864	return EOPNOTSUPP;
865}
866
867static int
868udp6_recvoob(struct socket *so, struct mbuf *m, int flags)
869{
870	KASSERT(solocked(so));
871
872	return EOPNOTSUPP;
873}
874
875static int
876udp6_send(struct socket *so, struct mbuf *m, struct sockaddr *nam,
877    struct mbuf *control, struct lwp *l)
878{
879	struct in6pcb *in6p = sotoin6pcb(so);
880	int error = 0;
881	int s;
882
883	KASSERT(solocked(so));
884	KASSERT(in6p != NULL);
885	KASSERT(m != NULL);
886
887	s = splsoftnet();
888	error = udp6_output(in6p, m, (struct sockaddr_in6 *)nam, control, l);
889	splx(s);
890
891	return error;
892}
893
894static int
895udp6_sendoob(struct socket *so, struct mbuf *m, struct mbuf *control)
896{
897	KASSERT(solocked(so));
898
899	if (m)
900		m_freem(m);
901	if (control)
902		m_freem(control);
903
904	return EOPNOTSUPP;
905}
906
907static int
908udp6_purgeif(struct socket *so, struct ifnet *ifp)
909{
910
911	mutex_enter(softnet_lock);
912	in6_pcbpurgeif0(&udbtable, ifp);
913#ifdef NET_MPSAFE
914	mutex_exit(softnet_lock);
915#endif
916	in6_purgeif(ifp);
917#ifdef NET_MPSAFE
918	mutex_enter(softnet_lock);
919#endif
920	in6_pcbpurgeif(&udbtable, ifp);
921	mutex_exit(softnet_lock);
922
923	return 0;
924}
925
926static int
927sysctl_net_inet6_udp6_stats(SYSCTLFN_ARGS)
928{
929
930	return (NETSTAT_SYSCTL(udp6stat_percpu, UDP6_NSTATS));
931}
932
933static void
934sysctl_net_inet6_udp6_setup(struct sysctllog **clog)
935{
936
937	sysctl_createv(clog, 0, NULL, NULL,
938		       CTLFLAG_PERMANENT,
939		       CTLTYPE_NODE, "inet6", NULL,
940		       NULL, 0, NULL, 0,
941		       CTL_NET, PF_INET6, CTL_EOL);
942	sysctl_createv(clog, 0, NULL, NULL,
943		       CTLFLAG_PERMANENT,
944		       CTLTYPE_NODE, "udp6",
945		       SYSCTL_DESCR("UDPv6 related settings"),
946		       NULL, 0, NULL, 0,
947		       CTL_NET, PF_INET6, IPPROTO_UDP, CTL_EOL);
948
949	sysctl_createv(clog, 0, NULL, NULL,
950		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
951		       CTLTYPE_INT, "sendspace",
952		       SYSCTL_DESCR("Default UDP send buffer size"),
953		       NULL, 0, &udp6_sendspace, 0,
954		       CTL_NET, PF_INET6, IPPROTO_UDP, UDP6CTL_SENDSPACE,
955		       CTL_EOL);
956	sysctl_createv(clog, 0, NULL, NULL,
957		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
958		       CTLTYPE_INT, "recvspace",
959		       SYSCTL_DESCR("Default UDP receive buffer size"),
960		       NULL, 0, &udp6_recvspace, 0,
961		       CTL_NET, PF_INET6, IPPROTO_UDP, UDP6CTL_RECVSPACE,
962		       CTL_EOL);
963	sysctl_createv(clog, 0, NULL, NULL,
964		       CTLFLAG_PERMANENT|CTLFLAG_READWRITE,
965		       CTLTYPE_INT, "do_loopback_cksum",
966		       SYSCTL_DESCR("Perform UDP checksum on loopback"),
967		       NULL, 0, &udp_do_loopback_cksum, 0,
968		       CTL_NET, PF_INET6, IPPROTO_UDP, UDP6CTL_LOOPBACKCKSUM,
969		       CTL_EOL);
970	sysctl_createv(clog, 0, NULL, NULL,
971		       CTLFLAG_PERMANENT,
972		       CTLTYPE_STRUCT, "pcblist",
973		       SYSCTL_DESCR("UDP protocol control block list"),
974		       sysctl_inpcblist, 0, &udbtable, 0,
975		       CTL_NET, PF_INET6, IPPROTO_UDP, CTL_CREATE,
976		       CTL_EOL);
977	sysctl_createv(clog, 0, NULL, NULL,
978		       CTLFLAG_PERMANENT,
979		       CTLTYPE_STRUCT, "stats",
980		       SYSCTL_DESCR("UDPv6 statistics"),
981		       sysctl_net_inet6_udp6_stats, 0, NULL, 0,
982		       CTL_NET, PF_INET6, IPPROTO_UDP, UDP6CTL_STATS,
983		       CTL_EOL);
984}
985
986void
987udp6_statinc(u_int stat)
988{
989
990	KASSERT(stat < UDP6_NSTATS);
991	UDP6_STATINC(stat);
992}
993
994PR_WRAP_USRREQS(udp6)
995#define	udp6_attach	udp6_attach_wrapper
996#define	udp6_detach	udp6_detach_wrapper
997#define	udp6_accept	udp6_accept_wrapper
998#define	udp6_bind	udp6_bind_wrapper
999#define	udp6_listen	udp6_listen_wrapper
1000#define	udp6_connect	udp6_connect_wrapper
1001#define	udp6_connect2	udp6_connect2_wrapper
1002#define	udp6_disconnect	udp6_disconnect_wrapper
1003#define	udp6_shutdown	udp6_shutdown_wrapper
1004#define	udp6_abort	udp6_abort_wrapper
1005#define	udp6_ioctl	udp6_ioctl_wrapper
1006#define	udp6_stat	udp6_stat_wrapper
1007#define	udp6_peeraddr	udp6_peeraddr_wrapper
1008#define	udp6_sockaddr	udp6_sockaddr_wrapper
1009#define	udp6_rcvd	udp6_rcvd_wrapper
1010#define	udp6_recvoob	udp6_recvoob_wrapper
1011#define	udp6_send	udp6_send_wrapper
1012#define	udp6_sendoob	udp6_sendoob_wrapper
1013#define	udp6_purgeif	udp6_purgeif_wrapper
1014
1015const struct pr_usrreqs udp6_usrreqs = {
1016	.pr_attach	= udp6_attach,
1017	.pr_detach	= udp6_detach,
1018	.pr_accept	= udp6_accept,
1019	.pr_bind	= udp6_bind,
1020	.pr_listen	= udp6_listen,
1021	.pr_connect	= udp6_connect,
1022	.pr_connect2	= udp6_connect2,
1023	.pr_disconnect	= udp6_disconnect,
1024	.pr_shutdown	= udp6_shutdown,
1025	.pr_abort	= udp6_abort,
1026	.pr_ioctl	= udp6_ioctl,
1027	.pr_stat	= udp6_stat,
1028	.pr_peeraddr	= udp6_peeraddr,
1029	.pr_sockaddr	= udp6_sockaddr,
1030	.pr_rcvd	= udp6_rcvd,
1031	.pr_recvoob	= udp6_recvoob,
1032	.pr_send	= udp6_send,
1033	.pr_sendoob	= udp6_sendoob,
1034	.pr_purgeif	= udp6_purgeif,
1035};
1036