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