]> git.saurik.com Git - apple/xnu.git/blob - bsd/netinet6/ip6_input.c
cdf3776b2b18ceca165d4f4950af1b774c2a1501
[apple/xnu.git] / bsd / netinet6 / ip6_input.c
1 /*
2 * Copyright (c) 2003-2008 Apple Inc. All rights reserved.
3 *
4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. The rights granted to you under the License
10 * may not be used to create, or enable the creation or redistribution of,
11 * unlawful or unlicensed copies of an Apple operating system, or to
12 * circumvent, violate, or enable the circumvention or violation of, any
13 * terms of an Apple operating system software license agreement.
14 *
15 * Please obtain a copy of the License at
16 * http://www.opensource.apple.com/apsl/ and read it before using this file.
17 *
18 * The Original Code and all software distributed under the License are
19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
23 * Please see the License for the specific language governing rights and
24 * limitations under the License.
25 *
26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@
27 */
28 /* $FreeBSD: src/sys/netinet6/ip6_input.c,v 1.11.2.10 2001/07/24 19:10:18 brooks Exp $ */
29 /* $KAME: ip6_input.c,v 1.194 2001/05/27 13:28:35 itojun Exp $ */
30
31 /*
32 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
33 * All rights reserved.
34 *
35 * Redistribution and use in source and binary forms, with or without
36 * modification, are permitted provided that the following conditions
37 * are met:
38 * 1. Redistributions of source code must retain the above copyright
39 * notice, this list of conditions and the following disclaimer.
40 * 2. Redistributions in binary form must reproduce the above copyright
41 * notice, this list of conditions and the following disclaimer in the
42 * documentation and/or other materials provided with the distribution.
43 * 3. Neither the name of the project nor the names of its contributors
44 * may be used to endorse or promote products derived from this software
45 * without specific prior written permission.
46 *
47 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
48 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
49 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
50 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
51 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
52 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
53 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
54 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
55 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
56 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
57 * SUCH DAMAGE.
58 */
59
60 /*
61 * Copyright (c) 1982, 1986, 1988, 1993
62 * The Regents of the University of California. All rights reserved.
63 *
64 * Redistribution and use in source and binary forms, with or without
65 * modification, are permitted provided that the following conditions
66 * are met:
67 * 1. Redistributions of source code must retain the above copyright
68 * notice, this list of conditions and the following disclaimer.
69 * 2. Redistributions in binary form must reproduce the above copyright
70 * notice, this list of conditions and the following disclaimer in the
71 * documentation and/or other materials provided with the distribution.
72 * 3. All advertising materials mentioning features or use of this software
73 * must display the following acknowledgement:
74 * This product includes software developed by the University of
75 * California, Berkeley and its contributors.
76 * 4. Neither the name of the University nor the names of its contributors
77 * may be used to endorse or promote products derived from this software
78 * without specific prior written permission.
79 *
80 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
81 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
82 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
83 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
84 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
85 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
86 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
87 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
88 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
89 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
90 * SUCH DAMAGE.
91 *
92 * @(#)ip_input.c 8.2 (Berkeley) 1/4/94
93 */
94
95
96 #include <sys/param.h>
97 #include <sys/systm.h>
98 #include <sys/malloc.h>
99 #include <sys/mbuf.h>
100 #include <sys/domain.h>
101 #include <sys/protosw.h>
102 #include <sys/socket.h>
103 #include <sys/socketvar.h>
104 #include <sys/errno.h>
105 #include <sys/time.h>
106 #include <sys/kernel.h>
107 #include <sys/syslog.h>
108 #include <sys/proc.h>
109 #include <sys/kauth.h>
110
111 #include <net/if.h>
112 #include <net/if_var.h>
113 #include <net/if_types.h>
114 #include <net/if_dl.h>
115 #include <net/route.h>
116 #include <net/kpi_protocol.h>
117
118 #include <netinet/in.h>
119 #include <netinet/in_systm.h>
120 #if INET
121 #include <netinet/ip.h>
122 #include <netinet/ip_icmp.h>
123 #endif /*INET*/
124 #include <netinet/ip6.h>
125 #include <netinet6/in6_var.h>
126 #include <netinet6/ip6_var.h>
127 #include <netinet/in_pcb.h>
128 #include <netinet/icmp6.h>
129 #include <netinet6/in6_ifattach.h>
130 #include <netinet6/nd6.h>
131 #include <netinet6/in6_prefix.h>
132
133 #if IPSEC
134 #include <netinet6/ipsec.h>
135 #if INET6
136 #include <netinet6/ipsec6.h>
137 #endif
138 extern int ipsec_bypass;
139 #endif
140
141 #include <netinet6/ip6_fw.h>
142
143 #include <netinet/kpi_ipfilter_var.h>
144
145 #include <netinet6/ip6protosw.h>
146
147 /* we need it for NLOOP. */
148 #include "loop.h"
149 #include "faith.h"
150
151 #include <net/net_osdep.h>
152
153 #if PF
154 #include <net/pfvar.h>
155 #endif /* PF */
156
157 extern struct domain inet6domain;
158 extern struct ip6protosw inet6sw[];
159
160 struct ip6protosw * ip6_protox[IPPROTO_MAX];
161 static int ip6qmaxlen = IFQ_MAXLEN;
162 struct in6_ifaddr *in6_ifaddrs;
163
164 int ip6_forward_srcrt; /* XXX */
165 int ip6_sourcecheck; /* XXX */
166 int ip6_sourcecheck_interval; /* XXX */
167 const int int6intrq_present = 1;
168
169 int ip6_ours_check_algorithm;
170 int in6_init2done = 0;
171
172
173 #if IPFW2
174 /* firewall hooks */
175 ip6_fw_chk_t *ip6_fw_chk_ptr;
176 ip6_fw_ctl_t *ip6_fw_ctl_ptr;
177 int ip6_fw_enable = 1;
178 #endif
179
180 struct ip6stat ip6stat;
181
182 #ifdef __APPLE__
183 struct ifqueue ip6intrq;
184 lck_mtx_t *ip6_mutex;
185 lck_mtx_t *dad6_mutex;
186 lck_mtx_t *nd6_mutex;
187 lck_mtx_t *prefix6_mutex;
188 lck_mtx_t *scope6_mutex;
189 lck_attr_t *ip6_mutex_attr;
190 lck_grp_t *ip6_mutex_grp;
191 lck_grp_attr_t *ip6_mutex_grp_attr;
192 extern lck_mtx_t *inet6_domain_mutex;
193 #endif
194 extern int loopattach_done;
195
196 static void ip6_init2(void *);
197 static struct ip6aux *ip6_setdstifaddr(struct mbuf *, struct in6_ifaddr *);
198
199 static int ip6_hopopts_input(u_int32_t *, u_int32_t *, struct mbuf **, int *);
200 #if PULLDOWN_TEST
201 static struct mbuf *ip6_pullexthdr(struct mbuf *, size_t, int);
202 #endif
203
204 #ifdef __APPLE__
205 void gifattach(void);
206 void faithattach(void);
207 void stfattach(void);
208 #endif
209
210 extern lck_mtx_t *domain_proto_mtx;
211
212
213 static void
214 ip6_proto_input(
215 __unused protocol_family_t protocol,
216 mbuf_t packet)
217 {
218 ip6_input(packet);
219 }
220
221 /*
222 * IP6 initialization: fill in IP6 protocol switch table.
223 * All protocols not implemented in kernel go to raw IP6 protocol handler.
224 */
225 void
226 ip6_init()
227 {
228 struct ip6protosw *pr;
229 int i;
230 struct timeval tv;
231
232 #if DIAGNOSTIC
233 if (sizeof(struct protosw) != sizeof(struct ip6protosw))
234 panic("sizeof(protosw) != sizeof(ip6protosw)");
235 #endif
236 pr = (struct ip6protosw *)pffindproto_locked(PF_INET6, IPPROTO_RAW, SOCK_RAW);
237 if (pr == 0)
238 panic("ip6_init");
239 for (i = 0; i < IPPROTO_MAX; i++)
240 ip6_protox[i] = pr;
241 for (pr = (struct ip6protosw*)inet6domain.dom_protosw; pr; pr = pr->pr_next) {
242 if(!(pr->pr_domain)) continue; /* If uninitialized, skip */
243 if (pr->pr_domain->dom_family == PF_INET6 &&
244 pr->pr_protocol && pr->pr_protocol != IPPROTO_RAW) {
245 ip6_protox[pr->pr_protocol] = pr;
246 }
247 }
248
249 ip6_mutex_grp_attr = lck_grp_attr_alloc_init();
250
251 ip6_mutex_grp = lck_grp_alloc_init("ip6", ip6_mutex_grp_attr);
252 ip6_mutex_attr = lck_attr_alloc_init();
253
254 if ((ip6_mutex = lck_mtx_alloc_init(ip6_mutex_grp, ip6_mutex_attr)) == NULL) {
255 panic("ip6_init: can't alloc ip6_mutex\n");
256 }
257 if ((dad6_mutex = lck_mtx_alloc_init(ip6_mutex_grp, ip6_mutex_attr)) == NULL) {
258 panic("ip6_init: can't alloc dad6_mutex\n");
259 }
260 if ((nd6_mutex = lck_mtx_alloc_init(ip6_mutex_grp, ip6_mutex_attr)) == NULL) {
261 panic("ip6_init: can't alloc nd6_mutex\n");
262 }
263
264 if ((prefix6_mutex = lck_mtx_alloc_init(ip6_mutex_grp, ip6_mutex_attr)) == NULL) {
265 panic("ip6_init: can't alloc prefix6_mutex\n");
266 }
267
268 if ((scope6_mutex = lck_mtx_alloc_init(ip6_mutex_grp, ip6_mutex_attr)) == NULL) {
269 panic("ip6_init: can't alloc scope6_mutex\n");
270 }
271
272
273 inet6domain.dom_flags = DOM_REENTRANT;
274
275 ip6intrq.ifq_maxlen = ip6qmaxlen;
276 in6_ifaddr_init();
277 nd6_init();
278 frag6_init();
279 icmp6_init();
280 /*
281 * in many cases, random() here does NOT return random number
282 * as initialization during bootstrap time occur in fixed order.
283 */
284 microtime(&tv);
285 ip6_flow_seq = random() ^ tv.tv_usec;
286 microtime(&tv);
287 ip6_desync_factor = (random() ^ tv.tv_usec) % MAX_TEMP_DESYNC_FACTOR;
288 timeout(ip6_init2, (caddr_t)0, 1 * hz);
289
290 lck_mtx_unlock(domain_proto_mtx);
291 proto_register_input(PF_INET6, ip6_proto_input, NULL, 0);
292 lck_mtx_lock(domain_proto_mtx);
293 }
294
295 static void
296 ip6_init2(
297 __unused void *dummy)
298 {
299 /*
300 * to route local address of p2p link to loopback,
301 * assign loopback address first.
302 */
303 if (loopattach_done == 0) {
304 timeout(ip6_init2, (caddr_t)0, 1 * hz);
305 return;
306 }
307 (void) in6_ifattach(lo_ifp, NULL, NULL);
308
309 #ifdef __APPLE__
310 /* nd6_timer_init */
311 timeout(nd6_timer, (caddr_t)0, hz);
312
313 /* router renumbering prefix list maintenance */
314 timeout(in6_rr_timer, (caddr_t)0, hz);
315
316 /* timer for regeneranation of temporary addresses randomize ID */
317 timeout(in6_tmpaddrtimer, (caddr_t)0,
318 (ip6_temp_preferred_lifetime - ip6_desync_factor -
319 ip6_temp_regen_advance) * hz);
320
321 #if NGIF
322 gifattach();
323 #endif
324 #if NFAITH
325 faithattach();
326 #endif
327 #if NSTF
328 stfattach();
329 #endif
330 #else
331 /* nd6_timer_init */
332
333 callout_init(&nd6_timer_ch);
334 callout_reset(&nd6_timer_ch, hz, nd6_timer, NULL);
335
336 /* router renumbering prefix list maintenance */
337 callout_init(&in6_rr_timer_ch);
338 callout_reset(&in6_rr_timer_ch, hz, in6_rr_timer, NULL);
339
340 /* timer for regeneranation of temporary addresses randomize ID */
341 callout_reset(&in6_tmpaddrtimer_ch,
342 (ip6_temp_preferred_lifetime - ip6_desync_factor -
343 ip6_temp_regen_advance) * hz,
344 in6_tmpaddrtimer, NULL);
345 #endif
346
347 in6_init2done = 1;
348 }
349
350 #if __FreeBSD__
351 /* cheat */
352 /* This must be after route_init(), which is now SI_ORDER_THIRD */
353 SYSINIT(netinet6init2, SI_SUB_PROTO_DOMAIN, SI_ORDER_MIDDLE, ip6_init2, NULL);
354 #endif
355
356 /*
357 * ip6_forward_rt contains the route entry that was recently used during
358 * the forwarding of an IPv6 packet and thus acts as a route cache. Access
359 * to this variable is protected by the global lock ip6_mutex.
360 */
361 static struct route_in6 ip6_forward_rt;
362
363 void
364 ip6_input(m)
365 struct mbuf *m;
366 {
367 struct ip6_hdr *ip6;
368 int off = sizeof(struct ip6_hdr), nest;
369 u_int32_t plen;
370 u_int32_t rtalert = ~0;
371 int nxt = 0, ours = 0;
372 struct ifnet *deliverifp = NULL;
373 ipfilter_t inject_ipfref = 0;
374 int seen;
375
376 /*
377 * No need to proccess packet twice if we've
378 * already seen it
379 */
380 inject_ipfref = ipf_get_inject_filter(m);
381 if (inject_ipfref != 0) {
382 ip6 = mtod(m, struct ip6_hdr *);
383 nxt = ip6->ip6_nxt;
384 seen = 0;
385 goto injectit;
386 } else
387 seen = 1;
388
389 #if IPSEC
390 /*
391 * should the inner packet be considered authentic?
392 * see comment in ah4_input().
393 */
394 if (m) {
395 m->m_flags &= ~M_AUTHIPHDR;
396 m->m_flags &= ~M_AUTHIPDGM;
397 }
398 #endif
399
400 /*
401 * make sure we don't have onion peering information into m_aux.
402 */
403 ip6_delaux(m);
404
405 lck_mtx_lock(ip6_mutex);
406 /*
407 * mbuf statistics
408 */
409 if (m->m_flags & M_EXT) {
410 if (m->m_next)
411 ip6stat.ip6s_mext2m++;
412 else
413 ip6stat.ip6s_mext1++;
414 } else {
415 #define M2MMAX (sizeof(ip6stat.ip6s_m2m)/sizeof(ip6stat.ip6s_m2m[0]))
416 if (m->m_next) {
417 if (m->m_flags & M_LOOP) {
418 ip6stat.ip6s_m2m[ifnet_index(lo_ifp)]++; /* XXX */
419 } else if (m->m_pkthdr.rcvif->if_index < M2MMAX)
420 ip6stat.ip6s_m2m[m->m_pkthdr.rcvif->if_index]++;
421 else
422 ip6stat.ip6s_m2m[0]++;
423 } else
424 ip6stat.ip6s_m1++;
425 #undef M2MMAX
426 }
427
428 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_receive);
429 ip6stat.ip6s_total++;
430
431 #ifndef PULLDOWN_TEST
432 /*
433 * L2 bridge code and some other code can return mbuf chain
434 * that does not conform to KAME requirement. too bad.
435 * XXX: fails to join if interface MTU > MCLBYTES. jumbogram?
436 */
437 if (m && m->m_next != NULL && m->m_pkthdr.len < MCLBYTES) {
438 struct mbuf *n;
439
440 MGETHDR(n, M_DONTWAIT, MT_HEADER); /* MAC-OK */
441 if (n)
442 M_COPY_PKTHDR(n, m);
443 if (n && m->m_pkthdr.len > MHLEN) {
444 MCLGET(n, M_DONTWAIT);
445 if ((n->m_flags & M_EXT) == 0) {
446 m_freem(n);
447 n = NULL;
448 }
449 }
450 if (n == NULL) {
451 m_freem(m);
452 lck_mtx_unlock(ip6_mutex);
453 return; /*ENOBUFS*/
454 }
455
456 m_copydata(m, 0, m->m_pkthdr.len, mtod(n, caddr_t));
457 n->m_len = m->m_pkthdr.len;
458 m_freem(m);
459 m = n;
460 }
461 IP6_EXTHDR_CHECK(m, 0, sizeof(struct ip6_hdr),
462 {lck_mtx_unlock(ip6_mutex); return;});
463 #endif
464
465 if (m->m_len < sizeof(struct ip6_hdr)) {
466 struct ifnet *inifp;
467 inifp = m->m_pkthdr.rcvif;
468 if ((m = m_pullup(m, sizeof(struct ip6_hdr))) == 0) {
469 ip6stat.ip6s_toosmall++;
470 in6_ifstat_inc(inifp, ifs6_in_hdrerr);
471 lck_mtx_unlock(ip6_mutex);
472 return;
473 }
474 }
475
476 ip6 = mtod(m, struct ip6_hdr *);
477
478 if ((ip6->ip6_vfc & IPV6_VERSION_MASK) != IPV6_VERSION) {
479 ip6stat.ip6s_badvers++;
480 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_hdrerr);
481 goto bad;
482 }
483
484 ip6stat.ip6s_nxthist[ip6->ip6_nxt]++;
485
486 #if IPFW2
487 /*
488 * Check with the firewall...
489 */
490 if (ip6_fw_enable && ip6_fw_chk_ptr) {
491 u_short port = 0;
492 /* If ipfw says divert, we have to just drop packet */
493 /* use port as a dummy argument */
494 if ((*ip6_fw_chk_ptr)(&ip6, NULL, &port, &m)) {
495 m_freem(m);
496 m = NULL;
497 }
498 if (!m) {
499 lck_mtx_unlock(ip6_mutex);
500 return;
501 }
502 }
503 #endif
504
505 /*
506 * Check against address spoofing/corruption.
507 */
508 if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_src) ||
509 IN6_IS_ADDR_UNSPECIFIED(&ip6->ip6_dst)) {
510 /*
511 * XXX: "badscope" is not very suitable for a multicast source.
512 */
513 ip6stat.ip6s_badscope++;
514 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);
515 goto bad;
516 }
517 if ((IN6_IS_ADDR_LOOPBACK(&ip6->ip6_src) ||
518 IN6_IS_ADDR_LOOPBACK(&ip6->ip6_dst)) &&
519 (m->m_pkthdr.rcvif->if_flags & IFF_LOOPBACK) == 0) {
520 ip6stat.ip6s_badscope++;
521 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);
522 goto bad;
523 }
524
525 /*
526 * The following check is not documented in specs. A malicious
527 * party may be able to use IPv4 mapped addr to confuse tcp/udp stack
528 * and bypass security checks (act as if it was from 127.0.0.1 by using
529 * IPv6 src ::ffff:127.0.0.1). Be cautious.
530 *
531 * This check chokes if we are in an SIIT cloud. As none of BSDs
532 * support IPv4-less kernel compilation, we cannot support SIIT
533 * environment at all. So, it makes more sense for us to reject any
534 * malicious packets for non-SIIT environment, than try to do a
535 * partical support for SIIT environment.
536 */
537 if (IN6_IS_ADDR_V4MAPPED(&ip6->ip6_src) ||
538 IN6_IS_ADDR_V4MAPPED(&ip6->ip6_dst)) {
539 ip6stat.ip6s_badscope++;
540 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);
541 goto bad;
542 }
543 #if 0
544 /*
545 * Reject packets with IPv4 compatible addresses (auto tunnel).
546 *
547 * The code forbids auto tunnel relay case in RFC1933 (the check is
548 * stronger than RFC1933). We may want to re-enable it if mech-xx
549 * is revised to forbid relaying case.
550 */
551 if (IN6_IS_ADDR_V4COMPAT(&ip6->ip6_src) ||
552 IN6_IS_ADDR_V4COMPAT(&ip6->ip6_dst)) {
553 ip6stat.ip6s_badscope++;
554 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);
555 goto bad;
556 }
557 #endif
558
559 #if PF
560 /* Invoke inbound packet filter */
561 lck_mtx_unlock(ip6_mutex);
562 if (pf_af_hook(m->m_pkthdr.rcvif, NULL, &m, AF_INET6, TRUE) != 0) {
563 if (m != NULL) {
564 panic("%s: unexpected packet %p\n", __func__, m);
565 /* NOTREACHED */
566 }
567 /* Already freed by callee */
568 return;
569 }
570 ip6 = mtod(m, struct ip6_hdr *);
571 lck_mtx_lock(ip6_mutex);
572 #endif /* PF */
573
574 /* drop packets if interface ID portion is already filled */
575 if ((m->m_pkthdr.rcvif->if_flags & IFF_LOOPBACK) == 0) {
576 if (IN6_IS_SCOPE_LINKLOCAL(&ip6->ip6_src) &&
577 ip6->ip6_src.s6_addr16[1]) {
578 ip6stat.ip6s_badscope++;
579 goto bad;
580 }
581 if (IN6_IS_SCOPE_LINKLOCAL(&ip6->ip6_dst) &&
582 ip6->ip6_dst.s6_addr16[1]) {
583 ip6stat.ip6s_badscope++;
584 goto bad;
585 }
586 }
587
588 if (IN6_IS_SCOPE_LINKLOCAL(&ip6->ip6_src))
589 ip6->ip6_src.s6_addr16[1]
590 = htons(m->m_pkthdr.rcvif->if_index);
591 if (IN6_IS_SCOPE_LINKLOCAL(&ip6->ip6_dst))
592 ip6->ip6_dst.s6_addr16[1]
593 = htons(m->m_pkthdr.rcvif->if_index);
594
595 #if 0 /* this case seems to be unnecessary. (jinmei, 20010401) */
596 /*
597 * We use rt->rt_ifp to determine if the address is ours or not.
598 * If rt_ifp is lo0, the address is ours.
599 * The problem here is, rt->rt_ifp for fe80::%lo0/64 is set to lo0,
600 * so any address under fe80::%lo0/64 will be mistakenly considered
601 * local. The special case is supplied to handle the case properly
602 * by actually looking at interface addresses
603 * (using in6ifa_ifpwithaddr).
604 */
605 if ((m->m_pkthdr.rcvif->if_flags & IFF_LOOPBACK) != 0 &&
606 IN6_IS_ADDR_LINKLOCAL(&ip6->ip6_dst)) {
607 struct in6_ifaddr *ia6;
608 if (!(ia6 = in6ifa_ifpwithaddr(m->m_pkthdr.rcvif, &ip6->ip6_dst))) {
609 lck_mtx_unlock(ip6_mutex);
610 icmp6_error(m, ICMP6_DST_UNREACH,
611 ICMP6_DST_UNREACH_ADDR, 0);
612 /* m is already freed */
613 return;
614 }
615 ifafree(&ia6->ia_ifa);
616
617 ours = 1;
618 deliverifp = m->m_pkthdr.rcvif;
619 goto hbhcheck;
620 }
621 #endif
622
623 /*
624 * Multicast check
625 */
626 if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst)) {
627 struct in6_multi *in6m = 0;
628 struct ifnet *ifp = m->m_pkthdr.rcvif;
629
630 in6_ifstat_inc(ifp, ifs6_in_mcast);
631 /*
632 * See if we belong to the destination multicast group on the
633 * arrival interface.
634 */
635 ifnet_lock_shared(ifp);
636 IN6_LOOKUP_MULTI(ip6->ip6_dst, ifp, in6m);
637 ifnet_lock_done(ifp);
638 if (in6m)
639 ours = 1;
640 #if MROUTING
641 else if (!ip6_mrouter) {
642 #else
643 else {
644 #endif
645 ip6stat.ip6s_notmember++;
646 ip6stat.ip6s_cantforward++;
647 in6_ifstat_inc(ifp, ifs6_in_discard);
648 goto bad;
649 }
650 deliverifp = ifp;
651 goto hbhcheck;
652 }
653
654 if (ip6_forward_rt.ro_rt != NULL)
655 RT_LOCK(ip6_forward_rt.ro_rt);
656 /*
657 * Unicast check
658 */
659 if (ip6_forward_rt.ro_rt != NULL &&
660 (ip6_forward_rt.ro_rt->rt_flags & RTF_UP) &&
661 IN6_ARE_ADDR_EQUAL(&ip6->ip6_dst,
662 &((struct sockaddr_in6 *)(&ip6_forward_rt.ro_dst))->sin6_addr) &&
663 ip6_forward_rt.ro_rt->generation_id == route_generation) {
664 ip6stat.ip6s_forward_cachehit++;
665 } else {
666 struct sockaddr_in6 *dst6;
667
668 if (ip6_forward_rt.ro_rt != NULL) {
669 /* route is down/stale or destination is different */
670 ip6stat.ip6s_forward_cachemiss++;
671 RT_UNLOCK(ip6_forward_rt.ro_rt);
672 rtfree(ip6_forward_rt.ro_rt);
673 ip6_forward_rt.ro_rt = NULL;
674 }
675
676 bzero(&ip6_forward_rt.ro_dst, sizeof(struct sockaddr_in6));
677 dst6 = (struct sockaddr_in6 *)&ip6_forward_rt.ro_dst;
678 dst6->sin6_len = sizeof(struct sockaddr_in6);
679 dst6->sin6_family = AF_INET6;
680 dst6->sin6_addr = ip6->ip6_dst;
681 #if SCOPEDROUTING
682 ip6_forward_rt.ro_dst.sin6_scope_id =
683 in6_addr2scopeid(m->m_pkthdr.rcvif, &ip6->ip6_dst);
684 #endif
685
686 rtalloc_ign((struct route *)&ip6_forward_rt, RTF_PRCLONING);
687 if (ip6_forward_rt.ro_rt != NULL)
688 RT_LOCK(ip6_forward_rt.ro_rt);
689 }
690
691 #define rt6_key(r) ((struct sockaddr_in6 *)((r)->rt_nodes->rn_key))
692
693 /*
694 * Accept the packet if the forwarding interface to the destination
695 * according to the routing table is the loopback interface,
696 * unless the associated route has a gateway.
697 * Note that this approach causes to accept a packet if there is a
698 * route to the loopback interface for the destination of the packet.
699 * But we think it's even useful in some situations, e.g. when using
700 * a special daemon which wants to intercept the packet.
701 *
702 * XXX: some OSes automatically make a cloned route for the destination
703 * of an outgoing packet. If the outgoing interface of the packet
704 * is a loopback one, the kernel would consider the packet to be
705 * accepted, even if we have no such address assinged on the interface.
706 * We check the cloned flag of the route entry to reject such cases,
707 * assuming that route entries for our own addresses are not made by
708 * cloning (it should be true because in6_addloop explicitly installs
709 * the host route). However, we might have to do an explicit check
710 * while it would be less efficient. Or, should we rather install a
711 * reject route for such a case?
712 */
713 if (ip6_forward_rt.ro_rt != NULL &&
714 (ip6_forward_rt.ro_rt->rt_flags &
715 (RTF_HOST|RTF_GATEWAY)) == RTF_HOST &&
716 #if RTF_WASCLONED
717 !(ip6_forward_rt.ro_rt->rt_flags & RTF_WASCLONED) &&
718 #endif
719 #if 0
720 /*
721 * The check below is redundant since the comparison of
722 * the destination and the key of the rtentry has
723 * already done through looking up the routing table.
724 */
725 IN6_ARE_ADDR_EQUAL(&ip6->ip6_dst,
726 &rt6_key(ip6_forward_rt.ro_rt)->sin6_addr)
727 #endif
728 ip6_forward_rt.ro_rt->rt_ifp->if_type == IFT_LOOP) {
729 struct in6_ifaddr *ia6 =
730 (struct in6_ifaddr *)ip6_forward_rt.ro_rt->rt_ifa;
731
732 /*
733 * record address information into m_aux.
734 */
735 (void)ip6_setdstifaddr(m, ia6);
736
737 /*
738 * packets to a tentative, duplicated, or somehow invalid
739 * address must not be accepted.
740 */
741 if (!(ia6->ia6_flags & IN6_IFF_NOTREADY)) {
742 /* this address is ready */
743 ours = 1;
744 deliverifp = ia6->ia_ifp; /* correct? */
745 /* Count the packet in the ip address stats */
746 #ifndef __APPLE__
747
748 ia6->ia_ifa.if_ipackets++;
749 ia6->ia_ifa.if_ibytes += m->m_pkthdr.len;
750 #endif
751 RT_UNLOCK(ip6_forward_rt.ro_rt);
752 goto hbhcheck;
753 } else {
754 RT_UNLOCK(ip6_forward_rt.ro_rt);
755 /* address is not ready, so discard the packet. */
756 nd6log((LOG_INFO,
757 "ip6_input: packet to an unready address %s->%s\n",
758 ip6_sprintf(&ip6->ip6_src),
759 ip6_sprintf(&ip6->ip6_dst)));
760 goto bad;
761 }
762 }
763
764 /*
765 * FAITH(Firewall Aided Internet Translator)
766 */
767 #if defined(NFAITH) && 0 < NFAITH
768 if (ip6_keepfaith) {
769 if (ip6_forward_rt.ro_rt && ip6_forward_rt.ro_rt->rt_ifp
770 && ip6_forward_rt.ro_rt->rt_ifp->if_type == IFT_FAITH) {
771 /* XXX do we need more sanity checks? */
772 ours = 1;
773 deliverifp = ip6_forward_rt.ro_rt->rt_ifp; /* faith */
774 RT_UNLOCK(ip6_forward_rt.ro_rt);
775 goto hbhcheck;
776 }
777 }
778 #endif
779 if (ip6_forward_rt.ro_rt != NULL)
780 RT_UNLOCK(ip6_forward_rt.ro_rt);
781
782 /*
783 * Now there is no reason to process the packet if it's not our own
784 * and we're not a router.
785 */
786 if (!ip6_forwarding) {
787 ip6stat.ip6s_cantforward++;
788 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);
789 goto bad;
790 }
791
792 hbhcheck:
793 /*
794 * record address information into m_aux, if we don't have one yet.
795 * note that we are unable to record it, if the address is not listed
796 * as our interface address (e.g. multicast addresses, addresses
797 * within FAITH prefixes and such).
798 */
799 if (deliverifp && !ip6_getdstifaddr(m)) {
800 struct in6_ifaddr *ia6;
801
802 ia6 = in6_ifawithifp(deliverifp, &ip6->ip6_dst);
803 if (ia6) {
804 if (!ip6_setdstifaddr(m, ia6)) {
805 /*
806 * XXX maybe we should drop the packet here,
807 * as we could not provide enough information
808 * to the upper layers.
809 */
810 }
811 ifafree(&ia6->ia_ifa);
812 }
813 }
814
815 /*
816 * Process Hop-by-Hop options header if it's contained.
817 * m may be modified in ip6_hopopts_input().
818 * If a JumboPayload option is included, plen will also be modified.
819 */
820 plen = (u_int32_t)ntohs(ip6->ip6_plen);
821 if (ip6->ip6_nxt == IPPROTO_HOPOPTS) {
822 struct ip6_hbh *hbh;
823
824 if (ip6_hopopts_input(&plen, &rtalert, &m, &off)) {
825 #if 0 /*touches NULL pointer*/
826 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);
827 #endif
828 lck_mtx_unlock(ip6_mutex);
829 return; /* m have already been freed */
830 }
831
832 /* adjust pointer */
833 ip6 = mtod(m, struct ip6_hdr *);
834
835 /*
836 * if the payload length field is 0 and the next header field
837 * indicates Hop-by-Hop Options header, then a Jumbo Payload
838 * option MUST be included.
839 */
840 if (ip6->ip6_plen == 0 && plen == 0) {
841 /*
842 * Note that if a valid jumbo payload option is
843 * contained, ip6_hoptops_input() must set a valid
844 * (non-zero) payload length to the variable plen.
845 */
846 ip6stat.ip6s_badoptions++;
847 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_discard);
848 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_hdrerr);
849 lck_mtx_unlock(ip6_mutex);
850 icmp6_error(m, ICMP6_PARAM_PROB,
851 ICMP6_PARAMPROB_HEADER,
852 (caddr_t)&ip6->ip6_plen - (caddr_t)ip6);
853 return;
854 }
855 #ifndef PULLDOWN_TEST
856 /* ip6_hopopts_input() ensures that mbuf is contiguous */
857 hbh = (struct ip6_hbh *)(ip6 + 1);
858 #else
859 IP6_EXTHDR_GET(hbh, struct ip6_hbh *, m, sizeof(struct ip6_hdr),
860 sizeof(struct ip6_hbh));
861 if (hbh == NULL) {
862 ip6stat.ip6s_tooshort++;
863 lck_mtx_unlock(ip6_mutex);
864 return;
865 }
866 #endif
867 nxt = hbh->ip6h_nxt;
868
869 /*
870 * accept the packet if a router alert option is included
871 * and we act as an IPv6 router.
872 */
873 if (rtalert != ~0 && ip6_forwarding)
874 ours = 1;
875 } else
876 nxt = ip6->ip6_nxt;
877
878 /*
879 * Check that the amount of data in the buffers
880 * is as at least much as the IPv6 header would have us expect.
881 * Trim mbufs if longer than we expect.
882 * Drop packet if shorter than we expect.
883 */
884 if (m->m_pkthdr.len - sizeof(struct ip6_hdr) < plen) {
885 ip6stat.ip6s_tooshort++;
886 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_truncated);
887 goto bad;
888 }
889 if (m->m_pkthdr.len > sizeof(struct ip6_hdr) + plen) {
890 if (m->m_len == m->m_pkthdr.len) {
891 m->m_len = sizeof(struct ip6_hdr) + plen;
892 m->m_pkthdr.len = sizeof(struct ip6_hdr) + plen;
893 } else
894 m_adj(m, sizeof(struct ip6_hdr) + plen - m->m_pkthdr.len);
895 }
896
897 /*
898 * Forward if desirable.
899 */
900 if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst)) {
901 /*
902 * If we are acting as a multicast router, all
903 * incoming multicast packets are passed to the
904 * kernel-level multicast forwarding function.
905 * The packet is returned (relatively) intact; if
906 * ip6_mforward() returns a non-zero value, the packet
907 * must be discarded, else it may be accepted below.
908 */
909 #if MROUTING
910 if (ip6_mrouter && ip6_mforward(ip6, m->m_pkthdr.rcvif, m)) {
911 ip6stat.ip6s_cantforward++;
912 m_freem(m);
913 lck_mtx_unlock(ip6_mutex);
914 return;
915 }
916 #endif
917 if (!ours) {
918 m_freem(m);
919 lck_mtx_unlock(ip6_mutex);
920 return;
921 }
922 } else if (!ours) {
923 ip6_forward(m, &ip6_forward_rt, 0, 1);
924 lck_mtx_unlock(ip6_mutex);
925 return;
926 }
927
928 ip6 = mtod(m, struct ip6_hdr *);
929
930 /*
931 * Malicious party may be able to use IPv4 mapped addr to confuse
932 * tcp/udp stack and bypass security checks (act as if it was from
933 * 127.0.0.1 by using IPv6 src ::ffff:127.0.0.1). Be cautious.
934 *
935 * For SIIT end node behavior, you may want to disable the check.
936 * However, you will become vulnerable to attacks using IPv4 mapped
937 * source.
938 */
939 if (IN6_IS_ADDR_V4MAPPED(&ip6->ip6_src) ||
940 IN6_IS_ADDR_V4MAPPED(&ip6->ip6_dst)) {
941 ip6stat.ip6s_badscope++;
942 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_addrerr);
943 goto bad;
944 }
945
946 /*
947 * Tell launch routine the next header
948 */
949 ip6stat.ip6s_delivered++;
950 in6_ifstat_inc(deliverifp, ifs6_in_deliver);
951
952 lck_mtx_unlock(ip6_mutex);
953 injectit:
954 nest = 0;
955
956 while (nxt != IPPROTO_DONE) {
957 struct ipfilter *filter;
958
959 if (ip6_hdrnestlimit && (++nest > ip6_hdrnestlimit)) {
960 ip6stat.ip6s_toomanyhdr++;
961 goto badunlocked;
962 }
963
964 /*
965 * protection against faulty packet - there should be
966 * more sanity checks in header chain processing.
967 */
968 if (m->m_pkthdr.len < off) {
969 ip6stat.ip6s_tooshort++;
970 in6_ifstat_inc(m->m_pkthdr.rcvif, ifs6_in_truncated);
971 goto badunlocked;
972 }
973
974 #if 0
975 /*
976 * do we need to do it for every header? yeah, other
977 * functions can play with it (like re-allocate and copy).
978 */
979 mhist = ip6_addaux(m);
980 if (mhist && M_TRAILINGSPACE(mhist) >= sizeof(nxt)) {
981 hist = mtod(mhist, caddr_t) + mhist->m_len;
982 bcopy(&nxt, hist, sizeof(nxt));
983 mhist->m_len += sizeof(nxt);
984 } else {
985 ip6stat.ip6s_toomanyhdr++;
986 goto bad;
987 }
988 #endif
989
990 #if IPSEC
991 /*
992 * enforce IPsec policy checking if we are seeing last header.
993 * note that we do not visit this with protocols with pcb layer
994 * code - like udp/tcp/raw ip.
995 */
996 if ((ipsec_bypass == 0) && (ip6_protox[nxt]->pr_flags & PR_LASTHDR) != 0) {
997 if (ipsec6_in_reject(m, NULL)) {
998 IPSEC_STAT_INCREMENT(ipsec6stat.in_polvio);
999 goto badunlocked;
1000 }
1001 }
1002 #endif
1003
1004 /*
1005 * Call IP filter
1006 */
1007 if (!TAILQ_EMPTY(&ipv6_filters)) {
1008 ipf_ref();
1009 TAILQ_FOREACH(filter, &ipv6_filters, ipf_link) {
1010 if (seen == 0) {
1011 if ((struct ipfilter *)inject_ipfref == filter)
1012 seen = 1;
1013 } else if (filter->ipf_filter.ipf_input) {
1014 errno_t result;
1015
1016 result = filter->ipf_filter.ipf_input(
1017 filter->ipf_filter.cookie, (mbuf_t*)&m, off, nxt);
1018 if (result == EJUSTRETURN) {
1019 ipf_unref();
1020 return;
1021 }
1022 if (result != 0) {
1023 ipf_unref();
1024 m_freem(m);
1025 return;
1026 }
1027 }
1028 }
1029 ipf_unref();
1030 }
1031 if (!(ip6_protox[nxt]->pr_flags & PR_PROTOLOCK)) {
1032 lck_mtx_lock(inet6_domain_mutex);
1033 nxt = (*ip6_protox[nxt]->pr_input)(&m, &off);
1034 lck_mtx_unlock(inet6_domain_mutex);
1035 }
1036 else
1037 nxt = (*ip6_protox[nxt]->pr_input)(&m, &off);
1038 }
1039 return;
1040 bad:
1041 lck_mtx_unlock(ip6_mutex);
1042 badunlocked:
1043 m_freem(m);
1044 return;
1045 }
1046
1047 /*
1048 * set/grab in6_ifaddr correspond to IPv6 destination address.
1049 * XXX backward compatibility wrapper
1050 */
1051 static struct ip6aux *
1052 ip6_setdstifaddr(struct mbuf *m, struct in6_ifaddr *ia6)
1053 {
1054 struct ip6aux *n;
1055
1056 n = ip6_addaux(m);
1057 if (n)
1058 n->ip6a_dstia6 = ia6;
1059 return (struct ip6aux *)n; /* NULL if failed to set */
1060 }
1061
1062 struct in6_ifaddr *
1063 ip6_getdstifaddr(m)
1064 struct mbuf *m;
1065 {
1066 struct ip6aux *n;
1067
1068 n = ip6_findaux(m);
1069 if (n)
1070 return n->ip6a_dstia6;
1071 else
1072 return NULL;
1073 }
1074
1075 /*
1076 * Hop-by-Hop options header processing. If a valid jumbo payload option is
1077 * included, the real payload length will be stored in plenp.
1078 */
1079 static int
1080 ip6_hopopts_input(plenp, rtalertp, mp, offp)
1081 u_int32_t *plenp;
1082 u_int32_t *rtalertp; /* XXX: should be stored more smart way */
1083 struct mbuf **mp;
1084 int *offp;
1085 {
1086 struct mbuf *m = *mp;
1087 int off = *offp, hbhlen;
1088 struct ip6_hbh *hbh;
1089 u_int8_t *opt;
1090
1091 /* validation of the length of the header */
1092 #ifndef PULLDOWN_TEST
1093 IP6_EXTHDR_CHECK(m, off, sizeof(*hbh), return -1);
1094 hbh = (struct ip6_hbh *)(mtod(m, caddr_t) + off);
1095 hbhlen = (hbh->ip6h_len + 1) << 3;
1096
1097 IP6_EXTHDR_CHECK(m, off, hbhlen, return -1);
1098 hbh = (struct ip6_hbh *)(mtod(m, caddr_t) + off);
1099 #else
1100 IP6_EXTHDR_GET(hbh, struct ip6_hbh *, m,
1101 sizeof(struct ip6_hdr), sizeof(struct ip6_hbh));
1102 if (hbh == NULL) {
1103 ip6stat.ip6s_tooshort++;
1104 return -1;
1105 }
1106 hbhlen = (hbh->ip6h_len + 1) << 3;
1107 IP6_EXTHDR_GET(hbh, struct ip6_hbh *, m, sizeof(struct ip6_hdr),
1108 hbhlen);
1109 if (hbh == NULL) {
1110 ip6stat.ip6s_tooshort++;
1111 return -1;
1112 }
1113 #endif
1114 off += hbhlen;
1115 hbhlen -= sizeof(struct ip6_hbh);
1116 opt = (u_int8_t *)hbh + sizeof(struct ip6_hbh);
1117
1118 if (ip6_process_hopopts(m, (u_int8_t *)hbh + sizeof(struct ip6_hbh),
1119 hbhlen, rtalertp, plenp) < 0)
1120 return(-1);
1121
1122 *offp = off;
1123 *mp = m;
1124 return(0);
1125 }
1126
1127 /*
1128 * Search header for all Hop-by-hop options and process each option.
1129 * This function is separate from ip6_hopopts_input() in order to
1130 * handle a case where the sending node itself process its hop-by-hop
1131 * options header. In such a case, the function is called from ip6_output().
1132 *
1133 * The function assumes that hbh header is located right after the IPv6 header
1134 * (RFC2460 p7), opthead is pointer into data content in m, and opthead to
1135 * opthead + hbhlen is located in continuous memory region.
1136 */
1137 int
1138 ip6_process_hopopts(m, opthead, hbhlen, rtalertp, plenp)
1139 struct mbuf *m;
1140 u_int8_t *opthead;
1141 int hbhlen;
1142 u_int32_t *rtalertp;
1143 u_int32_t *plenp;
1144 {
1145 struct ip6_hdr *ip6;
1146 int optlen = 0;
1147 u_int8_t *opt = opthead;
1148 u_int16_t rtalert_val;
1149 u_int32_t jumboplen;
1150 const int erroff = sizeof(struct ip6_hdr) + sizeof(struct ip6_hbh);
1151
1152 for (; hbhlen > 0; hbhlen -= optlen, opt += optlen) {
1153 switch (*opt) {
1154 case IP6OPT_PAD1:
1155 optlen = 1;
1156 break;
1157 case IP6OPT_PADN:
1158 if (hbhlen < IP6OPT_MINLEN) {
1159 ip6stat.ip6s_toosmall++;
1160 goto bad;
1161 }
1162 optlen = *(opt + 1) + 2;
1163 break;
1164 case IP6OPT_RTALERT:
1165 /* XXX may need check for alignment */
1166 if (hbhlen < IP6OPT_RTALERT_LEN) {
1167 ip6stat.ip6s_toosmall++;
1168 goto bad;
1169 }
1170 if (*(opt + 1) != IP6OPT_RTALERT_LEN - 2) {
1171 /* XXX stat */
1172 lck_mtx_unlock(ip6_mutex);
1173 icmp6_error(m, ICMP6_PARAM_PROB,
1174 ICMP6_PARAMPROB_HEADER,
1175 erroff + opt + 1 - opthead);
1176 lck_mtx_lock(ip6_mutex);
1177 return(-1);
1178 }
1179 optlen = IP6OPT_RTALERT_LEN;
1180 bcopy((caddr_t)(opt + 2), (caddr_t)&rtalert_val, 2);
1181 *rtalertp = ntohs(rtalert_val);
1182 break;
1183 case IP6OPT_JUMBO:
1184 /* XXX may need check for alignment */
1185 if (hbhlen < IP6OPT_JUMBO_LEN) {
1186 ip6stat.ip6s_toosmall++;
1187 goto bad;
1188 }
1189 if (*(opt + 1) != IP6OPT_JUMBO_LEN - 2) {
1190 /* XXX stat */
1191 lck_mtx_unlock(ip6_mutex);
1192 icmp6_error(m, ICMP6_PARAM_PROB,
1193 ICMP6_PARAMPROB_HEADER,
1194 erroff + opt + 1 - opthead);
1195 lck_mtx_lock(ip6_mutex);
1196 return(-1);
1197 }
1198 optlen = IP6OPT_JUMBO_LEN;
1199
1200 /*
1201 * IPv6 packets that have non 0 payload length
1202 * must not contain a jumbo payload option.
1203 */
1204 ip6 = mtod(m, struct ip6_hdr *);
1205 if (ip6->ip6_plen) {
1206 ip6stat.ip6s_badoptions++;
1207 lck_mtx_unlock(ip6_mutex);
1208 icmp6_error(m, ICMP6_PARAM_PROB,
1209 ICMP6_PARAMPROB_HEADER,
1210 erroff + opt - opthead);
1211 lck_mtx_lock(ip6_mutex);
1212 return(-1);
1213 }
1214
1215 /*
1216 * We may see jumbolen in unaligned location, so
1217 * we'd need to perform bcopy().
1218 */
1219 bcopy(opt + 2, &jumboplen, sizeof(jumboplen));
1220 jumboplen = (u_int32_t)htonl(jumboplen);
1221
1222 #if 1
1223 /*
1224 * if there are multiple jumbo payload options,
1225 * *plenp will be non-zero and the packet will be
1226 * rejected.
1227 * the behavior may need some debate in ipngwg -
1228 * multiple options does not make sense, however,
1229 * there's no explicit mention in specification.
1230 */
1231 if (*plenp != 0) {
1232 ip6stat.ip6s_badoptions++;
1233 lck_mtx_unlock(ip6_mutex);
1234 icmp6_error(m, ICMP6_PARAM_PROB,
1235 ICMP6_PARAMPROB_HEADER,
1236 erroff + opt + 2 - opthead);
1237 lck_mtx_lock(ip6_mutex);
1238 return(-1);
1239 }
1240 #endif
1241
1242 /*
1243 * jumbo payload length must be larger than 65535.
1244 */
1245 if (jumboplen <= IPV6_MAXPACKET) {
1246 ip6stat.ip6s_badoptions++;
1247 lck_mtx_unlock(ip6_mutex);
1248 icmp6_error(m, ICMP6_PARAM_PROB,
1249 ICMP6_PARAMPROB_HEADER,
1250 erroff + opt + 2 - opthead);
1251 lck_mtx_lock(ip6_mutex);
1252 return(-1);
1253 }
1254 *plenp = jumboplen;
1255
1256 break;
1257 default: /* unknown option */
1258 if (hbhlen < IP6OPT_MINLEN) {
1259 ip6stat.ip6s_toosmall++;
1260 goto bad;
1261 }
1262 optlen = ip6_unknown_opt(opt, m,
1263 erroff + opt - opthead, 1);
1264 if (optlen == -1) {
1265 /* ip6_unknown opt unlocked ip6_mutex */
1266 return(-1);
1267 }
1268 optlen += 2;
1269 break;
1270 }
1271 }
1272
1273 return(0);
1274
1275 bad:
1276 m_freem(m);
1277 return(-1);
1278 }
1279
1280 /*
1281 * Unknown option processing.
1282 * The third argument `off' is the offset from the IPv6 header to the option,
1283 * which is necessary if the IPv6 header the and option header and IPv6 header
1284 * is not continuous in order to return an ICMPv6 error.
1285 */
1286 int
1287 ip6_unknown_opt(optp, m, off, locked)
1288 u_int8_t *optp;
1289 struct mbuf *m;
1290 int off;
1291 int locked;
1292 {
1293 struct ip6_hdr *ip6;
1294
1295 switch (IP6OPT_TYPE(*optp)) {
1296 case IP6OPT_TYPE_SKIP: /* ignore the option */
1297 return((int)*(optp + 1));
1298 case IP6OPT_TYPE_DISCARD: /* silently discard */
1299 m_freem(m);
1300 return(-1);
1301 case IP6OPT_TYPE_FORCEICMP: /* send ICMP even if multicasted */
1302 ip6stat.ip6s_badoptions++;
1303 if (locked)
1304 lck_mtx_unlock(ip6_mutex);
1305 icmp6_error(m, ICMP6_PARAM_PROB, ICMP6_PARAMPROB_OPTION, off);
1306 if (locked)
1307 lck_mtx_lock(ip6_mutex);
1308 return(-1);
1309 case IP6OPT_TYPE_ICMP: /* send ICMP if not multicasted */
1310 ip6stat.ip6s_badoptions++;
1311 ip6 = mtod(m, struct ip6_hdr *);
1312 if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst) ||
1313 (m->m_flags & (M_BCAST|M_MCAST)))
1314 m_freem(m);
1315 else {
1316 if (locked)
1317 lck_mtx_unlock(ip6_mutex);
1318 icmp6_error(m, ICMP6_PARAM_PROB,
1319 ICMP6_PARAMPROB_OPTION, off);
1320 if (locked)
1321 lck_mtx_lock(ip6_mutex);
1322 }
1323 return(-1);
1324 }
1325
1326 m_freem(m); /* XXX: NOTREACHED */
1327 return(-1);
1328 }
1329
1330 /*
1331 * Create the "control" list for this pcb.
1332 * The function will not modify mbuf chain at all.
1333 *
1334 * with KAME mbuf chain restriction:
1335 * The routine will be called from upper layer handlers like tcp6_input().
1336 * Thus the routine assumes that the caller (tcp6_input) have already
1337 * called IP6_EXTHDR_CHECK() and all the extension headers are located in the
1338 * very first mbuf on the mbuf chain.
1339 */
1340 void
1341 ip6_savecontrol(in6p, mp, ip6, m)
1342 struct inpcb *in6p;
1343 struct mbuf **mp;
1344 struct ip6_hdr *ip6;
1345 struct mbuf *m;
1346 {
1347 int rthdr_exist = 0;
1348
1349 #if SO_TIMESTAMP
1350 if ((in6p->in6p_socket->so_options & SO_TIMESTAMP) != 0) {
1351 struct timeval tv;
1352
1353 microtime(&tv);
1354 *mp = sbcreatecontrol((caddr_t) &tv, sizeof(tv),
1355 SCM_TIMESTAMP, SOL_SOCKET);
1356 if (*mp) {
1357 mp = &(*mp)->m_next;
1358 }
1359 }
1360 #endif
1361
1362 /* some OSes call this logic with IPv4 packet, for SO_TIMESTAMP */
1363 if ((ip6->ip6_vfc & IPV6_VERSION_MASK) != IPV6_VERSION)
1364 return;
1365
1366 /* RFC 2292 sec. 5 */
1367 if ((in6p->in6p_flags & IN6P_PKTINFO) != 0) {
1368 struct in6_pktinfo pi6;
1369 bcopy(&ip6->ip6_dst, &pi6.ipi6_addr, sizeof(struct in6_addr));
1370 if (IN6_IS_SCOPE_LINKLOCAL(&pi6.ipi6_addr))
1371 pi6.ipi6_addr.s6_addr16[1] = 0;
1372 pi6.ipi6_ifindex = (m && m->m_pkthdr.rcvif)
1373 ? m->m_pkthdr.rcvif->if_index
1374 : 0;
1375 *mp = sbcreatecontrol((caddr_t) &pi6,
1376 sizeof(struct in6_pktinfo), IPV6_PKTINFO,
1377 IPPROTO_IPV6);
1378 if (*mp)
1379 mp = &(*mp)->m_next;
1380 }
1381
1382 if ((in6p->in6p_flags & IN6P_HOPLIMIT) != 0) {
1383 int hlim = ip6->ip6_hlim & 0xff;
1384 *mp = sbcreatecontrol((caddr_t) &hlim,
1385 sizeof(int), IPV6_HOPLIMIT, IPPROTO_IPV6);
1386 if (*mp)
1387 mp = &(*mp)->m_next;
1388 }
1389
1390 if ((in6p->in6p_flags & IN6P_TCLASS) != 0) {
1391 u_int32_t flowinfo;
1392 int tclass;
1393
1394 flowinfo = (u_int32_t)ntohl(ip6->ip6_flow & IPV6_FLOWINFO_MASK);
1395 flowinfo >>= 20;
1396
1397 tclass = flowinfo & 0xff;
1398 *mp = sbcreatecontrol((caddr_t) &tclass, sizeof(tclass),
1399 IPV6_TCLASS, IPPROTO_IPV6);
1400 if (*mp)
1401 mp = &(*mp)->m_next;
1402 }
1403
1404 /*
1405 * IPV6_HOPOPTS socket option. Recall that we required super-user
1406 * privilege for the option (see ip6_ctloutput), but it might be too
1407 * strict, since there might be some hop-by-hop options which can be
1408 * returned to normal user.
1409 * See RFC 2292 section 6.
1410 */
1411 if ((in6p->in6p_flags & IN6P_HOPOPTS) != 0) {
1412 /*
1413 * Check if a hop-by-hop options header is contatined in the
1414 * received packet, and if so, store the options as ancillary
1415 * data. Note that a hop-by-hop options header must be
1416 * just after the IPv6 header, which fact is assured through
1417 * the IPv6 input processing.
1418 */
1419 ip6 = mtod(m, struct ip6_hdr *);
1420 if (ip6->ip6_nxt == IPPROTO_HOPOPTS) {
1421 struct ip6_hbh *hbh;
1422 int hbhlen = 0;
1423 #if PULLDOWN_TEST
1424 struct mbuf *ext;
1425 #endif
1426
1427 #ifndef PULLDOWN_TEST
1428 hbh = (struct ip6_hbh *)(ip6 + 1);
1429 hbhlen = (hbh->ip6h_len + 1) << 3;
1430 #else
1431 ext = ip6_pullexthdr(m, sizeof(struct ip6_hdr),
1432 ip6->ip6_nxt);
1433 if (ext == NULL) {
1434 ip6stat.ip6s_tooshort++;
1435 return;
1436 }
1437 hbh = mtod(ext, struct ip6_hbh *);
1438 hbhlen = (hbh->ip6h_len + 1) << 3;
1439 if (hbhlen != ext->m_len) {
1440 m_freem(ext);
1441 ip6stat.ip6s_tooshort++;
1442 return;
1443 }
1444 #endif
1445
1446 /*
1447 * XXX: We copy whole the header even if a jumbo
1448 * payload option is included, which option is to
1449 * be removed before returning in the RFC 2292.
1450 * Note: this constraint is removed in 2292bis.
1451 */
1452 *mp = sbcreatecontrol((caddr_t)hbh, hbhlen,
1453 IPV6_HOPOPTS, IPPROTO_IPV6);
1454 if (*mp)
1455 mp = &(*mp)->m_next;
1456 #if PULLDOWN_TEST
1457 m_freem(ext);
1458 #endif
1459 }
1460 }
1461
1462 /* IPV6_DSTOPTS and IPV6_RTHDR socket options */
1463 if ((in6p->in6p_flags & (IN6P_DSTOPTS | IN6P_RTHDRDSTOPTS)) != 0) {
1464 int proto, off, nxt;
1465
1466 /*
1467 * go through the header chain to see if a routing header is
1468 * contained in the packet. We need this information to store
1469 * destination options headers (if any) properly.
1470 * XXX: performance issue. We should record this info when
1471 * processing extension headers in incoming routine.
1472 * (todo) use m_aux?
1473 */
1474 proto = IPPROTO_IPV6;
1475 off = 0;
1476 nxt = -1;
1477 while (1) {
1478 int newoff;
1479
1480 newoff = ip6_nexthdr(m, off, proto, &nxt);
1481 if (newoff < 0)
1482 break;
1483 if (newoff < off) /* invalid, check for safety */
1484 break;
1485 if ((proto = nxt) == IPPROTO_ROUTING) {
1486 rthdr_exist = 1;
1487 break;
1488 }
1489 off = newoff;
1490 }
1491 }
1492
1493 if ((in6p->in6p_flags &
1494 (IN6P_RTHDR | IN6P_DSTOPTS | IN6P_RTHDRDSTOPTS)) != 0) {
1495 ip6 = mtod(m, struct ip6_hdr *);
1496 int nxt = ip6->ip6_nxt, off = sizeof(struct ip6_hdr);
1497
1498 /*
1499 * Search for destination options headers or routing
1500 * header(s) through the header chain, and stores each
1501 * header as ancillary data.
1502 * Note that the order of the headers remains in
1503 * the chain of ancillary data.
1504 */
1505 while (1) { /* is explicit loop prevention necessary? */
1506 struct ip6_ext *ip6e = NULL;
1507 int elen;
1508 #if PULLDOWN_TEST
1509 struct mbuf *ext = NULL;
1510 #endif
1511
1512 /*
1513 * if it is not an extension header, don't try to
1514 * pull it from the chain.
1515 */
1516 switch (nxt) {
1517 case IPPROTO_DSTOPTS:
1518 case IPPROTO_ROUTING:
1519 case IPPROTO_HOPOPTS:
1520 case IPPROTO_AH: /* is it possible? */
1521 break;
1522 default:
1523 goto loopend;
1524 }
1525
1526 #ifndef PULLDOWN_TEST
1527 if (off + sizeof(*ip6e) > m->m_len)
1528 goto loopend;
1529 ip6e = (struct ip6_ext *)(mtod(m, caddr_t) + off);
1530 if (nxt == IPPROTO_AH)
1531 elen = (ip6e->ip6e_len + 2) << 2;
1532 else
1533 elen = (ip6e->ip6e_len + 1) << 3;
1534 if (off + elen > m->m_len)
1535 goto loopend;
1536 #else
1537 ext = ip6_pullexthdr(m, off, nxt);
1538 if (ext == NULL) {
1539 ip6stat.ip6s_tooshort++;
1540 return;
1541 }
1542 ip6e = mtod(ext, struct ip6_ext *);
1543 if (nxt == IPPROTO_AH)
1544 elen = (ip6e->ip6e_len + 2) << 2;
1545 else
1546 elen = (ip6e->ip6e_len + 1) << 3;
1547 if (elen != ext->m_len) {
1548 m_freem(ext);
1549 ip6stat.ip6s_tooshort++;
1550 return;
1551 }
1552 #endif
1553
1554 switch (nxt) {
1555 case IPPROTO_DSTOPTS:
1556 if ((in6p->in6p_flags & IN6P_DSTOPTS) == 0)
1557 break;
1558
1559 *mp = sbcreatecontrol((caddr_t)ip6e, elen,
1560 IPV6_DSTOPTS,
1561 IPPROTO_IPV6);
1562 if (*mp)
1563 mp = &(*mp)->m_next;
1564 break;
1565 case IPPROTO_ROUTING:
1566 if (!in6p->in6p_flags & IN6P_RTHDR)
1567 break;
1568
1569 *mp = sbcreatecontrol((caddr_t)ip6e, elen,
1570 IPV6_RTHDR,
1571 IPPROTO_IPV6);
1572 if (*mp)
1573 mp = &(*mp)->m_next;
1574 break;
1575 case IPPROTO_HOPOPTS:
1576 case IPPROTO_AH: /* is it possible? */
1577 break;
1578
1579 default:
1580 /*
1581 * other cases have been filtered in the above.
1582 * none will visit this case. here we supply
1583 * the code just in case (nxt overwritten or
1584 * other cases).
1585 */
1586 #if PULLDOWN_TEST
1587 m_freem(ext);
1588 #endif
1589 goto loopend;
1590
1591 }
1592
1593 /* proceed with the next header. */
1594 off += elen;
1595 nxt = ip6e->ip6e_nxt;
1596 ip6e = NULL;
1597 #if PULLDOWN_TEST
1598 m_freem(ext);
1599 ext = NULL;
1600 #endif
1601 }
1602 loopend:
1603 ;
1604 }
1605
1606 }
1607
1608 #if PULLDOWN_TEST
1609 /*
1610 * pull single extension header from mbuf chain. returns single mbuf that
1611 * contains the result, or NULL on error.
1612 */
1613 static struct mbuf *
1614 ip6_pullexthdr(m, off, nxt)
1615 struct mbuf *m;
1616 size_t off;
1617 int nxt;
1618 {
1619 struct ip6_ext ip6e;
1620 size_t elen;
1621 struct mbuf *n;
1622
1623 #if DIAGNOSTIC
1624 switch (nxt) {
1625 case IPPROTO_DSTOPTS:
1626 case IPPROTO_ROUTING:
1627 case IPPROTO_HOPOPTS:
1628 case IPPROTO_AH: /* is it possible? */
1629 break;
1630 default:
1631 printf("ip6_pullexthdr: invalid nxt=%d\n", nxt);
1632 }
1633 #endif
1634
1635 m_copydata(m, off, sizeof(ip6e), (caddr_t)&ip6e);
1636 if (nxt == IPPROTO_AH)
1637 elen = (ip6e.ip6e_len + 2) << 2;
1638 else
1639 elen = (ip6e.ip6e_len + 1) << 3;
1640
1641 MGET(n, M_DONTWAIT, MT_DATA);
1642 if (n && elen >= MLEN) {
1643 MCLGET(n, M_DONTWAIT);
1644 if ((n->m_flags & M_EXT) == 0) {
1645 m_free(n);
1646 n = NULL;
1647 }
1648 }
1649 if (!n)
1650 return NULL;
1651
1652 n->m_len = 0;
1653 if (elen >= M_TRAILINGSPACE(n)) {
1654 m_free(n);
1655 return NULL;
1656 }
1657
1658 m_copydata(m, off, elen, mtod(n, caddr_t));
1659 n->m_len = elen;
1660 return n;
1661 }
1662 #endif
1663
1664 /*
1665 * Get pointer to the previous header followed by the header
1666 * currently processed.
1667 * XXX: This function supposes that
1668 * M includes all headers,
1669 * the next header field and the header length field of each header
1670 * are valid, and
1671 * the sum of each header length equals to OFF.
1672 * Because of these assumptions, this function must be called very
1673 * carefully. Moreover, it will not be used in the near future when
1674 * we develop `neater' mechanism to process extension headers.
1675 */
1676 char *
1677 ip6_get_prevhdr(m, off)
1678 struct mbuf *m;
1679 int off;
1680 {
1681 struct ip6_hdr *ip6 = mtod(m, struct ip6_hdr *);
1682
1683 if (off == sizeof(struct ip6_hdr))
1684 return((char *) &ip6->ip6_nxt);
1685 else {
1686 int len, nxt;
1687 struct ip6_ext *ip6e = NULL;
1688
1689 nxt = ip6->ip6_nxt;
1690 len = sizeof(struct ip6_hdr);
1691 while (len < off) {
1692 ip6e = (struct ip6_ext *)(mtod(m, caddr_t) + len);
1693
1694 switch (nxt) {
1695 case IPPROTO_FRAGMENT:
1696 len += sizeof(struct ip6_frag);
1697 break;
1698 case IPPROTO_AH:
1699 len += (ip6e->ip6e_len + 2) << 2;
1700 break;
1701 default:
1702 len += (ip6e->ip6e_len + 1) << 3;
1703 break;
1704 }
1705 nxt = ip6e->ip6e_nxt;
1706 }
1707 if (ip6e)
1708 return((char *) &ip6e->ip6e_nxt);
1709 else
1710 return NULL;
1711 }
1712 }
1713
1714 /*
1715 * get next header offset. m will be retained.
1716 */
1717 int
1718 ip6_nexthdr(m, off, proto, nxtp)
1719 struct mbuf *m;
1720 int off;
1721 int proto;
1722 int *nxtp;
1723 {
1724 struct ip6_hdr ip6;
1725 struct ip6_ext ip6e;
1726 struct ip6_frag fh;
1727
1728 /* just in case */
1729 if (m == NULL)
1730 panic("ip6_nexthdr: m == NULL");
1731 if ((m->m_flags & M_PKTHDR) == 0 || m->m_pkthdr.len < off)
1732 return -1;
1733
1734 switch (proto) {
1735 case IPPROTO_IPV6:
1736 if (m->m_pkthdr.len < off + sizeof(ip6))
1737 return -1;
1738 m_copydata(m, off, sizeof(ip6), (caddr_t)&ip6);
1739 if (nxtp)
1740 *nxtp = ip6.ip6_nxt;
1741 off += sizeof(ip6);
1742 return off;
1743
1744 case IPPROTO_FRAGMENT:
1745 /*
1746 * terminate parsing if it is not the first fragment,
1747 * it does not make sense to parse through it.
1748 */
1749 if (m->m_pkthdr.len < off + sizeof(fh))
1750 return -1;
1751 m_copydata(m, off, sizeof(fh), (caddr_t)&fh);
1752 /* IP6F_OFF_MASK = 0xfff8(BigEndian), 0xf8ff(LittleEndian) */
1753 if (fh.ip6f_offlg & IP6F_OFF_MASK)
1754 return -1;
1755 if (nxtp)
1756 *nxtp = fh.ip6f_nxt;
1757 off += sizeof(struct ip6_frag);
1758 return off;
1759
1760 case IPPROTO_AH:
1761 if (m->m_pkthdr.len < off + sizeof(ip6e))
1762 return -1;
1763 m_copydata(m, off, sizeof(ip6e), (caddr_t)&ip6e);
1764 if (nxtp)
1765 *nxtp = ip6e.ip6e_nxt;
1766 off += (ip6e.ip6e_len + 2) << 2;
1767 return off;
1768
1769 case IPPROTO_HOPOPTS:
1770 case IPPROTO_ROUTING:
1771 case IPPROTO_DSTOPTS:
1772 if (m->m_pkthdr.len < off + sizeof(ip6e))
1773 return -1;
1774 m_copydata(m, off, sizeof(ip6e), (caddr_t)&ip6e);
1775 if (nxtp)
1776 *nxtp = ip6e.ip6e_nxt;
1777 off += (ip6e.ip6e_len + 1) << 3;
1778 return off;
1779
1780 case IPPROTO_NONE:
1781 case IPPROTO_ESP:
1782 case IPPROTO_IPCOMP:
1783 /* give up */
1784 return -1;
1785
1786 default:
1787 return -1;
1788 }
1789
1790 return -1;
1791 }
1792
1793 /*
1794 * get offset for the last header in the chain. m will be kept untainted.
1795 */
1796 int
1797 ip6_lasthdr(m, off, proto, nxtp)
1798 struct mbuf *m;
1799 int off;
1800 int proto;
1801 int *nxtp;
1802 {
1803 int newoff;
1804 int nxt;
1805
1806 if (!nxtp) {
1807 nxt = -1;
1808 nxtp = &nxt;
1809 }
1810 while (1) {
1811 newoff = ip6_nexthdr(m, off, proto, nxtp);
1812 if (newoff < 0)
1813 return off;
1814 else if (newoff < off)
1815 return -1; /* invalid */
1816 else if (newoff == off)
1817 return newoff;
1818
1819 off = newoff;
1820 proto = *nxtp;
1821 }
1822 }
1823
1824 struct ip6aux *
1825 ip6_addaux(
1826 struct mbuf *m)
1827 {
1828 struct m_tag *tag;
1829
1830 /* Check if one is already allocated */
1831 tag = m_tag_locate(m, KERNEL_MODULE_TAG_ID, KERNEL_TAG_TYPE_INET6, NULL);
1832 if (tag == NULL) {
1833 /* Allocate a tag */
1834 tag = m_tag_alloc(KERNEL_MODULE_TAG_ID, KERNEL_TAG_TYPE_INET6,
1835 sizeof (struct ip6aux), M_DONTWAIT);
1836
1837 /* Attach it to the mbuf */
1838 if (tag) {
1839 m_tag_prepend(m, tag);
1840 }
1841 }
1842
1843 return tag ? (struct ip6aux*)(tag + 1) : NULL;
1844 }
1845
1846 struct ip6aux *
1847 ip6_findaux(
1848 struct mbuf *m)
1849 {
1850 struct m_tag *tag;
1851
1852 tag = m_tag_locate(m, KERNEL_MODULE_TAG_ID, KERNEL_TAG_TYPE_ENCAP, NULL);
1853
1854 return tag ? (struct ip6aux*)(tag + 1) : NULL;
1855 }
1856
1857 void
1858 ip6_delaux(
1859 struct mbuf *m)
1860 {
1861 struct m_tag *tag;
1862
1863 tag = m_tag_locate(m, KERNEL_MODULE_TAG_ID, KERNEL_TAG_TYPE_ENCAP, NULL);
1864 if (tag) {
1865 m_tag_delete(m, tag);
1866 }
1867 }
1868
1869 /*
1870 * System control for IP6
1871 */
1872
1873 u_char inet6ctlerrmap[PRC_NCMDS] = {
1874 0, 0, 0, 0,
1875 0, EMSGSIZE, EHOSTDOWN, EHOSTUNREACH,
1876 EHOSTUNREACH, EHOSTUNREACH, ECONNREFUSED, ECONNREFUSED,
1877 EMSGSIZE, EHOSTUNREACH, 0, 0,
1878 0, 0, 0, 0,
1879 ENOPROTOOPT
1880 };