/dev/random was almost always returning 0 bytes. This was due to several
[dragonfly.git] / sys / netinet6 / ip6_output.c
1 /*      $FreeBSD: src/sys/netinet6/ip6_output.c,v 1.13.2.18 2003/01/24 05:11:35 sam Exp $       */
2 /*      $DragonFly: src/sys/netinet6/ip6_output.c,v 1.19 2006/01/14 11:44:25 swildner Exp $     */
3 /*      $KAME: ip6_output.c,v 1.279 2002/01/26 06:12:30 jinmei Exp $    */
4
5 /*
6  * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
7  * All rights reserved.
8  *
9  * Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  * 1. Redistributions of source code must retain the above copyright
13  *    notice, this list of conditions and the following disclaimer.
14  * 2. Redistributions in binary form must reproduce the above copyright
15  *    notice, this list of conditions and the following disclaimer in the
16  *    documentation and/or other materials provided with the distribution.
17  * 3. Neither the name of the project nor the names of its contributors
18  *    may be used to endorse or promote products derived from this software
19  *    without specific prior written permission.
20  *
21  * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
22  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
24  * ARE DISCLAIMED.  IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
25  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
26  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
27  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
28  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
30  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  */
33
34 /*
35  * Copyright (c) 1982, 1986, 1988, 1990, 1993
36  *      The Regents of the University of California.  All rights reserved.
37  *
38  * Redistribution and use in source and binary forms, with or without
39  * modification, are permitted provided that the following conditions
40  * are met:
41  * 1. Redistributions of source code must retain the above copyright
42  *    notice, this list of conditions and the following disclaimer.
43  * 2. Redistributions in binary form must reproduce the above copyright
44  *    notice, this list of conditions and the following disclaimer in the
45  *    documentation and/or other materials provided with the distribution.
46  * 3. All advertising materials mentioning features or use of this software
47  *    must display the following acknowledgement:
48  *      This product includes software developed by the University of
49  *      California, Berkeley and its contributors.
50  * 4. Neither the name of the University nor the names of its contributors
51  *    may be used to endorse or promote products derived from this software
52  *    without specific prior written permission.
53  *
54  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
55  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
56  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
57  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
58  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
59  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
60  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
61  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
62  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
63  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
64  * SUCH DAMAGE.
65  *
66  *      @(#)ip_output.c 8.3 (Berkeley) 1/21/94
67  */
68
69 #include "opt_ip6fw.h"
70 #include "opt_inet.h"
71 #include "opt_inet6.h"
72 #include "opt_ipsec.h"
73
74 #include <sys/param.h>
75 #include <sys/malloc.h>
76 #include <sys/mbuf.h>
77 #include <sys/errno.h>
78 #include <sys/protosw.h>
79 #include <sys/socket.h>
80 #include <sys/socketvar.h>
81 #include <sys/systm.h>
82 #include <sys/kernel.h>
83 #include <sys/proc.h>
84
85 #include <net/if.h>
86 #include <net/route.h>
87 #include <net/pfil.h>
88
89 #include <netinet/in.h>
90 #include <netinet/in_var.h>
91 #include <netinet6/in6_var.h>
92 #include <netinet/ip6.h>
93 #include <netinet/icmp6.h>
94 #include <netinet6/ip6_var.h>
95 #include <netinet/in_pcb.h>
96 #include <netinet6/nd6.h>
97
98 #ifdef IPSEC
99 #include <netinet6/ipsec.h>
100 #ifdef INET6
101 #include <netinet6/ipsec6.h>
102 #endif
103 #include <netproto/key/key.h>
104 #endif /* IPSEC */
105
106 #ifdef FAST_IPSEC
107 #include <netproto/ipsec/ipsec.h>
108 #include <netproto/ipsec/ipsec6.h>
109 #include <netproto/ipsec/key.h>
110 #endif /* FAST_IPSEC */
111
112 #include <net/ip6fw/ip6_fw.h>
113
114 #include <net/net_osdep.h>
115
116 static MALLOC_DEFINE(M_IPMOPTS, "ip6_moptions", "internet multicast options");
117
118 struct ip6_exthdrs {
119         struct mbuf *ip6e_ip6;
120         struct mbuf *ip6e_hbh;
121         struct mbuf *ip6e_dest1;
122         struct mbuf *ip6e_rthdr;
123         struct mbuf *ip6e_dest2;
124 };
125
126 static int ip6_pcbopts (struct ip6_pktopts **, struct mbuf *,
127                             struct socket *, struct sockopt *sopt);
128 static int ip6_setmoptions (int, struct ip6_moptions **, struct mbuf *);
129 static int ip6_getmoptions (int, struct ip6_moptions *, struct mbuf **);
130 static int ip6_copyexthdr (struct mbuf **, caddr_t, int);
131 static int ip6_insertfraghdr (struct mbuf *, struct mbuf *, int,
132                                   struct ip6_frag **);
133 static int ip6_insert_jumboopt (struct ip6_exthdrs *, u_int32_t);
134 static int ip6_splithdr (struct mbuf *, struct ip6_exthdrs *);
135
136 /*
137  * IP6 output. The packet in mbuf chain m contains a skeletal IP6
138  * header (with pri, len, nxt, hlim, src, dst).
139  * This function may modify ver and hlim only.
140  * The mbuf chain containing the packet will be freed.
141  * The mbuf opt, if present, will not be freed.
142  *
143  * type of "mtu": rt_rmx.rmx_mtu is u_long, ifnet.ifr_mtu is int, and
144  * nd_ifinfo.linkmtu is u_int32_t.  so we use u_long to hold largest one,
145  * which is rt_rmx.rmx_mtu.
146  */
147 int
148 ip6_output(struct mbuf *m0, struct ip6_pktopts *opt, struct route_in6 *ro,
149            int flags, struct ip6_moptions *im6o,
150            struct ifnet **ifpp,         /* XXX: just for statistics */
151            struct inpcb *inp)
152 {
153         struct ip6_hdr *ip6, *mhip6;
154         struct ifnet *ifp, *origifp;
155         struct mbuf *m = m0;
156         int hlen, tlen, len, off;
157         struct route_in6 ip6route;
158         struct sockaddr_in6 *dst;
159         int error = 0;
160         struct in6_ifaddr *ia = NULL;
161         u_long mtu;
162         u_int32_t optlen = 0, plen = 0, unfragpartlen = 0;
163         struct ip6_exthdrs exthdrs;
164         struct in6_addr finaldst;
165         struct route_in6 *ro_pmtu = NULL;
166         int hdrsplit = 0;
167         int needipsec = 0;
168 #ifdef IPSEC
169         int needipsectun = 0;
170         struct secpolicy *sp = NULL;
171         struct socket *so = inp ? inp->inp_socket : NULL;
172
173         ip6 = mtod(m, struct ip6_hdr *);
174 #endif /* IPSEC */
175 #ifdef FAST_IPSEC
176         int needipsectun = 0;
177         struct secpolicy *sp = NULL;
178
179         ip6 = mtod(m, struct ip6_hdr *);
180 #endif /* FAST_IPSEC */
181
182 #define MAKE_EXTHDR(hp, mp)                                             \
183     do {                                                                \
184         if (hp) {                                                       \
185                 struct ip6_ext *eh = (struct ip6_ext *)(hp);            \
186                 error = ip6_copyexthdr((mp), (caddr_t)(hp),             \
187                                        ((eh)->ip6e_len + 1) << 3);      \
188                 if (error)                                              \
189                         goto freehdrs;                                  \
190         }                                                               \
191     } while (0)
192         
193         bzero(&exthdrs, sizeof(exthdrs));
194         
195         if (opt) {
196                 /* Hop-by-Hop options header */
197                 MAKE_EXTHDR(opt->ip6po_hbh, &exthdrs.ip6e_hbh);
198                 /* Destination options header(1st part) */
199                 MAKE_EXTHDR(opt->ip6po_dest1, &exthdrs.ip6e_dest1);
200                 /* Routing header */
201                 MAKE_EXTHDR(opt->ip6po_rthdr, &exthdrs.ip6e_rthdr);
202                 /* Destination options header(2nd part) */
203                 MAKE_EXTHDR(opt->ip6po_dest2, &exthdrs.ip6e_dest2);
204         }
205
206 #ifdef IPSEC
207         /* get a security policy for this packet */
208         if (so == NULL)
209                 sp = ipsec6_getpolicybyaddr(m, IPSEC_DIR_OUTBOUND, 0, &error);
210         else
211                 sp = ipsec6_getpolicybysock(m, IPSEC_DIR_OUTBOUND, so, &error);
212
213         if (sp == NULL) {
214                 ipsec6stat.out_inval++;
215                 goto freehdrs;
216         }
217
218         error = 0;
219
220         /* check policy */
221         switch (sp->policy) {
222         case IPSEC_POLICY_DISCARD:
223                 /*
224                  * This packet is just discarded.
225                  */
226                 ipsec6stat.out_polvio++;
227                 goto freehdrs;
228
229         case IPSEC_POLICY_BYPASS:
230         case IPSEC_POLICY_NONE:
231                 /* no need to do IPsec. */
232                 needipsec = 0;
233                 break;
234         
235         case IPSEC_POLICY_IPSEC:
236                 if (sp->req == NULL) {
237                         /* acquire a policy */
238                         error = key_spdacquire(sp);
239                         goto freehdrs;
240                 }
241                 needipsec = 1;
242                 break;
243
244         case IPSEC_POLICY_ENTRUST:
245         default:
246                 printf("ip6_output: Invalid policy found. %d\n", sp->policy);
247         }
248 #endif /* IPSEC */
249 #ifdef FAST_IPSEC
250         /* get a security policy for this packet */
251         if (inp == NULL)
252                 sp = ipsec_getpolicybyaddr(m, IPSEC_DIR_OUTBOUND, 0, &error);
253         else
254                 sp = ipsec_getpolicybysock(m, IPSEC_DIR_OUTBOUND, inp, &error);
255
256         if (sp == NULL) {
257                 newipsecstat.ips_out_inval++;
258                 goto freehdrs;
259         }
260
261         error = 0;
262
263         /* check policy */
264         switch (sp->policy) {
265         case IPSEC_POLICY_DISCARD:
266                 /*
267                  * This packet is just discarded.
268                  */
269                 newipsecstat.ips_out_polvio++;
270                 goto freehdrs;
271
272         case IPSEC_POLICY_BYPASS:
273         case IPSEC_POLICY_NONE:
274                 /* no need to do IPsec. */
275                 needipsec = 0;
276                 break;
277         
278         case IPSEC_POLICY_IPSEC:
279                 if (sp->req == NULL) {
280                         /* acquire a policy */
281                         error = key_spdacquire(sp);
282                         goto freehdrs;
283                 }
284                 needipsec = 1;
285                 break;
286
287         case IPSEC_POLICY_ENTRUST:
288         default:
289                 printf("ip6_output: Invalid policy found. %d\n", sp->policy);
290         }
291 #endif /* FAST_IPSEC */
292
293         /*
294          * Calculate the total length of the extension header chain.
295          * Keep the length of the unfragmentable part for fragmentation.
296          */
297         optlen = 0;
298         if (exthdrs.ip6e_hbh) optlen += exthdrs.ip6e_hbh->m_len;
299         if (exthdrs.ip6e_dest1) optlen += exthdrs.ip6e_dest1->m_len;
300         if (exthdrs.ip6e_rthdr) optlen += exthdrs.ip6e_rthdr->m_len;
301         unfragpartlen = optlen + sizeof(struct ip6_hdr);
302         /* NOTE: we don't add AH/ESP length here. do that later. */
303         if (exthdrs.ip6e_dest2) optlen += exthdrs.ip6e_dest2->m_len;
304
305         /*
306          * If we need IPsec, or there is at least one extension header,
307          * separate IP6 header from the payload.
308          */
309         if ((needipsec || optlen) && !hdrsplit) {
310                 if ((error = ip6_splithdr(m, &exthdrs)) != 0) {
311                         m = NULL;
312                         goto freehdrs;
313                 }
314                 m = exthdrs.ip6e_ip6;
315                 hdrsplit++;
316         }
317
318         /* adjust pointer */
319         ip6 = mtod(m, struct ip6_hdr *);
320
321         /* adjust mbuf packet header length */
322         m->m_pkthdr.len += optlen;
323         plen = m->m_pkthdr.len - sizeof(*ip6);
324
325         /* If this is a jumbo payload, insert a jumbo payload option. */
326         if (plen > IPV6_MAXPACKET) {
327                 if (!hdrsplit) {
328                         if ((error = ip6_splithdr(m, &exthdrs)) != 0) {
329                                 m = NULL;
330                                 goto freehdrs;
331                         }
332                         m = exthdrs.ip6e_ip6;
333                         hdrsplit++;
334                 }
335                 /* adjust pointer */
336                 ip6 = mtod(m, struct ip6_hdr *);
337                 if ((error = ip6_insert_jumboopt(&exthdrs, plen)) != 0)
338                         goto freehdrs;
339                 ip6->ip6_plen = 0;
340         } else
341                 ip6->ip6_plen = htons(plen);
342
343         /*
344          * Concatenate headers and fill in next header fields.
345          * Here we have, on "m"
346          *      IPv6 payload
347          * and we insert headers accordingly.  Finally, we should be getting:
348          *      IPv6 hbh dest1 rthdr ah* [esp* dest2 payload]
349          *
350          * during the header composing process, "m" points to IPv6 header.
351          * "mprev" points to an extension header prior to esp.
352          */
353         {
354                 u_char *nexthdrp = &ip6->ip6_nxt;
355                 struct mbuf *mprev = m;
356
357                 /*
358                  * we treat dest2 specially.  this makes IPsec processing
359                  * much easier.  the goal here is to make mprev point the
360                  * mbuf prior to dest2.
361                  *
362                  * result: IPv6 dest2 payload
363                  * m and mprev will point to IPv6 header.
364                  */
365                 if (exthdrs.ip6e_dest2) {
366                         if (!hdrsplit)
367                                 panic("assumption failed: hdr not split");
368                         exthdrs.ip6e_dest2->m_next = m->m_next;
369                         m->m_next = exthdrs.ip6e_dest2;
370                         *mtod(exthdrs.ip6e_dest2, u_char *) = ip6->ip6_nxt;
371                         ip6->ip6_nxt = IPPROTO_DSTOPTS;
372                 }
373
374 #define MAKE_CHAIN(m, mp, p, i)\
375     do {\
376         if (m) {\
377                 if (!hdrsplit) \
378                         panic("assumption failed: hdr not split"); \
379                 *mtod((m), u_char *) = *(p);\
380                 *(p) = (i);\
381                 p = mtod((m), u_char *);\
382                 (m)->m_next = (mp)->m_next;\
383                 (mp)->m_next = (m);\
384                 (mp) = (m);\
385         }\
386     } while (0)
387                 /*
388                  * result: IPv6 hbh dest1 rthdr dest2 payload
389                  * m will point to IPv6 header.  mprev will point to the
390                  * extension header prior to dest2 (rthdr in the above case).
391                  */
392                 MAKE_CHAIN(exthdrs.ip6e_hbh, mprev,
393                            nexthdrp, IPPROTO_HOPOPTS);
394                 MAKE_CHAIN(exthdrs.ip6e_dest1, mprev,
395                            nexthdrp, IPPROTO_DSTOPTS);
396                 MAKE_CHAIN(exthdrs.ip6e_rthdr, mprev,
397                            nexthdrp, IPPROTO_ROUTING);
398
399 #if defined(IPSEC) || defined(FAST_IPSEC)
400                 if (!needipsec)
401                         goto skip_ipsec2;
402
403                 /*
404                  * pointers after IPsec headers are not valid any more.
405                  * other pointers need a great care too.
406                  * (IPsec routines should not mangle mbufs prior to AH/ESP)
407                  */
408                 exthdrs.ip6e_dest2 = NULL;
409
410             {
411                 struct ip6_rthdr *rh = NULL;
412                 int segleft_org = 0;
413                 struct ipsec_output_state state;
414
415                 if (exthdrs.ip6e_rthdr) {
416                         rh = mtod(exthdrs.ip6e_rthdr, struct ip6_rthdr *);
417                         segleft_org = rh->ip6r_segleft;
418                         rh->ip6r_segleft = 0;
419                 }
420
421                 bzero(&state, sizeof(state));
422                 state.m = m;
423                 error = ipsec6_output_trans(&state, nexthdrp, mprev, sp, flags,
424                         &needipsectun);
425                 m = state.m;
426                 if (error) {
427                         /* mbuf is already reclaimed in ipsec6_output_trans. */
428                         m = NULL;
429                         switch (error) {
430                         case EHOSTUNREACH:
431                         case ENETUNREACH:
432                         case EMSGSIZE:
433                         case ENOBUFS:
434                         case ENOMEM:
435                                 break;
436                         default:
437                                 printf("ip6_output (ipsec): error code %d\n", error);
438                                 /* fall through */
439                         case ENOENT:
440                                 /* don't show these error codes to the user */
441                                 error = 0;
442                                 break;
443                         }
444                         goto bad;
445                 }
446                 if (exthdrs.ip6e_rthdr) {
447                         /* ah6_output doesn't modify mbuf chain */
448                         rh->ip6r_segleft = segleft_org;
449                 }
450             }
451 skip_ipsec2:;
452 #endif
453         }
454
455         /*
456          * If there is a routing header, replace destination address field
457          * with the first hop of the routing header.
458          */
459         if (exthdrs.ip6e_rthdr) {
460                 struct ip6_rthdr *rh =
461                         (struct ip6_rthdr *)(mtod(exthdrs.ip6e_rthdr,
462                                                   struct ip6_rthdr *));
463                 struct ip6_rthdr0 *rh0;
464
465                 finaldst = ip6->ip6_dst;
466                 switch (rh->ip6r_type) {
467                 case IPV6_RTHDR_TYPE_0:
468                          rh0 = (struct ip6_rthdr0 *)rh;
469                          ip6->ip6_dst = rh0->ip6r0_addr[0];
470                          bcopy((caddr_t)&rh0->ip6r0_addr[1],
471                                (caddr_t)&rh0->ip6r0_addr[0],
472                                sizeof(struct in6_addr)*(rh0->ip6r0_segleft - 1)
473                                  );
474                          rh0->ip6r0_addr[rh0->ip6r0_segleft - 1] = finaldst;
475                          break;
476                 default:        /* is it possible? */
477                          error = EINVAL;
478                          goto bad;
479                 }
480         }
481
482         /* Source address validation */
483         if (IN6_IS_ADDR_UNSPECIFIED(&ip6->ip6_src) &&
484             (flags & IPV6_DADOUTPUT) == 0) {
485                 error = EOPNOTSUPP;
486                 ip6stat.ip6s_badscope++;
487                 goto bad;
488         }
489         if (IN6_IS_ADDR_MULTICAST(&ip6->ip6_src)) {
490                 error = EOPNOTSUPP;
491                 ip6stat.ip6s_badscope++;
492                 goto bad;
493         }
494
495         ip6stat.ip6s_localout++;
496
497         /*
498          * Route packet.
499          */
500         if (ro == 0) {
501                 ro = &ip6route;
502                 bzero((caddr_t)ro, sizeof(*ro));
503         }
504         ro_pmtu = ro;
505         if (opt && opt->ip6po_rthdr)
506                 ro = &opt->ip6po_route;
507         dst = (struct sockaddr_in6 *)&ro->ro_dst;
508         /*
509          * If there is a cached route,
510          * check that it is to the same destination
511          * and is still up. If not, free it and try again.
512          */
513         if (ro->ro_rt && ((ro->ro_rt->rt_flags & RTF_UP) == 0 ||
514                          dst->sin6_family != AF_INET6 ||
515                          !IN6_ARE_ADDR_EQUAL(&dst->sin6_addr, &ip6->ip6_dst))) {
516                 RTFREE(ro->ro_rt);
517                 ro->ro_rt = (struct rtentry *)0;
518         }
519         if (ro->ro_rt == 0) {
520                 bzero(dst, sizeof(*dst));
521                 dst->sin6_family = AF_INET6;
522                 dst->sin6_len = sizeof(struct sockaddr_in6);
523                 dst->sin6_addr = ip6->ip6_dst;
524         }
525 #if defined(IPSEC) || defined(FAST_IPSEC)
526         if (needipsec && needipsectun) {
527                 struct ipsec_output_state state;
528
529                 /*
530                  * All the extension headers will become inaccessible
531                  * (since they can be encrypted).
532                  * Don't panic, we need no more updates to extension headers
533                  * on inner IPv6 packet (since they are now encapsulated).
534                  *
535                  * IPv6 [ESP|AH] IPv6 [extension headers] payload
536                  */
537                 bzero(&exthdrs, sizeof(exthdrs));
538                 exthdrs.ip6e_ip6 = m;
539
540                 bzero(&state, sizeof(state));
541                 state.m = m;
542                 state.ro = (struct route *)ro;
543                 state.dst = (struct sockaddr *)dst;
544
545                 error = ipsec6_output_tunnel(&state, sp, flags);
546
547                 m = state.m;
548                 ro = (struct route_in6 *)state.ro;
549                 dst = (struct sockaddr_in6 *)state.dst;
550                 if (error) {
551                         /* mbuf is already reclaimed in ipsec6_output_tunnel. */
552                         m0 = m = NULL;
553                         m = NULL;
554                         switch (error) {
555                         case EHOSTUNREACH:
556                         case ENETUNREACH:
557                         case EMSGSIZE:
558                         case ENOBUFS:
559                         case ENOMEM:
560                                 break;
561                         default:
562                                 printf("ip6_output (ipsec): error code %d\n", error);
563                                 /* fall through */
564                         case ENOENT:
565                                 /* don't show these error codes to the user */
566                                 error = 0;
567                                 break;
568                         }
569                         goto bad;
570                 }
571
572                 exthdrs.ip6e_ip6 = m;
573         }
574 #endif /* IPSEC */
575
576         if (!IN6_IS_ADDR_MULTICAST(&ip6->ip6_dst)) {
577                 /* Unicast */
578
579 #define ifatoia6(ifa)   ((struct in6_ifaddr *)(ifa))
580 #define sin6tosa(sin6)  ((struct sockaddr *)(sin6))
581                 /* xxx
582                  * interface selection comes here
583                  * if an interface is specified from an upper layer,
584                  * ifp must point it.
585                  */
586                 if (ro->ro_rt == 0) {
587                         /*
588                          * non-bsdi always clone routes, if parent is
589                          * PRF_CLONING.
590                          */
591                         rtalloc((struct route *)ro);
592                 }
593                 if (ro->ro_rt == 0) {
594                         ip6stat.ip6s_noroute++;
595                         error = EHOSTUNREACH;
596                         /* XXX in6_ifstat_inc(ifp, ifs6_out_discard); */
597                         goto bad;
598                 }
599                 ia = ifatoia6(ro->ro_rt->rt_ifa);
600                 ifp = ro->ro_rt->rt_ifp;
601                 ro->ro_rt->rt_use++;
602                 if (ro->ro_rt->rt_flags & RTF_GATEWAY)
603                         dst = (struct sockaddr_in6 *)ro->ro_rt->rt_gateway;
604                 m->m_flags &= ~(M_BCAST | M_MCAST);     /* just in case */
605
606                 in6_ifstat_inc(ifp, ifs6_out_request);
607
608                 /*
609                  * Check if the outgoing interface conflicts with
610                  * the interface specified by ifi6_ifindex (if specified).
611                  * Note that loopback interface is always okay.
612                  * (this may happen when we are sending a packet to one of
613                  *  our own addresses.)
614                  */
615                 if (opt && opt->ip6po_pktinfo
616                  && opt->ip6po_pktinfo->ipi6_ifindex) {
617                         if (!(ifp->if_flags & IFF_LOOPBACK)
618                          && ifp->if_index != opt->ip6po_pktinfo->ipi6_ifindex) {
619                                 ip6stat.ip6s_noroute++;
620                                 in6_ifstat_inc(ifp, ifs6_out_discard);
621                                 error = EHOSTUNREACH;
622                                 goto bad;
623                         }
624                 }
625
626                 if (opt && opt->ip6po_hlim != -1)
627                         ip6->ip6_hlim = opt->ip6po_hlim & 0xff;
628         } else {
629                 /* Multicast */
630                 struct  in6_multi *in6m;
631
632                 m->m_flags = (m->m_flags & ~M_BCAST) | M_MCAST;
633
634                 /*
635                  * See if the caller provided any multicast options
636                  */
637                 ifp = NULL;
638                 if (im6o != NULL) {
639                         ip6->ip6_hlim = im6o->im6o_multicast_hlim;
640                         if (im6o->im6o_multicast_ifp != NULL)
641                                 ifp = im6o->im6o_multicast_ifp;
642                 } else
643                         ip6->ip6_hlim = ip6_defmcasthlim;
644
645                 /*
646                  * See if the caller provided the outgoing interface
647                  * as an ancillary data.
648                  * Boundary check for ifindex is assumed to be already done.
649                  */
650                 if (opt && opt->ip6po_pktinfo && opt->ip6po_pktinfo->ipi6_ifindex)
651                         ifp = ifindex2ifnet[opt->ip6po_pktinfo->ipi6_ifindex];
652
653                 /*
654                  * If the destination is a node-local scope multicast,
655                  * the packet should be loop-backed only.
656                  */
657                 if (IN6_IS_ADDR_MC_NODELOCAL(&ip6->ip6_dst)) {
658                         /*
659                          * If the outgoing interface is already specified,
660                          * it should be a loopback interface.
661                          */
662                         if (ifp && (ifp->if_flags & IFF_LOOPBACK) == 0) {
663                                 ip6stat.ip6s_badscope++;
664                                 error = ENETUNREACH; /* XXX: better error? */
665                                 /* XXX correct ifp? */
666                                 in6_ifstat_inc(ifp, ifs6_out_discard);
667                                 goto bad;
668                         } else {
669                                 ifp = &loif[0];
670                         }
671                 }
672
673                 if (opt && opt->ip6po_hlim != -1)
674                         ip6->ip6_hlim = opt->ip6po_hlim & 0xff;
675
676                 /*
677                  * If caller did not provide an interface lookup a
678                  * default in the routing table.  This is either a
679                  * default for the speicfied group (i.e. a host
680                  * route), or a multicast default (a route for the
681                  * ``net'' ff00::/8).
682                  */
683                 if (ifp == NULL) {
684                         if (ro->ro_rt == NULL) {
685                                 ro->ro_rt =
686                                   rtpurelookup((struct sockaddr *)&ro->ro_dst);
687                         }
688                         if (ro->ro_rt == NULL) {
689                                 ip6stat.ip6s_noroute++;
690                                 error = EHOSTUNREACH;
691                                 /* XXX in6_ifstat_inc(ifp, ifs6_out_discard) */
692                                 goto bad;
693                         }
694                         ia = ifatoia6(ro->ro_rt->rt_ifa);
695                         ifp = ro->ro_rt->rt_ifp;
696                         ro->ro_rt->rt_use++;
697                 }
698
699                 if ((flags & IPV6_FORWARDING) == 0)
700                         in6_ifstat_inc(ifp, ifs6_out_request);
701                 in6_ifstat_inc(ifp, ifs6_out_mcast);
702
703                 /*
704                  * Confirm that the outgoing interface supports multicast.
705                  */
706                 if ((ifp->if_flags & IFF_MULTICAST) == 0) {
707                         ip6stat.ip6s_noroute++;
708                         in6_ifstat_inc(ifp, ifs6_out_discard);
709                         error = ENETUNREACH;
710                         goto bad;
711                 }
712                 IN6_LOOKUP_MULTI(ip6->ip6_dst, ifp, in6m);
713                 if (in6m != NULL &&
714                    (im6o == NULL || im6o->im6o_multicast_loop)) {
715                         /*
716                          * If we belong to the destination multicast group
717                          * on the outgoing interface, and the caller did not
718                          * forbid loopback, loop back a copy.
719                          */
720                         ip6_mloopback(ifp, m, dst);
721                 } else {
722                         /*
723                          * If we are acting as a multicast router, perform
724                          * multicast forwarding as if the packet had just
725                          * arrived on the interface to which we are about
726                          * to send.  The multicast forwarding function
727                          * recursively calls this function, using the
728                          * IPV6_FORWARDING flag to prevent infinite recursion.
729                          *
730                          * Multicasts that are looped back by ip6_mloopback(),
731                          * above, will be forwarded by the ip6_input() routine,
732                          * if necessary.
733                          */
734                         if (ip6_mrouter && (flags & IPV6_FORWARDING) == 0) {
735                                 if (ip6_mforward(ip6, ifp, m) != 0) {
736                                         m_freem(m);
737                                         goto done;
738                                 }
739                         }
740                 }
741                 /*
742                  * Multicasts with a hoplimit of zero may be looped back,
743                  * above, but must not be transmitted on a network.
744                  * Also, multicasts addressed to the loopback interface
745                  * are not sent -- the above call to ip6_mloopback() will
746                  * loop back a copy if this host actually belongs to the
747                  * destination group on the loopback interface.
748                  */
749                 if (ip6->ip6_hlim == 0 || (ifp->if_flags & IFF_LOOPBACK)) {
750                         m_freem(m);
751                         goto done;
752                 }
753         }
754
755         /*
756          * Fill the outgoing inteface to tell the upper layer
757          * to increment per-interface statistics.
758          */
759         if (ifpp)
760                 *ifpp = ifp;
761
762         /*
763          * Determine path MTU.
764          */
765         if (ro_pmtu != ro) {
766                 /* The first hop and the final destination may differ. */
767                 struct sockaddr_in6 *sin6_fin =
768                         (struct sockaddr_in6 *)&ro_pmtu->ro_dst;
769
770                 if (ro_pmtu->ro_rt && ((ro->ro_rt->rt_flags & RTF_UP) == 0 ||
771                                        !IN6_ARE_ADDR_EQUAL(&sin6_fin->sin6_addr,
772                                                            &finaldst))) {
773                         RTFREE(ro_pmtu->ro_rt);
774                         ro_pmtu->ro_rt = (struct rtentry *)0;
775                 }
776                 if (ro_pmtu->ro_rt == 0) {
777                         bzero(sin6_fin, sizeof(*sin6_fin));
778                         sin6_fin->sin6_family = AF_INET6;
779                         sin6_fin->sin6_len = sizeof(struct sockaddr_in6);
780                         sin6_fin->sin6_addr = finaldst;
781
782                         rtalloc((struct route *)ro_pmtu);
783                 }
784         }
785         if (ro_pmtu->ro_rt != NULL) {
786                 u_int32_t ifmtu = ND_IFINFO(ifp)->linkmtu;
787
788                 mtu = ro_pmtu->ro_rt->rt_rmx.rmx_mtu;
789                 if (mtu > ifmtu || mtu == 0) {
790                         /*
791                          * The MTU on the route is larger than the MTU on
792                          * the interface!  This shouldn't happen, unless the
793                          * MTU of the interface has been changed after the
794                          * interface was brought up.  Change the MTU in the
795                          * route to match the interface MTU (as long as the
796                          * field isn't locked).
797                          *
798                          * if MTU on the route is 0, we need to fix the MTU.
799                          * this case happens with path MTU discovery timeouts.
800                          */
801                          mtu = ifmtu;
802                          if ((ro_pmtu->ro_rt->rt_rmx.rmx_locks & RTV_MTU) == 0)
803                                  ro_pmtu->ro_rt->rt_rmx.rmx_mtu = mtu; /* XXX */
804                 }
805         } else {
806                 mtu = ND_IFINFO(ifp)->linkmtu;
807         }
808
809         /*
810          * advanced API (IPV6_USE_MIN_MTU) overrides mtu setting
811          */
812         if ((flags & IPV6_MINMTU) != 0 && mtu > IPV6_MMTU)
813                 mtu = IPV6_MMTU;
814
815         /* Fake scoped addresses */
816         if ((ifp->if_flags & IFF_LOOPBACK) != 0) {
817                 /*
818                  * If source or destination address is a scoped address, and
819                  * the packet is going to be sent to a loopback interface,
820                  * we should keep the original interface.
821                  */
822
823                 /*
824                  * XXX: this is a very experimental and temporary solution.
825                  * We eventually have sockaddr_in6 and use the sin6_scope_id
826                  * field of the structure here.
827                  * We rely on the consistency between two scope zone ids
828                  * of source and destination, which should already be assured.
829                  * Larger scopes than link will be supported in the future. 
830                  */
831                 origifp = NULL;
832                 if (IN6_IS_SCOPE_LINKLOCAL(&ip6->ip6_src))
833                         origifp = ifindex2ifnet[ntohs(ip6->ip6_src.s6_addr16[1])];
834                 else if (IN6_IS_SCOPE_LINKLOCAL(&ip6->ip6_dst))
835                         origifp = ifindex2ifnet[ntohs(ip6->ip6_dst.s6_addr16[1])];
836                 /*
837                  * XXX: origifp can be NULL even in those two cases above.
838                  * For example, if we remove the (only) link-local address
839                  * from the loopback interface, and try to send a link-local
840                  * address without link-id information.  Then the source
841                  * address is ::1, and the destination address is the
842                  * link-local address with its s6_addr16[1] being zero.
843                  * What is worse, if the packet goes to the loopback interface
844                  * by a default rejected route, the null pointer would be
845                  * passed to looutput, and the kernel would hang.
846                  * The following last resort would prevent such disaster.
847                  */
848                 if (origifp == NULL)
849                         origifp = ifp;
850         }
851         else
852                 origifp = ifp;
853         /*
854          * clear embedded scope identifiers if necessary.
855          * in6_clearscope will touch the addresses only when necessary.
856          */
857         in6_clearscope(&ip6->ip6_src);
858         in6_clearscope(&ip6->ip6_dst);
859
860         /*
861          * Check with the firewall...
862          */
863         if (ip6_fw_enable && ip6_fw_chk_ptr) {
864                 u_short port = 0;
865                 m->m_pkthdr.rcvif = NULL;       /* XXX */
866                 /* If ipfw says divert, we have to just drop packet */
867                 if ((*ip6_fw_chk_ptr)(&ip6, ifp, &port, &m)) {
868                         m_freem(m);
869                         goto done;
870                 }
871                 if (!m) {
872                         error = EACCES;
873                         goto done;
874                 }
875         }
876
877         /*
878          * If the outgoing packet contains a hop-by-hop options header,
879          * it must be examined and processed even by the source node.
880          * (RFC 2460, section 4.)
881          */
882         if (exthdrs.ip6e_hbh) {
883                 struct ip6_hbh *hbh = mtod(exthdrs.ip6e_hbh, struct ip6_hbh *);
884                 u_int32_t dummy1; /* XXX unused */
885                 u_int32_t dummy2; /* XXX unused */
886
887 #ifdef DIAGNOSTIC
888                 if ((hbh->ip6h_len + 1) << 3 > exthdrs.ip6e_hbh->m_len)
889                         panic("ip6e_hbh is not continuous");
890 #endif
891                 /*
892                  *  XXX: if we have to send an ICMPv6 error to the sender,
893                  *       we need the M_LOOP flag since icmp6_error() expects
894                  *       the IPv6 and the hop-by-hop options header are
895                  *       continuous unless the flag is set.
896                  */
897                 m->m_flags |= M_LOOP;
898                 m->m_pkthdr.rcvif = ifp;
899                 if (ip6_process_hopopts(m,
900                                         (u_int8_t *)(hbh + 1),
901                                         ((hbh->ip6h_len + 1) << 3) -
902                                         sizeof(struct ip6_hbh),
903                                         &dummy1, &dummy2) < 0) {
904                         /* m was already freed at this point */
905                         error = EINVAL;/* better error? */
906                         goto done;
907                 }
908                 m->m_flags &= ~M_LOOP; /* XXX */
909                 m->m_pkthdr.rcvif = NULL;
910         }
911
912         /*
913          * Run through list of hooks for output packets.
914          */
915         if (pfil_has_hooks(&inet6_pfil_hook)) {
916                 error = pfil_run_hooks(&inet6_pfil_hook, &m, ifp, PFIL_OUT);
917                 if (error != 0 || m == NULL)
918                         goto done;
919                 ip6 = mtod(m, struct ip6_hdr *);
920         }
921
922         /*
923          * Send the packet to the outgoing interface.
924          * If necessary, do IPv6 fragmentation before sending.
925          */
926         tlen = m->m_pkthdr.len;
927         if (tlen <= mtu
928 #ifdef notyet
929             /*
930              * On any link that cannot convey a 1280-octet packet in one piece,
931              * link-specific fragmentation and reassembly must be provided at
932              * a layer below IPv6. [RFC 2460, sec.5]
933              * Thus if the interface has ability of link-level fragmentation,
934              * we can just send the packet even if the packet size is
935              * larger than the link's MTU.
936              * XXX: IFF_FRAGMENTABLE (or such) flag has not been defined yet...
937              */
938         
939             || ifp->if_flags & IFF_FRAGMENTABLE
940 #endif
941             )
942         {
943                 /* Record statistics for this interface address. */
944                 if (ia && !(flags & IPV6_FORWARDING)) {
945                         ia->ia_ifa.if_opackets++;
946                         ia->ia_ifa.if_obytes += m->m_pkthdr.len;
947                 }
948 #ifdef IPSEC
949                 /* clean ipsec history once it goes out of the node */
950                 ipsec_delaux(m);
951 #endif
952                 error = nd6_output(ifp, origifp, m, dst, ro->ro_rt);
953                 goto done;
954         } else if (mtu < IPV6_MMTU) {
955                 /*
956                  * note that path MTU is never less than IPV6_MMTU
957                  * (see icmp6_input).
958                  */
959                 error = EMSGSIZE;
960                 in6_ifstat_inc(ifp, ifs6_out_fragfail);
961                 goto bad;
962         } else if (ip6->ip6_plen == 0) { /* jumbo payload cannot be fragmented */
963                 error = EMSGSIZE;
964                 in6_ifstat_inc(ifp, ifs6_out_fragfail);
965                 goto bad;
966         } else {
967                 struct mbuf **mnext, *m_frgpart;
968                 struct ip6_frag *ip6f;
969                 u_int32_t id = htonl(ip6_id++);
970                 u_char nextproto;
971
972                 /*
973                  * Too large for the destination or interface;
974                  * fragment if possible.
975                  * Must be able to put at least 8 bytes per fragment.
976                  */
977                 hlen = unfragpartlen;
978                 if (mtu > IPV6_MAXPACKET)
979                         mtu = IPV6_MAXPACKET;
980
981                 len = (mtu - hlen - sizeof(struct ip6_frag)) & ~7;
982                 if (len < 8) {
983                         error = EMSGSIZE;
984                         in6_ifstat_inc(ifp, ifs6_out_fragfail);
985                         goto bad;
986                 }
987
988                 mnext = &m->m_nextpkt;
989
990                 /*
991                  * Change the next header field of the last header in the
992                  * unfragmentable part.
993                  */
994                 if (exthdrs.ip6e_rthdr) {
995                         nextproto = *mtod(exthdrs.ip6e_rthdr, u_char *);
996                         *mtod(exthdrs.ip6e_rthdr, u_char *) = IPPROTO_FRAGMENT;
997                 } else if (exthdrs.ip6e_dest1) {
998                         nextproto = *mtod(exthdrs.ip6e_dest1, u_char *);
999                         *mtod(exthdrs.ip6e_dest1, u_char *) = IPPROTO_FRAGMENT;
1000                 } else if (exthdrs.ip6e_hbh) {
1001                         nextproto = *mtod(exthdrs.ip6e_hbh, u_char *);
1002                         *mtod(exthdrs.ip6e_hbh, u_char *) = IPPROTO_FRAGMENT;
1003                 } else {
1004                         nextproto = ip6->ip6_nxt;
1005                         ip6->ip6_nxt = IPPROTO_FRAGMENT;
1006                 }
1007
1008                 /*
1009                  * Loop through length of segment after first fragment,
1010                  * make new header and copy data of each part and link onto
1011                  * chain.
1012                  */
1013                 m0 = m;
1014                 for (off = hlen; off < tlen; off += len) {
1015                         MGETHDR(m, MB_DONTWAIT, MT_HEADER);
1016                         if (!m) {
1017                                 error = ENOBUFS;
1018                                 ip6stat.ip6s_odropped++;
1019                                 goto sendorfree;
1020                         }
1021                         m->m_pkthdr.rcvif = NULL;
1022                         m->m_flags = m0->m_flags & M_COPYFLAGS;
1023                         *mnext = m;
1024                         mnext = &m->m_nextpkt;
1025                         m->m_data += max_linkhdr;
1026                         mhip6 = mtod(m, struct ip6_hdr *);
1027                         *mhip6 = *ip6;
1028                         m->m_len = sizeof(*mhip6);
1029                         error = ip6_insertfraghdr(m0, m, hlen, &ip6f);
1030                         if (error) {
1031                                 ip6stat.ip6s_odropped++;
1032                                 goto sendorfree;
1033                         }
1034                         ip6f->ip6f_offlg = htons((u_short)((off - hlen) & ~7));
1035                         if (off + len >= tlen)
1036                                 len = tlen - off;
1037                         else
1038                                 ip6f->ip6f_offlg |= IP6F_MORE_FRAG;
1039                         mhip6->ip6_plen = htons((u_short)(len + hlen +
1040                                                           sizeof(*ip6f) -
1041                                                           sizeof(struct ip6_hdr)));
1042                         if ((m_frgpart = m_copy(m0, off, len)) == 0) {
1043                                 error = ENOBUFS;
1044                                 ip6stat.ip6s_odropped++;
1045                                 goto sendorfree;
1046                         }
1047                         m_cat(m, m_frgpart);
1048                         m->m_pkthdr.len = len + hlen + sizeof(*ip6f);
1049                         m->m_pkthdr.rcvif = (struct ifnet *)0;
1050                         ip6f->ip6f_reserved = 0;
1051                         ip6f->ip6f_ident = id;
1052                         ip6f->ip6f_nxt = nextproto;
1053                         ip6stat.ip6s_ofragments++;
1054                         in6_ifstat_inc(ifp, ifs6_out_fragcreat);
1055                 }
1056
1057                 in6_ifstat_inc(ifp, ifs6_out_fragok);
1058         }
1059
1060         /*
1061          * Remove leading garbages.
1062          */
1063 sendorfree:
1064         m = m0->m_nextpkt;
1065         m0->m_nextpkt = 0;
1066         m_freem(m0);
1067         for (m0 = m; m; m = m0) {
1068                 m0 = m->m_nextpkt;
1069                 m->m_nextpkt = 0;
1070                 if (error == 0) {
1071                         /* Record statistics for this interface address. */
1072                         if (ia) {
1073                                 ia->ia_ifa.if_opackets++;
1074                                 ia->ia_ifa.if_obytes += m->m_pkthdr.len;
1075                         }
1076 #ifdef IPSEC
1077                         /* clean ipsec history once it goes out of the node */
1078                         ipsec_delaux(m);
1079 #endif
1080                         error = nd6_output(ifp, origifp, m, dst, ro->ro_rt);
1081                 } else
1082                         m_freem(m);
1083         }
1084
1085         if (error == 0)
1086                 ip6stat.ip6s_fragmented++;
1087
1088 done:
1089         if (ro == &ip6route && ro->ro_rt) { /* brace necessary for RTFREE */
1090                 RTFREE(ro->ro_rt);
1091         } else if (ro_pmtu == &ip6route && ro_pmtu->ro_rt) {
1092                 RTFREE(ro_pmtu->ro_rt);
1093         }
1094
1095 #ifdef IPSEC
1096         if (sp != NULL)
1097                 key_freesp(sp);
1098 #endif /* IPSEC */
1099 #ifdef FAST_IPSEC
1100         if (sp != NULL)
1101                 KEY_FREESP(&sp);
1102 #endif /* FAST_IPSEC */
1103
1104         return(error);
1105
1106 freehdrs:
1107         m_freem(exthdrs.ip6e_hbh);      /* m_freem will check if mbuf is 0 */
1108         m_freem(exthdrs.ip6e_dest1);
1109         m_freem(exthdrs.ip6e_rthdr);
1110         m_freem(exthdrs.ip6e_dest2);
1111         /* fall through */
1112 bad:
1113         m_freem(m);
1114         goto done;
1115 }
1116
1117 static int
1118 ip6_copyexthdr(struct mbuf **mp, caddr_t hdr, int hlen)
1119 {
1120         struct mbuf *m;
1121
1122         if (hlen > MCLBYTES)
1123                 return(ENOBUFS); /* XXX */
1124
1125         MGET(m, MB_DONTWAIT, MT_DATA);
1126         if (!m)
1127                 return(ENOBUFS);
1128
1129         if (hlen > MLEN) {
1130                 MCLGET(m, MB_DONTWAIT);
1131                 if ((m->m_flags & M_EXT) == 0) {
1132                         m_free(m);
1133                         return(ENOBUFS);
1134                 }
1135         }
1136         m->m_len = hlen;
1137         if (hdr)
1138                 bcopy(hdr, mtod(m, caddr_t), hlen);
1139
1140         *mp = m;
1141         return(0);
1142 }
1143
1144 /*
1145  * Insert jumbo payload option.
1146  */
1147 static int
1148 ip6_insert_jumboopt(struct ip6_exthdrs *exthdrs, u_int32_t plen)
1149 {
1150         struct mbuf *mopt;
1151         u_char *optbuf;
1152         u_int32_t v;
1153
1154 #define JUMBOOPTLEN     8       /* length of jumbo payload option and padding */
1155
1156         /*
1157          * If there is no hop-by-hop options header, allocate new one.
1158          * If there is one but it doesn't have enough space to store the
1159          * jumbo payload option, allocate a cluster to store the whole options.
1160          * Otherwise, use it to store the options.
1161          */
1162         if (exthdrs->ip6e_hbh == 0) {
1163                 MGET(mopt, MB_DONTWAIT, MT_DATA);
1164                 if (mopt == 0)
1165                         return(ENOBUFS);
1166                 mopt->m_len = JUMBOOPTLEN;
1167                 optbuf = mtod(mopt, u_char *);
1168                 optbuf[1] = 0;  /* = ((JUMBOOPTLEN) >> 3) - 1 */
1169                 exthdrs->ip6e_hbh = mopt;
1170         } else {
1171                 struct ip6_hbh *hbh;
1172
1173                 mopt = exthdrs->ip6e_hbh;
1174                 if (M_TRAILINGSPACE(mopt) < JUMBOOPTLEN) {
1175                         /*
1176                          * XXX assumption:
1177                          * - exthdrs->ip6e_hbh is not referenced from places
1178                          *   other than exthdrs.
1179                          * - exthdrs->ip6e_hbh is not an mbuf chain.
1180                          */
1181                         int oldoptlen = mopt->m_len;
1182                         struct mbuf *n;
1183
1184                         /*
1185                          * XXX: give up if the whole (new) hbh header does
1186                          * not fit even in an mbuf cluster.
1187                          */
1188                         if (oldoptlen + JUMBOOPTLEN > MCLBYTES)
1189                                 return(ENOBUFS);
1190
1191                         /*
1192                          * As a consequence, we must always prepare a cluster
1193                          * at this point.
1194                          */
1195                         MGET(n, MB_DONTWAIT, MT_DATA);
1196                         if (n) {
1197                                 MCLGET(n, MB_DONTWAIT);
1198                                 if ((n->m_flags & M_EXT) == 0) {
1199                                         m_freem(n);
1200                                         n = NULL;
1201                                 }
1202                         }
1203                         if (!n)
1204                                 return(ENOBUFS);
1205                         n->m_len = oldoptlen + JUMBOOPTLEN;
1206                         bcopy(mtod(mopt, caddr_t), mtod(n, caddr_t),
1207                               oldoptlen);
1208                         optbuf = mtod(n, caddr_t) + oldoptlen;
1209                         m_freem(mopt);
1210                         mopt = exthdrs->ip6e_hbh = n;
1211                 } else {
1212                         optbuf = mtod(mopt, u_char *) + mopt->m_len;
1213                         mopt->m_len += JUMBOOPTLEN;
1214                 }
1215                 optbuf[0] = IP6OPT_PADN;
1216                 optbuf[1] = 1;
1217
1218                 /*
1219                  * Adjust the header length according to the pad and
1220                  * the jumbo payload option.
1221                  */
1222                 hbh = mtod(mopt, struct ip6_hbh *);
1223                 hbh->ip6h_len += (JUMBOOPTLEN >> 3);
1224         }
1225
1226         /* fill in the option. */
1227         optbuf[2] = IP6OPT_JUMBO;
1228         optbuf[3] = 4;
1229         v = (u_int32_t)htonl(plen + JUMBOOPTLEN);
1230         bcopy(&v, &optbuf[4], sizeof(u_int32_t));
1231
1232         /* finally, adjust the packet header length */
1233         exthdrs->ip6e_ip6->m_pkthdr.len += JUMBOOPTLEN;
1234
1235         return(0);
1236 #undef JUMBOOPTLEN
1237 }
1238
1239 /*
1240  * Insert fragment header and copy unfragmentable header portions.
1241  */
1242 static int
1243 ip6_insertfraghdr(struct mbuf *m0, struct mbuf *m, int hlen,
1244                   struct ip6_frag **frghdrp)
1245 {
1246         struct mbuf *n, *mlast;
1247
1248         if (hlen > sizeof(struct ip6_hdr)) {
1249                 n = m_copym(m0, sizeof(struct ip6_hdr),
1250                             hlen - sizeof(struct ip6_hdr), MB_DONTWAIT);
1251                 if (n == 0)
1252                         return(ENOBUFS);
1253                 m->m_next = n;
1254         } else
1255                 n = m;
1256
1257         /* Search for the last mbuf of unfragmentable part. */
1258         for (mlast = n; mlast->m_next; mlast = mlast->m_next)
1259                 ;
1260
1261         if ((mlast->m_flags & M_EXT) == 0 &&
1262             M_TRAILINGSPACE(mlast) >= sizeof(struct ip6_frag)) {
1263                 /* use the trailing space of the last mbuf for the fragment hdr */
1264                 *frghdrp =
1265                         (struct ip6_frag *)(mtod(mlast, caddr_t) + mlast->m_len);
1266                 mlast->m_len += sizeof(struct ip6_frag);
1267                 m->m_pkthdr.len += sizeof(struct ip6_frag);
1268         } else {
1269                 /* allocate a new mbuf for the fragment header */
1270                 struct mbuf *mfrg;
1271
1272                 MGET(mfrg, MB_DONTWAIT, MT_DATA);
1273                 if (mfrg == 0)
1274                         return(ENOBUFS);
1275                 mfrg->m_len = sizeof(struct ip6_frag);
1276                 *frghdrp = mtod(mfrg, struct ip6_frag *);
1277                 mlast->m_next = mfrg;
1278         }
1279
1280         return(0);
1281 }
1282
1283 /*
1284  * IP6 socket option processing.
1285  */
1286 int
1287 ip6_ctloutput(struct socket *so, struct sockopt *sopt)
1288 {
1289         int privileged;
1290         struct inpcb *in6p = so->so_pcb;
1291         int error, optval;
1292         int level, op, optname;
1293         int optlen;
1294         struct thread *td;
1295
1296         if (sopt) {
1297                 level = sopt->sopt_level;
1298                 op = sopt->sopt_dir;
1299                 optname = sopt->sopt_name;
1300                 optlen = sopt->sopt_valsize;
1301                 td = sopt->sopt_td;
1302         } else {
1303                 panic("ip6_ctloutput: arg soopt is NULL");
1304                 /* NOT REACHED */
1305                 td = NULL;
1306         }
1307         error = optval = 0;
1308
1309         privileged = (td == NULL || suser(td)) ? 0 : 1;
1310
1311         if (level == IPPROTO_IPV6) {
1312                 switch (op) {
1313
1314                 case SOPT_SET:
1315                         switch (optname) {
1316                         case IPV6_PKTOPTIONS:
1317                         {
1318                                 struct mbuf *m;
1319
1320                                 error = soopt_getm(sopt, &m); /* XXX */
1321                                 if (error != NULL)
1322                                         break;
1323                                 error = soopt_mcopyin(sopt, m); /* XXX */
1324                                 if (error != NULL)
1325                                         break;
1326                                 error = ip6_pcbopts(&in6p->in6p_outputopts,
1327                                                     m, so, sopt);
1328                                 m_freem(m); /* XXX */
1329                                 break;
1330                         }
1331
1332                         /*
1333                          * Use of some Hop-by-Hop options or some
1334                          * Destination options, might require special
1335                          * privilege.  That is, normal applications
1336                          * (without special privilege) might be forbidden
1337                          * from setting certain options in outgoing packets,
1338                          * and might never see certain options in received
1339                          * packets. [RFC 2292 Section 6]
1340                          * KAME specific note:
1341                          *  KAME prevents non-privileged users from sending or
1342                          *  receiving ANY hbh/dst options in order to avoid
1343                          *  overhead of parsing options in the kernel.
1344                          */
1345                         case IPV6_UNICAST_HOPS:
1346                         case IPV6_CHECKSUM:
1347                         case IPV6_FAITH:
1348
1349                         case IPV6_V6ONLY:
1350                                 if (optlen != sizeof(int)) {
1351                                         error = EINVAL;
1352                                         break;
1353                                 }
1354                                 error = sooptcopyin(sopt, &optval,
1355                                         sizeof optval, sizeof optval);
1356                                 if (error)
1357                                         break;
1358                                 switch (optname) {
1359
1360                                 case IPV6_UNICAST_HOPS:
1361                                         if (optval < -1 || optval >= 256)
1362                                                 error = EINVAL;
1363                                         else {
1364                                                 /* -1 = kernel default */
1365                                                 in6p->in6p_hops = optval;
1366
1367                                                 if ((in6p->in6p_vflag &
1368                                                      INP_IPV4) != 0)
1369                                                         in6p->inp_ip_ttl = optval;
1370                                         }
1371                                         break;
1372 #define OPTSET(bit) \
1373 do { \
1374         if (optval) \
1375                 in6p->in6p_flags |= (bit); \
1376         else \
1377                 in6p->in6p_flags &= ~(bit); \
1378 } while (0)
1379 #define OPTBIT(bit) (in6p->in6p_flags & (bit) ? 1 : 0)
1380
1381                                 case IPV6_CHECKSUM:
1382                                         in6p->in6p_cksum = optval;
1383                                         break;
1384
1385                                 case IPV6_FAITH:
1386                                         OPTSET(IN6P_FAITH);
1387                                         break;
1388
1389                                 case IPV6_V6ONLY:
1390                                         /*
1391                                          * make setsockopt(IPV6_V6ONLY)
1392                                          * available only prior to bind(2).
1393                                          * see ipng mailing list, Jun 22 2001.
1394                                          */
1395                                         if (in6p->in6p_lport ||
1396                                             !IN6_IS_ADDR_UNSPECIFIED(&in6p->in6p_laddr))
1397                                         {
1398                                                 error = EINVAL;
1399                                                 break;
1400                                         }
1401                                         OPTSET(IN6P_IPV6_V6ONLY);
1402                                         if (optval)
1403                                                 in6p->in6p_vflag &= ~INP_IPV4;
1404                                         else
1405                                                 in6p->in6p_vflag |= INP_IPV4;
1406                                         break;
1407                                 }
1408                                 break;
1409
1410                         case IPV6_PKTINFO:
1411                         case IPV6_HOPLIMIT:
1412                         case IPV6_HOPOPTS:
1413                         case IPV6_DSTOPTS:
1414                         case IPV6_RTHDR:
1415                                 /* RFC 2292 */
1416                                 if (optlen != sizeof(int)) {
1417                                         error = EINVAL;
1418                                         break;
1419                                 }
1420                                 error = sooptcopyin(sopt, &optval,
1421                                         sizeof optval, sizeof optval);
1422                                 if (error)
1423                                         break;
1424                                 switch (optname) {
1425                                 case IPV6_PKTINFO:
1426                                         OPTSET(IN6P_PKTINFO);
1427                                         break;
1428                                 case IPV6_HOPLIMIT:
1429                                         OPTSET(IN6P_HOPLIMIT);
1430                                         break;
1431                                 case IPV6_HOPOPTS:
1432                                         /*
1433                                          * Check super-user privilege.
1434                                          * See comments for IPV6_RECVHOPOPTS.
1435                                          */
1436                                         if (!privileged)
1437                                                 return(EPERM);
1438                                         OPTSET(IN6P_HOPOPTS);
1439                                         break;
1440                                 case IPV6_DSTOPTS:
1441                                         if (!privileged)
1442                                                 return(EPERM);
1443                                         OPTSET(IN6P_DSTOPTS|IN6P_RTHDRDSTOPTS); /* XXX */
1444                                         break;
1445                                 case IPV6_RTHDR:
1446                                         OPTSET(IN6P_RTHDR);
1447                                         break;
1448                                 }
1449                                 break;
1450 #undef OPTSET
1451
1452                         case IPV6_MULTICAST_IF:
1453                         case IPV6_MULTICAST_HOPS:
1454                         case IPV6_MULTICAST_LOOP:
1455                         case IPV6_JOIN_GROUP:
1456                         case IPV6_LEAVE_GROUP:
1457                             {
1458                                 struct mbuf *m;
1459                                 if (sopt->sopt_valsize > MLEN) {
1460                                         error = EMSGSIZE;
1461                                         break;
1462                                 }
1463                                 /* XXX */
1464                                 MGET(m, sopt->sopt_td ? MB_WAIT : MB_DONTWAIT, MT_HEADER);
1465                                 if (m == 0) {
1466                                         error = ENOBUFS;
1467                                         break;
1468                                 }
1469                                 m->m_len = sopt->sopt_valsize;
1470                                 error = sooptcopyin(sopt, mtod(m, char *),
1471                                                     m->m_len, m->m_len);
1472                                 error = ip6_setmoptions(sopt->sopt_name,
1473                                                         &in6p->in6p_moptions,
1474                                                         m);
1475                                 m_free(m);
1476                             }
1477                                 break;
1478
1479                         case IPV6_PORTRANGE:
1480                                 error = sooptcopyin(sopt, &optval,
1481                                     sizeof optval, sizeof optval);
1482                                 if (error)
1483                                         break;
1484
1485                                 switch (optval) {
1486                                 case IPV6_PORTRANGE_DEFAULT:
1487                                         in6p->in6p_flags &= ~(IN6P_LOWPORT);
1488                                         in6p->in6p_flags &= ~(IN6P_HIGHPORT);
1489                                         break;
1490
1491                                 case IPV6_PORTRANGE_HIGH:
1492                                         in6p->in6p_flags &= ~(IN6P_LOWPORT);
1493                                         in6p->in6p_flags |= IN6P_HIGHPORT;
1494                                         break;
1495
1496                                 case IPV6_PORTRANGE_LOW:
1497                                         in6p->in6p_flags &= ~(IN6P_HIGHPORT);
1498                                         in6p->in6p_flags |= IN6P_LOWPORT;
1499                                         break;
1500
1501                                 default:
1502                                         error = EINVAL;
1503                                         break;
1504                                 }
1505                                 break;
1506
1507 #if defined(IPSEC) || defined(FAST_IPSEC)
1508                         case IPV6_IPSEC_POLICY:
1509                             {
1510                                 caddr_t req = NULL;
1511                                 size_t len = 0;
1512                                 struct mbuf *m;
1513
1514                                 if ((error = soopt_getm(sopt, &m)) != 0) /* XXX */
1515                                         break;
1516                                 if ((error = soopt_mcopyin(sopt, m)) != 0) /* XXX */
1517                                         break;
1518                                 if (m) {
1519                                         req = mtod(m, caddr_t);
1520                                         len = m->m_len;
1521                                 }
1522                                 error = ipsec6_set_policy(in6p, optname, req,
1523                                                           len, privileged);
1524                                 m_freem(m);
1525                             }
1526                                 break;
1527 #endif /* KAME IPSEC */
1528
1529                         case IPV6_FW_ADD:
1530                         case IPV6_FW_DEL:
1531                         case IPV6_FW_FLUSH:
1532                         case IPV6_FW_ZERO:
1533                             {
1534                                 struct mbuf *m;
1535                                 struct mbuf **mp = &m;
1536
1537                                 if (ip6_fw_ctl_ptr == NULL)
1538                                         return EINVAL;
1539                                 /* XXX */
1540                                 if ((error = soopt_getm(sopt, &m)) != 0)
1541                                         break;
1542                                 /* XXX */
1543                                 if ((error = soopt_mcopyin(sopt, m)) != 0)
1544                                         break;
1545                                 error = (*ip6_fw_ctl_ptr)(optname, mp);
1546                                 m = *mp;
1547                             }
1548                                 break;
1549
1550                         default:
1551                                 error = ENOPROTOOPT;
1552                                 break;
1553                         }
1554                         break;
1555
1556                 case SOPT_GET:
1557                         switch (optname) {
1558
1559                         case IPV6_PKTOPTIONS:
1560                                 if (in6p->in6p_options) {
1561                                         struct mbuf *m;
1562                                         m = m_copym(in6p->in6p_options,
1563                                             0, M_COPYALL, MB_WAIT);
1564                                         error = soopt_mcopyout(sopt, m);
1565                                         if (error == 0)
1566                                                 m_freem(m);
1567                                 } else
1568                                         sopt->sopt_valsize = 0;
1569                                 break;
1570
1571                         case IPV6_UNICAST_HOPS:
1572                         case IPV6_CHECKSUM:
1573
1574                         case IPV6_FAITH:
1575                         case IPV6_V6ONLY:
1576                         case IPV6_PORTRANGE:
1577                                 switch (optname) {
1578
1579                                 case IPV6_UNICAST_HOPS:
1580                                         optval = in6p->in6p_hops;
1581                                         break;
1582
1583                                 case IPV6_CHECKSUM:
1584                                         optval = in6p->in6p_cksum;
1585                                         break;
1586
1587                                 case IPV6_FAITH:
1588                                         optval = OPTBIT(IN6P_FAITH);
1589                                         break;
1590
1591                                 case IPV6_V6ONLY:
1592                                         optval = OPTBIT(IN6P_IPV6_V6ONLY);
1593                                         break;
1594
1595                                 case IPV6_PORTRANGE:
1596                                     {
1597                                         int flags;
1598                                         flags = in6p->in6p_flags;
1599                                         if (flags & IN6P_HIGHPORT)
1600                                                 optval = IPV6_PORTRANGE_HIGH;
1601                                         else if (flags & IN6P_LOWPORT)
1602                                                 optval = IPV6_PORTRANGE_LOW;
1603                                         else
1604                                                 optval = 0;
1605                                         break;
1606                                     }
1607                                 }
1608                                 error = sooptcopyout(sopt, &optval,
1609                                         sizeof optval);
1610                                 break;
1611
1612                         case IPV6_PKTINFO:
1613                         case IPV6_HOPLIMIT:
1614                         case IPV6_HOPOPTS:
1615                         case IPV6_RTHDR:
1616                         case IPV6_DSTOPTS:
1617                                 if (optname == IPV6_HOPOPTS ||
1618                                     optname == IPV6_DSTOPTS ||
1619                                     !privileged)
1620                                         return(EPERM);
1621                                 switch (optname) {
1622                                 case IPV6_PKTINFO:
1623                                         optval = OPTBIT(IN6P_PKTINFO);
1624                                         break;
1625                                 case IPV6_HOPLIMIT:
1626                                         optval = OPTBIT(IN6P_HOPLIMIT);
1627                                         break;
1628                                 case IPV6_HOPOPTS:
1629                                         if (!privileged)
1630                                                 return(EPERM);
1631                                         optval = OPTBIT(IN6P_HOPOPTS);
1632                                         break;
1633                                 case IPV6_RTHDR:
1634                                         optval = OPTBIT(IN6P_RTHDR);
1635                                         break;
1636                                 case IPV6_DSTOPTS:
1637                                         if (!privileged)
1638                                                 return(EPERM);
1639                                         optval = OPTBIT(IN6P_DSTOPTS|IN6P_RTHDRDSTOPTS);
1640                                         break;
1641                                 }
1642                                 error = sooptcopyout(sopt, &optval,
1643                                         sizeof optval);
1644                                 break;
1645
1646                         case IPV6_MULTICAST_IF:
1647                         case IPV6_MULTICAST_HOPS:
1648                         case IPV6_MULTICAST_LOOP:
1649                         case IPV6_JOIN_GROUP:
1650                         case IPV6_LEAVE_GROUP:
1651                             {
1652                                 struct mbuf *m;
1653                                 error = ip6_getmoptions(sopt->sopt_name,
1654                                                 in6p->in6p_moptions, &m);
1655                                 if (error == 0)
1656                                         error = sooptcopyout(sopt,
1657                                                 mtod(m, char *), m->m_len);
1658                                 m_freem(m);
1659                             }
1660                                 break;
1661
1662 #if defined(IPSEC) || defined(FAST_IPSEC)
1663                         case IPV6_IPSEC_POLICY:
1664                           {
1665                                 caddr_t req = NULL;
1666                                 size_t len = 0;
1667                                 struct mbuf *m = NULL;
1668                                 struct mbuf **mp = &m;
1669
1670                                 error = soopt_getm(sopt, &m); /* XXX */
1671                                 if (error != NULL)
1672                                         break;
1673                                 error = soopt_mcopyin(sopt, m); /* XXX */
1674                                 if (error != NULL)
1675                                         break;
1676                                 if (m) {
1677                                         req = mtod(m, caddr_t);
1678                                         len = m->m_len;
1679                                 }
1680                                 error = ipsec6_get_policy(in6p, req, len, mp);
1681                                 if (error == 0)
1682                                         error = soopt_mcopyout(sopt, m); /*XXX*/
1683                                 if (error == 0 && m)
1684                                         m_freem(m);
1685                                 break;
1686                           }
1687 #endif /* KAME IPSEC */
1688
1689                         case IPV6_FW_GET:
1690                           {
1691                                 struct mbuf *m;
1692                                 struct mbuf **mp = &m;
1693
1694                                 if (ip6_fw_ctl_ptr == NULL)
1695                                 {
1696                                         return EINVAL;
1697                                 }
1698                                 error = (*ip6_fw_ctl_ptr)(optname, mp);
1699                                 if (error == 0)
1700                                         error = soopt_mcopyout(sopt, m); /* XXX */
1701                                 if (error == 0 && m)
1702                                         m_freem(m);
1703                           }
1704                                 break;
1705
1706                         default:
1707                                 error = ENOPROTOOPT;
1708                                 break;
1709                         }
1710                         break;
1711                 }
1712         } else {
1713                 error = EINVAL;
1714         }
1715         return(error);
1716 }
1717
1718 /*
1719  * Set up IP6 options in pcb for insertion in output packets or
1720  * specifying behavior of outgoing packets.
1721  */
1722 static int
1723 ip6_pcbopts(struct ip6_pktopts **pktopt, struct mbuf *m, struct socket *so,
1724             struct sockopt *sopt)
1725 {
1726         struct ip6_pktopts *opt = *pktopt;
1727         int error = 0;
1728         struct thread *td = sopt->sopt_td;
1729         int priv = 0;
1730
1731         /* turn off any old options. */
1732         if (opt) {
1733 #ifdef DIAGNOSTIC
1734                 if (opt->ip6po_pktinfo || opt->ip6po_nexthop ||
1735                     opt->ip6po_hbh || opt->ip6po_dest1 || opt->ip6po_dest2 ||
1736                     opt->ip6po_rhinfo.ip6po_rhi_rthdr)
1737                         printf("ip6_pcbopts: all specified options are cleared.\n");
1738 #endif
1739                 ip6_clearpktopts(opt, 1, -1);
1740         } else
1741                 opt = malloc(sizeof(*opt), M_IP6OPT, M_WAITOK);
1742         *pktopt = NULL;
1743
1744         if (!m || m->m_len == 0) {
1745                 /*
1746                  * Only turning off any previous options, regardless of
1747                  * whether the opt is just created or given.
1748                  */
1749                 free(opt, M_IP6OPT);
1750                 return(0);
1751         }
1752
1753         /*  set options specified by user. */
1754         if (suser(td) == 0)
1755                 priv = 1;
1756         if ((error = ip6_setpktoptions(m, opt, priv, 1)) != 0) {
1757                 ip6_clearpktopts(opt, 1, -1); /* XXX: discard all options */
1758                 free(opt, M_IP6OPT);
1759                 return(error);
1760         }
1761         *pktopt = opt;
1762         return(0);
1763 }
1764
1765 /*
1766  * initialize ip6_pktopts.  beware that there are non-zero default values in
1767  * the struct.
1768  */
1769 void
1770 init_ip6pktopts(struct ip6_pktopts *opt)
1771 {
1772
1773         bzero(opt, sizeof(*opt));
1774         opt->ip6po_hlim = -1;   /* -1 means default hop limit */
1775 }
1776
1777 void
1778 ip6_clearpktopts(struct ip6_pktopts *pktopt, int needfree, int optname)
1779 {
1780         if (pktopt == NULL)
1781                 return;
1782
1783         if (optname == -1) {
1784                 if (needfree && pktopt->ip6po_pktinfo)
1785                         free(pktopt->ip6po_pktinfo, M_IP6OPT);
1786                 pktopt->ip6po_pktinfo = NULL;
1787         }
1788         if (optname == -1)
1789                 pktopt->ip6po_hlim = -1;
1790         if (optname == -1) {
1791                 if (needfree && pktopt->ip6po_nexthop)
1792                         free(pktopt->ip6po_nexthop, M_IP6OPT);
1793                 pktopt->ip6po_nexthop = NULL;
1794         }
1795         if (optname == -1) {
1796                 if (needfree && pktopt->ip6po_hbh)
1797                         free(pktopt->ip6po_hbh, M_IP6OPT);
1798                 pktopt->ip6po_hbh = NULL;
1799         }
1800         if (optname == -1) {
1801                 if (needfree && pktopt->ip6po_dest1)
1802                         free(pktopt->ip6po_dest1, M_IP6OPT);
1803                 pktopt->ip6po_dest1 = NULL;
1804         }
1805         if (optname == -1) {
1806                 if (needfree && pktopt->ip6po_rhinfo.ip6po_rhi_rthdr)
1807                         free(pktopt->ip6po_rhinfo.ip6po_rhi_rthdr, M_IP6OPT);
1808                 pktopt->ip6po_rhinfo.ip6po_rhi_rthdr = NULL;
1809                 if (pktopt->ip6po_route.ro_rt) {
1810                         RTFREE(pktopt->ip6po_route.ro_rt);
1811                         pktopt->ip6po_route.ro_rt = NULL;
1812                 }
1813         }
1814         if (optname == -1) {
1815                 if (needfree && pktopt->ip6po_dest2)
1816                         free(pktopt->ip6po_dest2, M_IP6OPT);
1817                 pktopt->ip6po_dest2 = NULL;
1818         }
1819 }
1820
1821 #define PKTOPT_EXTHDRCPY(type) \
1822 do {\
1823         if (src->type) {\
1824                 int hlen =\
1825                         (((struct ip6_ext *)src->type)->ip6e_len + 1) << 3;\
1826                 dst->type = malloc(hlen, M_IP6OPT, canwait);\
1827                 if (dst->type == NULL && canwait == M_NOWAIT)\
1828                         goto bad;\
1829                 bcopy(src->type, dst->type, hlen);\
1830         }\
1831 } while (0)
1832
1833 struct ip6_pktopts *
1834 ip6_copypktopts(struct ip6_pktopts *src, int canwait)
1835 {
1836         struct ip6_pktopts *dst;
1837
1838         if (src == NULL) {
1839                 printf("ip6_clearpktopts: invalid argument\n");
1840                 return(NULL);
1841         }
1842
1843         dst = malloc(sizeof(*dst), M_IP6OPT, canwait);
1844         if (dst == NULL && canwait == M_NOWAIT)
1845                 return (NULL);
1846         bzero(dst, sizeof(*dst));
1847
1848         dst->ip6po_hlim = src->ip6po_hlim;
1849         if (src->ip6po_pktinfo) {
1850                 dst->ip6po_pktinfo = malloc(sizeof(*dst->ip6po_pktinfo),
1851                                             M_IP6OPT, canwait);
1852                 if (dst->ip6po_pktinfo == NULL && canwait == M_NOWAIT)
1853                         goto bad;
1854                 *dst->ip6po_pktinfo = *src->ip6po_pktinfo;
1855         }
1856         if (src->ip6po_nexthop) {
1857                 dst->ip6po_nexthop = malloc(src->ip6po_nexthop->sa_len,
1858                                             M_IP6OPT, canwait);
1859                 if (dst->ip6po_nexthop == NULL && canwait == M_NOWAIT)
1860                         goto bad;
1861                 bcopy(src->ip6po_nexthop, dst->ip6po_nexthop,
1862                       src->ip6po_nexthop->sa_len);
1863         }
1864         PKTOPT_EXTHDRCPY(ip6po_hbh);
1865         PKTOPT_EXTHDRCPY(ip6po_dest1);
1866         PKTOPT_EXTHDRCPY(ip6po_dest2);
1867         PKTOPT_EXTHDRCPY(ip6po_rthdr); /* not copy the cached route */
1868         return(dst);
1869
1870   bad:
1871         if (dst->ip6po_pktinfo) free(dst->ip6po_pktinfo, M_IP6OPT);
1872         if (dst->ip6po_nexthop) free(dst->ip6po_nexthop, M_IP6OPT);
1873         if (dst->ip6po_hbh) free(dst->ip6po_hbh, M_IP6OPT);
1874         if (dst->ip6po_dest1) free(dst->ip6po_dest1, M_IP6OPT);
1875         if (dst->ip6po_dest2) free(dst->ip6po_dest2, M_IP6OPT);
1876         if (dst->ip6po_rthdr) free(dst->ip6po_rthdr, M_IP6OPT);
1877         free(dst, M_IP6OPT);
1878         return(NULL);
1879 }
1880 #undef PKTOPT_EXTHDRCPY
1881
1882 void
1883 ip6_freepcbopts(struct ip6_pktopts *pktopt)
1884 {
1885         if (pktopt == NULL)
1886                 return;
1887
1888         ip6_clearpktopts(pktopt, 1, -1);
1889
1890         free(pktopt, M_IP6OPT);
1891 }
1892
1893 /*
1894  * Set the IP6 multicast options in response to user setsockopt().
1895  */
1896 static int
1897 ip6_setmoptions(int optname, struct ip6_moptions **im6op, struct mbuf *m)
1898 {
1899         int error = 0;
1900         u_int loop, ifindex;
1901         struct ipv6_mreq *mreq;
1902         struct ifnet *ifp;
1903         struct ip6_moptions *im6o = *im6op;
1904         struct route_in6 ro;
1905         struct sockaddr_in6 *dst;
1906         struct in6_multi_mship *imm;
1907         struct thread *td = curthread;  /* XXX */
1908
1909         if (im6o == NULL) {
1910                 /*
1911                  * No multicast option buffer attached to the pcb;
1912                  * allocate one and initialize to default values.
1913                  */
1914                 im6o = (struct ip6_moptions *)
1915                         malloc(sizeof(*im6o), M_IPMOPTS, M_WAITOK);
1916
1917                 if (im6o == NULL)
1918                         return(ENOBUFS);
1919                 *im6op = im6o;
1920                 im6o->im6o_multicast_ifp = NULL;
1921                 im6o->im6o_multicast_hlim = ip6_defmcasthlim;
1922                 im6o->im6o_multicast_loop = IPV6_DEFAULT_MULTICAST_LOOP;
1923                 LIST_INIT(&im6o->im6o_memberships);
1924         }
1925
1926         switch (optname) {
1927
1928         case IPV6_MULTICAST_IF:
1929                 /*
1930                  * Select the interface for outgoing multicast packets.
1931                  */
1932                 if (m == NULL || m->m_len != sizeof(u_int)) {
1933                         error = EINVAL;
1934                         break;
1935                 }
1936                 bcopy(mtod(m, u_int *), &ifindex, sizeof(ifindex));
1937                 if (ifindex < 0 || if_index < ifindex) {
1938                         error = ENXIO;  /* XXX EINVAL? */
1939                         break;
1940                 }
1941                 ifp = ifindex2ifnet[ifindex];
1942                 if (ifp == NULL || (ifp->if_flags & IFF_MULTICAST) == 0) {
1943                         error = EADDRNOTAVAIL;
1944                         break;
1945                 }
1946                 im6o->im6o_multicast_ifp = ifp;
1947                 break;
1948
1949         case IPV6_MULTICAST_HOPS:
1950             {
1951                 /*
1952                  * Set the IP6 hoplimit for outgoing multicast packets.
1953                  */
1954                 int optval;
1955                 if (m == NULL || m->m_len != sizeof(int)) {
1956                         error = EINVAL;
1957                         break;
1958                 }
1959                 bcopy(mtod(m, u_int *), &optval, sizeof(optval));
1960                 if (optval < -1 || optval >= 256)
1961                         error = EINVAL;
1962                 else if (optval == -1)
1963                         im6o->im6o_multicast_hlim = ip6_defmcasthlim;
1964                 else
1965                         im6o->im6o_multicast_hlim = optval;
1966                 break;
1967             }
1968
1969         case IPV6_MULTICAST_LOOP:
1970                 /*
1971                  * Set the loopback flag for outgoing multicast packets.
1972                  * Must be zero or one.
1973                  */
1974                 if (m == NULL || m->m_len != sizeof(u_int)) {
1975                         error = EINVAL;
1976                         break;
1977                 }
1978                 bcopy(mtod(m, u_int *), &loop, sizeof(loop));
1979                 if (loop > 1) {
1980                         error = EINVAL;
1981                         break;
1982                 }
1983                 im6o->im6o_multicast_loop = loop;
1984                 break;
1985
1986         case IPV6_JOIN_GROUP:
1987                 /*
1988                  * Add a multicast group membership.
1989                  * Group must be a valid IP6 multicast address.
1990                  */
1991                 if (m == NULL || m->m_len != sizeof(struct ipv6_mreq)) {
1992                         error = EINVAL;
1993                         break;
1994                 }
1995                 mreq = mtod(m, struct ipv6_mreq *);
1996                 if (IN6_IS_ADDR_UNSPECIFIED(&mreq->ipv6mr_multiaddr)) {
1997                         /*
1998                          * We use the unspecified address to specify to accept
1999                          * all multicast addresses. Only super user is allowed
2000                          * to do this.
2001                          */
2002                         if (suser(td))
2003                         {
2004                                 error = EACCES;
2005                                 break;
2006                         }
2007                 } else if (!IN6_IS_ADDR_MULTICAST(&mreq->ipv6mr_multiaddr)) {
2008                         error = EINVAL;
2009                         break;
2010                 }
2011
2012                 /*
2013                  * If the interface is specified, validate it.
2014                  */
2015                 if (mreq->ipv6mr_interface < 0
2016                  || if_index < mreq->ipv6mr_interface) {
2017                         error = ENXIO;  /* XXX EINVAL? */
2018                         break;
2019                 }
2020                 /*
2021                  * If no interface was explicitly specified, choose an
2022                  * appropriate one according to the given multicast address.
2023                  */
2024                 if (mreq->ipv6mr_interface == 0) {
2025                         /*
2026                          * If the multicast address is in node-local scope,
2027                          * the interface should be a loopback interface.
2028                          * Otherwise, look up the routing table for the
2029                          * address, and choose the outgoing interface.
2030                          *   XXX: is it a good approach?
2031                          */
2032                         if (IN6_IS_ADDR_MC_NODELOCAL(&mreq->ipv6mr_multiaddr)) {
2033                                 ifp = &loif[0];
2034                         } else {
2035                                 ro.ro_rt = NULL;
2036                                 dst = (struct sockaddr_in6 *)&ro.ro_dst;
2037                                 bzero(dst, sizeof(*dst));
2038                                 dst->sin6_len = sizeof(struct sockaddr_in6);
2039                                 dst->sin6_family = AF_INET6;
2040                                 dst->sin6_addr = mreq->ipv6mr_multiaddr;
2041                                 rtalloc((struct route *)&ro);
2042                                 if (ro.ro_rt == NULL) {
2043                                         error = EADDRNOTAVAIL;
2044                                         break;
2045                                 }
2046                                 ifp = ro.ro_rt->rt_ifp;
2047                                 rtfree(ro.ro_rt);
2048                         }
2049                 } else
2050                         ifp = ifindex2ifnet[mreq->ipv6mr_interface];
2051
2052                 /*
2053                  * See if we found an interface, and confirm that it
2054                  * supports multicast
2055                  */
2056                 if (ifp == NULL || (ifp->if_flags & IFF_MULTICAST) == 0) {
2057                         error = EADDRNOTAVAIL;
2058                         break;
2059                 }
2060                 /*
2061                  * Put interface index into the multicast address,
2062                  * if the address has link-local scope.
2063                  */
2064                 if (IN6_IS_ADDR_MC_LINKLOCAL(&mreq->ipv6mr_multiaddr)) {
2065                         mreq->ipv6mr_multiaddr.s6_addr16[1]
2066                                 = htons(mreq->ipv6mr_interface);
2067                 }
2068                 /*
2069                  * See if the membership already exists.
2070                  */
2071                 for (imm = im6o->im6o_memberships.lh_first;
2072                      imm != NULL; imm = imm->i6mm_chain.le_next)
2073                         if (imm->i6mm_maddr->in6m_ifp == ifp &&
2074                             IN6_ARE_ADDR_EQUAL(&imm->i6mm_maddr->in6m_addr,
2075                                                &mreq->ipv6mr_multiaddr))
2076                                 break;
2077                 if (imm != NULL) {
2078                         error = EADDRINUSE;
2079                         break;
2080                 }
2081                 /*
2082                  * Everything looks good; add a new record to the multicast
2083                  * address list for the given interface.
2084                  */
2085                 imm = malloc(sizeof(*imm), M_IPMADDR, M_WAITOK);
2086                 if (imm == NULL) {
2087                         error = ENOBUFS;
2088                         break;
2089                 }
2090                 if ((imm->i6mm_maddr =
2091                      in6_addmulti(&mreq->ipv6mr_multiaddr, ifp, &error)) == NULL) {
2092                         free(imm, M_IPMADDR);
2093                         break;
2094                 }
2095                 LIST_INSERT_HEAD(&im6o->im6o_memberships, imm, i6mm_chain);
2096                 break;
2097
2098         case IPV6_LEAVE_GROUP:
2099                 /*
2100                  * Drop a multicast group membership.
2101                  * Group must be a valid IP6 multicast address.
2102                  */
2103                 if (m == NULL || m->m_len != sizeof(struct ipv6_mreq)) {
2104                         error = EINVAL;
2105                         break;
2106                 }
2107                 mreq = mtod(m, struct ipv6_mreq *);
2108                 if (IN6_IS_ADDR_UNSPECIFIED(&mreq->ipv6mr_multiaddr)) {
2109                         if (suser(td)) {
2110                                 error = EACCES;
2111                                 break;
2112                         }
2113                 } else if (!IN6_IS_ADDR_MULTICAST(&mreq->ipv6mr_multiaddr)) {
2114                         error = EINVAL;
2115                         break;
2116                 }
2117                 /*
2118                  * If an interface address was specified, get a pointer
2119                  * to its ifnet structure.
2120                  */
2121                 if (mreq->ipv6mr_interface < 0
2122                  || if_index < mreq->ipv6mr_interface) {
2123                         error = ENXIO;  /* XXX EINVAL? */
2124                         break;
2125                 }
2126                 ifp = ifindex2ifnet[mreq->ipv6mr_interface];
2127                 /*
2128                  * Put interface index into the multicast address,
2129                  * if the address has link-local scope.
2130                  */
2131                 if (IN6_IS_ADDR_MC_LINKLOCAL(&mreq->ipv6mr_multiaddr)) {
2132                         mreq->ipv6mr_multiaddr.s6_addr16[1]
2133                                 = htons(mreq->ipv6mr_interface);
2134                 }
2135                 /*
2136                  * Find the membership in the membership list.
2137                  */
2138                 for (imm = im6o->im6o_memberships.lh_first;
2139                      imm != NULL; imm = imm->i6mm_chain.le_next) {
2140                         if ((ifp == NULL ||
2141                              imm->i6mm_maddr->in6m_ifp == ifp) &&
2142                             IN6_ARE_ADDR_EQUAL(&imm->i6mm_maddr->in6m_addr,
2143                                                &mreq->ipv6mr_multiaddr))
2144                                 break;
2145                 }
2146                 if (imm == NULL) {
2147                         /* Unable to resolve interface */
2148                         error = EADDRNOTAVAIL;
2149                         break;
2150                 }
2151                 /*
2152                  * Give up the multicast address record to which the
2153                  * membership points.
2154                  */
2155                 LIST_REMOVE(imm, i6mm_chain);
2156                 in6_delmulti(imm->i6mm_maddr);
2157                 free(imm, M_IPMADDR);
2158                 break;
2159
2160         default:
2161                 error = EOPNOTSUPP;
2162                 break;
2163         }
2164
2165         /*
2166          * If all options have default values, no need to keep the mbuf.
2167          */
2168         if (im6o->im6o_multicast_ifp == NULL &&
2169             im6o->im6o_multicast_hlim == ip6_defmcasthlim &&
2170             im6o->im6o_multicast_loop == IPV6_DEFAULT_MULTICAST_LOOP &&
2171             im6o->im6o_memberships.lh_first == NULL) {
2172                 free(*im6op, M_IPMOPTS);
2173                 *im6op = NULL;
2174         }
2175
2176         return(error);
2177 }
2178
2179 /*
2180  * Return the IP6 multicast options in response to user getsockopt().
2181  */
2182 static int
2183 ip6_getmoptions(int optname, struct ip6_moptions *im6o, struct mbuf **mp)
2184 {
2185         u_int *hlim, *loop, *ifindex;
2186
2187         *mp = m_get(MB_WAIT, MT_HEADER);                /* XXX */
2188
2189         switch (optname) {
2190
2191         case IPV6_MULTICAST_IF:
2192                 ifindex = mtod(*mp, u_int *);
2193                 (*mp)->m_len = sizeof(u_int);
2194                 if (im6o == NULL || im6o->im6o_multicast_ifp == NULL)
2195                         *ifindex = 0;
2196                 else
2197                         *ifindex = im6o->im6o_multicast_ifp->if_index;
2198                 return(0);
2199
2200         case IPV6_MULTICAST_HOPS:
2201                 hlim = mtod(*mp, u_int *);
2202                 (*mp)->m_len = sizeof(u_int);
2203                 if (im6o == NULL)
2204                         *hlim = ip6_defmcasthlim;
2205                 else
2206                         *hlim = im6o->im6o_multicast_hlim;
2207                 return(0);
2208
2209         case IPV6_MULTICAST_LOOP:
2210                 loop = mtod(*mp, u_int *);
2211                 (*mp)->m_len = sizeof(u_int);
2212                 if (im6o == NULL)
2213                         *loop = ip6_defmcasthlim;
2214                 else
2215                         *loop = im6o->im6o_multicast_loop;
2216                 return(0);
2217
2218         default:
2219                 return(EOPNOTSUPP);
2220         }
2221 }
2222
2223 /*
2224  * Discard the IP6 multicast options.
2225  */
2226 void
2227 ip6_freemoptions(struct ip6_moptions *im6o)
2228 {
2229         struct in6_multi_mship *imm;
2230
2231         if (im6o == NULL)
2232                 return;
2233
2234         while ((imm = im6o->im6o_memberships.lh_first) != NULL) {
2235                 LIST_REMOVE(imm, i6mm_chain);
2236                 if (imm->i6mm_maddr)
2237                         in6_delmulti(imm->i6mm_maddr);
2238                 free(imm, M_IPMADDR);
2239         }
2240         free(im6o, M_IPMOPTS);
2241 }
2242
2243 /*
2244  * Set IPv6 outgoing packet options based on advanced API.
2245  */
2246 int
2247 ip6_setpktoptions(struct mbuf *control, struct ip6_pktopts *opt, int priv,
2248                   int needcopy)
2249 {
2250         struct cmsghdr *cm = 0;
2251
2252         if (control == 0 || opt == 0)
2253                 return(EINVAL);
2254
2255         init_ip6pktopts(opt);
2256
2257         /*
2258          * XXX: Currently, we assume all the optional information is stored
2259          * in a single mbuf.
2260          */
2261         if (control->m_next)
2262                 return(EINVAL);
2263
2264         for (; control->m_len; control->m_data += CMSG_ALIGN(cm->cmsg_len),
2265                      control->m_len -= CMSG_ALIGN(cm->cmsg_len)) {
2266                 cm = mtod(control, struct cmsghdr *);
2267                 if (cm->cmsg_len == 0 || cm->cmsg_len > control->m_len)
2268                         return(EINVAL);
2269                 if (cm->cmsg_level != IPPROTO_IPV6)
2270                         continue;
2271
2272                 /*
2273                  * XXX should check if RFC2292 API is mixed with 2292bis API
2274                  */
2275                 switch (cm->cmsg_type) {
2276                 case IPV6_PKTINFO:
2277                         if (cm->cmsg_len != CMSG_LEN(sizeof(struct in6_pktinfo)))
2278                                 return(EINVAL);
2279                         if (needcopy) {
2280                                 /* XXX: Is it really WAITOK? */
2281                                 opt->ip6po_pktinfo =
2282                                         malloc(sizeof(struct in6_pktinfo),
2283                                                M_IP6OPT, M_WAITOK);
2284                                 bcopy(CMSG_DATA(cm), opt->ip6po_pktinfo,
2285                                     sizeof(struct in6_pktinfo));
2286                         } else
2287                                 opt->ip6po_pktinfo =
2288                                         (struct in6_pktinfo *)CMSG_DATA(cm);
2289                         if (opt->ip6po_pktinfo->ipi6_ifindex &&
2290                             IN6_IS_ADDR_LINKLOCAL(&opt->ip6po_pktinfo->ipi6_addr))
2291                                 opt->ip6po_pktinfo->ipi6_addr.s6_addr16[1] =
2292                                         htons(opt->ip6po_pktinfo->ipi6_ifindex);
2293
2294                         if (opt->ip6po_pktinfo->ipi6_ifindex > if_index
2295                          || opt->ip6po_pktinfo->ipi6_ifindex < 0) {
2296                                 return(ENXIO);
2297                         }
2298
2299                         /*
2300                          * Check if the requested source address is indeed a
2301                          * unicast address assigned to the node, and can be
2302                          * used as the packet's source address.
2303                          */
2304                         if (!IN6_IS_ADDR_UNSPECIFIED(&opt->ip6po_pktinfo->ipi6_addr)) {
2305                                 struct in6_ifaddr *ia6;
2306                                 struct sockaddr_in6 sin6;
2307
2308                                 bzero(&sin6, sizeof(sin6));
2309                                 sin6.sin6_len = sizeof(sin6);
2310                                 sin6.sin6_family = AF_INET6;
2311                                 sin6.sin6_addr =
2312                                         opt->ip6po_pktinfo->ipi6_addr;
2313                                 ia6 = (struct in6_ifaddr *)ifa_ifwithaddr(sin6tosa(&sin6));
2314                                 if (ia6 == NULL ||
2315                                     (ia6->ia6_flags & (IN6_IFF_ANYCAST |
2316                                                        IN6_IFF_NOTREADY)) != 0)
2317                                         return(EADDRNOTAVAIL);
2318                         }
2319                         break;
2320
2321                 case IPV6_HOPLIMIT:
2322                         if (cm->cmsg_len != CMSG_LEN(sizeof(int)))
2323                                 return(EINVAL);
2324
2325                         opt->ip6po_hlim = *(int *)CMSG_DATA(cm);
2326                         if (opt->ip6po_hlim < -1 || opt->ip6po_hlim > 255)
2327                                 return(EINVAL);
2328                         break;
2329
2330                 case IPV6_NEXTHOP:
2331                         if (!priv)
2332                                 return(EPERM);
2333
2334                         if (cm->cmsg_len < sizeof(u_char) ||
2335                             /* check if cmsg_len is large enough for sa_len */
2336                             cm->cmsg_len < CMSG_LEN(*CMSG_DATA(cm)))
2337                                 return(EINVAL);
2338
2339                         if (needcopy) {
2340                                 opt->ip6po_nexthop =
2341                                         malloc(*CMSG_DATA(cm),
2342                                                M_IP6OPT, M_WAITOK);
2343                                 bcopy(CMSG_DATA(cm),
2344                                       opt->ip6po_nexthop,
2345                                       *CMSG_DATA(cm));
2346                         } else
2347                                 opt->ip6po_nexthop =
2348                                         (struct sockaddr *)CMSG_DATA(cm);
2349                         break;
2350
2351                 case IPV6_HOPOPTS:
2352                 {
2353                         struct ip6_hbh *hbh;
2354                         int hbhlen;
2355
2356                         if (cm->cmsg_len < CMSG_LEN(sizeof(struct ip6_hbh)))
2357                                 return(EINVAL);
2358                         hbh = (struct ip6_hbh *)CMSG_DATA(cm);
2359                         hbhlen = (hbh->ip6h_len + 1) << 3;
2360                         if (cm->cmsg_len != CMSG_LEN(hbhlen))
2361                                 return(EINVAL);
2362
2363                         if (needcopy) {
2364                                 opt->ip6po_hbh =
2365                                         malloc(hbhlen, M_IP6OPT, M_WAITOK);
2366                                 bcopy(hbh, opt->ip6po_hbh, hbhlen);
2367                         } else
2368                                 opt->ip6po_hbh = hbh;
2369                         break;
2370                 }
2371
2372                 case IPV6_DSTOPTS:
2373                 {
2374                         struct ip6_dest *dest, **newdest;
2375                         int destlen;
2376
2377                         if (cm->cmsg_len < CMSG_LEN(sizeof(struct ip6_dest)))
2378                                 return(EINVAL);
2379                         dest = (struct ip6_dest *)CMSG_DATA(cm);
2380                         destlen = (dest->ip6d_len + 1) << 3;
2381                         if (cm->cmsg_len != CMSG_LEN(destlen))
2382                                 return(EINVAL);
2383
2384                         /* 
2385                          * The old advacned API is ambiguous on this
2386                          * point. Our approach is to determine the
2387                          * position based according to the existence
2388                          * of a routing header. Note, however, that
2389                          * this depends on the order of the extension
2390                          * headers in the ancillary data; the 1st part
2391                          * of the destination options header must
2392                          * appear before the routing header in the
2393                          * ancillary data, too.
2394                          * RFC2292bis solved the ambiguity by
2395                          * introducing separate cmsg types.
2396                          */
2397                         if (opt->ip6po_rthdr == NULL)
2398                                 newdest = &opt->ip6po_dest1;
2399                         else
2400                                 newdest = &opt->ip6po_dest2;
2401
2402                         if (needcopy) {
2403                                 *newdest = malloc(destlen, M_IP6OPT, M_WAITOK);
2404                                 bcopy(dest, *newdest, destlen);
2405                         } else
2406                                 *newdest = dest;
2407
2408                         break;
2409                 }
2410
2411                 case IPV6_RTHDR:
2412                 {
2413                         struct ip6_rthdr *rth;
2414                         int rthlen;
2415
2416                         if (cm->cmsg_len < CMSG_LEN(sizeof(struct ip6_rthdr)))
2417                                 return(EINVAL);
2418                         rth = (struct ip6_rthdr *)CMSG_DATA(cm);
2419                         rthlen = (rth->ip6r_len + 1) << 3;
2420                         if (cm->cmsg_len != CMSG_LEN(rthlen))
2421                                 return(EINVAL);
2422
2423                         switch (rth->ip6r_type) {
2424                         case IPV6_RTHDR_TYPE_0:
2425                                 /* must contain one addr */
2426                                 if (rth->ip6r_len == 0)
2427                                         return(EINVAL);
2428                                 /* length must be even */
2429                                 if (rth->ip6r_len % 2)
2430                                         return(EINVAL);
2431                                 if (rth->ip6r_len / 2 != rth->ip6r_segleft)
2432                                         return(EINVAL);
2433                                 break;
2434                         default:
2435                                 return(EINVAL); /* not supported */
2436                         }
2437
2438                         if (needcopy) {
2439                                 opt->ip6po_rthdr = malloc(rthlen, M_IP6OPT,
2440                                                           M_WAITOK);
2441                                 bcopy(rth, opt->ip6po_rthdr, rthlen);
2442                         } else
2443                                 opt->ip6po_rthdr = rth;
2444
2445                         break;
2446                 }
2447
2448                 default:
2449                         return(ENOPROTOOPT);
2450                 }
2451         }
2452
2453         return(0);
2454 }
2455
2456 /*
2457  * Routine called from ip6_output() to loop back a copy of an IP6 multicast
2458  * packet to the input queue of a specified interface.  Note that this
2459  * calls the output routine of the loopback "driver", but with an interface
2460  * pointer that might NOT be &loif -- easier than replicating that code here.
2461  */
2462 void
2463 ip6_mloopback(struct ifnet *ifp, struct mbuf *m, struct sockaddr_in6 *dst)
2464 {
2465         struct mbuf *copym;
2466         struct ip6_hdr *ip6;
2467
2468         copym = m_copy(m, 0, M_COPYALL);
2469         if (copym == NULL)
2470                 return;
2471
2472         /*
2473          * Make sure to deep-copy IPv6 header portion in case the data
2474          * is in an mbuf cluster, so that we can safely override the IPv6
2475          * header portion later.
2476          */
2477         if ((copym->m_flags & M_EXT) != 0 ||
2478             copym->m_len < sizeof(struct ip6_hdr)) {
2479                 copym = m_pullup(copym, sizeof(struct ip6_hdr));
2480                 if (copym == NULL)
2481                         return;
2482         }
2483
2484 #ifdef DIAGNOSTIC
2485         if (copym->m_len < sizeof(*ip6)) {
2486                 m_freem(copym);
2487                 return;
2488         }
2489 #endif
2490
2491         ip6 = mtod(copym, struct ip6_hdr *);
2492         /*
2493          * clear embedded scope identifiers if necessary.
2494          * in6_clearscope will touch the addresses only when necessary.
2495          */
2496         in6_clearscope(&ip6->ip6_src);
2497         in6_clearscope(&ip6->ip6_dst);
2498
2499         if_simloop(ifp, copym, dst->sin6_family, NULL);
2500 }
2501
2502 /*
2503  * Chop IPv6 header off from the payload.
2504  */
2505 static int
2506 ip6_splithdr(struct mbuf *m, struct ip6_exthdrs *exthdrs)
2507 {
2508         struct mbuf *mh;
2509         struct ip6_hdr *ip6;
2510
2511         ip6 = mtod(m, struct ip6_hdr *);
2512         if (m->m_len > sizeof(*ip6)) {
2513                 MGETHDR(mh, MB_DONTWAIT, MT_HEADER);
2514                 if (mh == 0) {
2515                         m_freem(m);
2516                         return ENOBUFS;
2517                 }
2518                 M_MOVE_PKTHDR(mh, m);
2519                 MH_ALIGN(mh, sizeof(*ip6));
2520                 m->m_len -= sizeof(*ip6);
2521                 m->m_data += sizeof(*ip6);
2522                 mh->m_next = m;
2523                 m = mh;
2524                 m->m_len = sizeof(*ip6);
2525                 bcopy((caddr_t)ip6, mtod(m, caddr_t), sizeof(*ip6));
2526         }
2527         exthdrs->ip6e_ip6 = m;
2528         return 0;
2529 }
2530
2531 /*
2532  * Compute IPv6 extension header length.
2533  */
2534 int
2535 ip6_optlen(struct in6pcb *in6p)
2536 {
2537         int len;
2538
2539         if (!in6p->in6p_outputopts)
2540                 return 0;
2541
2542         len = 0;
2543 #define elen(x) \
2544     (((struct ip6_ext *)(x)) ? (((struct ip6_ext *)(x))->ip6e_len + 1) << 3 : 0)
2545
2546         len += elen(in6p->in6p_outputopts->ip6po_hbh);
2547         if (in6p->in6p_outputopts->ip6po_rthdr)
2548                 /* dest1 is valid with rthdr only */
2549                 len += elen(in6p->in6p_outputopts->ip6po_dest1);
2550         len += elen(in6p->in6p_outputopts->ip6po_rthdr);
2551         len += elen(in6p->in6p_outputopts->ip6po_dest2);
2552         return len;
2553 #undef elen
2554 }