ip_output.c revision 1.74.4.2 1 /* $NetBSD: ip_output.c,v 1.74.4.2 2002/01/14 15:44:38 he Exp $ */
2
3 /*
4 * Copyright (C) 1995, 1996, 1997, and 1998 WIDE Project.
5 * All rights reserved.
6 *
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
9 * are met:
10 * 1. Redistributions of source code must retain the above copyright
11 * notice, this list of conditions and the following disclaimer.
12 * 2. Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 * 3. Neither the name of the project nor the names of its contributors
16 * may be used to endorse or promote products derived from this software
17 * without specific prior written permission.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND
20 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE
23 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
24 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
25 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
26 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
27 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
28 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
29 * SUCH DAMAGE.
30 */
31
32 /*-
33 * Copyright (c) 1998 The NetBSD Foundation, Inc.
34 * All rights reserved.
35 *
36 * This code is derived from software contributed to The NetBSD Foundation
37 * by Public Access Networks Corporation ("Panix"). It was developed under
38 * contract to Panix by Eric Haszlakiewicz and Thor Lancelot Simon.
39 *
40 * Redistribution and use in source and binary forms, with or without
41 * modification, are permitted provided that the following conditions
42 * are met:
43 * 1. Redistributions of source code must retain the above copyright
44 * notice, this list of conditions and the following disclaimer.
45 * 2. Redistributions in binary form must reproduce the above copyright
46 * notice, this list of conditions and the following disclaimer in the
47 * documentation and/or other materials provided with the distribution.
48 * 3. All advertising materials mentioning features or use of this software
49 * must display the following acknowledgement:
50 * This product includes software developed by the NetBSD
51 * Foundation, Inc. and its contributors.
52 * 4. Neither the name of The NetBSD Foundation nor the names of its
53 * contributors may be used to endorse or promote products derived
54 * from this software without specific prior written permission.
55 *
56 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
57 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
58 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
59 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
60 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
61 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
62 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
63 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
64 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
65 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
66 * POSSIBILITY OF SUCH DAMAGE.
67 */
68
69 /*
70 * Copyright (c) 1982, 1986, 1988, 1990, 1993
71 * The Regents of the University of California. All rights reserved.
72 *
73 * Redistribution and use in source and binary forms, with or without
74 * modification, are permitted provided that the following conditions
75 * are met:
76 * 1. Redistributions of source code must retain the above copyright
77 * notice, this list of conditions and the following disclaimer.
78 * 2. Redistributions in binary form must reproduce the above copyright
79 * notice, this list of conditions and the following disclaimer in the
80 * documentation and/or other materials provided with the distribution.
81 * 3. All advertising materials mentioning features or use of this software
82 * must display the following acknowledgement:
83 * This product includes software developed by the University of
84 * California, Berkeley and its contributors.
85 * 4. Neither the name of the University nor the names of its contributors
86 * may be used to endorse or promote products derived from this software
87 * without specific prior written permission.
88 *
89 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
90 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
91 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
92 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
93 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
94 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
95 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
96 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
97 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
98 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
99 * SUCH DAMAGE.
100 *
101 * @(#)ip_output.c 8.3 (Berkeley) 1/21/94
102 */
103
104 #include "opt_pfil_hooks.h"
105 #include "opt_ipsec.h"
106 #include "opt_mrouting.h"
107
108 #include <sys/param.h>
109 #include <sys/malloc.h>
110 #include <sys/mbuf.h>
111 #include <sys/errno.h>
112 #include <sys/protosw.h>
113 #include <sys/socket.h>
114 #include <sys/socketvar.h>
115 #include <sys/systm.h>
116
117 #include <vm/vm.h>
118 #include <sys/proc.h>
119
120 #include <net/if.h>
121 #include <net/route.h>
122 #include <net/pfil.h>
123
124 #include <netinet/in.h>
125 #include <netinet/in_systm.h>
126 #include <netinet/ip.h>
127 #include <netinet/in_pcb.h>
128 #include <netinet/in_var.h>
129 #include <netinet/ip_var.h>
130
131 #ifdef MROUTING
132 #include <netinet/ip_mroute.h>
133 #endif
134
135 #ifdef __vax__
136 #include <machine/mtpr.h>
137 #endif
138
139 #include <machine/stdarg.h>
140
141 #ifdef IPSEC
142 #include <netinet6/ipsec.h>
143 #include <netkey/key.h>
144 #include <netkey/key_debug.h>
145 #endif /*IPSEC*/
146
147 static struct mbuf *ip_insertoptions __P((struct mbuf *, struct mbuf *, int *));
148 static void ip_mloopback
149 __P((struct ifnet *, struct mbuf *, struct sockaddr_in *));
150
151 /*
152 * IP output. The packet in mbuf chain m contains a skeletal IP
153 * header (with len, off, ttl, proto, tos, src, dst).
154 * The mbuf chain containing the packet will be freed.
155 * The mbuf opt, if present, will not be freed.
156 */
157 int
158 #if __STDC__
159 ip_output(struct mbuf *m0, ...)
160 #else
161 ip_output(m0, va_alist)
162 struct mbuf *m0;
163 va_dcl
164 #endif
165 {
166 struct ip *ip, *mhip;
167 struct ifnet *ifp;
168 struct mbuf *m = m0;
169 int hlen = sizeof (struct ip);
170 int len, off, error = 0;
171 struct route iproute;
172 struct sockaddr_in *dst;
173 #if IFA_STATS
174 struct sockaddr_in src;
175 #endif
176 struct in_ifaddr *ia;
177 struct mbuf *opt;
178 struct route *ro;
179 int flags;
180 int *mtu_p;
181 int mtu;
182 struct ip_moptions *imo;
183 va_list ap;
184 #ifdef PFIL_HOOKS
185 struct packet_filter_hook *pfh;
186 struct mbuf *m1;
187 int rv;
188 #endif /* PFIL_HOOKS */
189 #ifdef IPSEC
190 struct socket *so;
191 struct secpolicy *sp = NULL;
192 #endif /*IPSEC*/
193
194 va_start(ap, m0);
195 opt = va_arg(ap, struct mbuf *);
196 ro = va_arg(ap, struct route *);
197 flags = va_arg(ap, int);
198 imo = va_arg(ap, struct ip_moptions *);
199 if (flags & IP_RETURNMTU)
200 mtu_p = va_arg(ap, int *);
201 else
202 mtu_p = NULL;
203 va_end(ap);
204
205 #ifdef IPSEC
206 so = ipsec_getsocket(m);
207 (void)ipsec_setsocket(m, NULL);
208 #endif /*IPSEC*/
209
210 #ifdef DIAGNOSTIC
211 if ((m->m_flags & M_PKTHDR) == 0)
212 panic("ip_output no HDR");
213 #endif
214 if (opt) {
215 m = ip_insertoptions(m, opt, &len);
216 hlen = len;
217 }
218 ip = mtod(m, struct ip *);
219 /*
220 * Fill in IP header.
221 */
222 if ((flags & (IP_FORWARDING|IP_RAWOUTPUT)) == 0) {
223 ip->ip_v = IPVERSION;
224 ip->ip_off &= IP_DF;
225 ip->ip_id = htons(ip_id++);
226 ip->ip_hl = hlen >> 2;
227 ipstat.ips_localout++;
228 } else {
229 hlen = ip->ip_hl << 2;
230 }
231 /*
232 * Route packet.
233 */
234 if (ro == 0) {
235 ro = &iproute;
236 bzero((caddr_t)ro, sizeof (*ro));
237 }
238 dst = satosin(&ro->ro_dst);
239 /*
240 * If there is a cached route,
241 * check that it is to the same destination
242 * and is still up. If not, free it and try again.
243 */
244 if (ro->ro_rt && ((ro->ro_rt->rt_flags & RTF_UP) == 0 ||
245 !in_hosteq(dst->sin_addr, ip->ip_dst))) {
246 RTFREE(ro->ro_rt);
247 ro->ro_rt = (struct rtentry *)0;
248 }
249 if (ro->ro_rt == 0) {
250 dst->sin_family = AF_INET;
251 dst->sin_len = sizeof(*dst);
252 dst->sin_addr = ip->ip_dst;
253 }
254 /*
255 * If routing to interface only,
256 * short circuit routing lookup.
257 */
258 if (flags & IP_ROUTETOIF) {
259 if ((ia = ifatoia(ifa_ifwithladdr(sintosa(dst)))) == 0) {
260 ipstat.ips_noroute++;
261 error = ENETUNREACH;
262 goto bad;
263 }
264 ifp = ia->ia_ifp;
265 mtu = ifp->if_mtu;
266 ip->ip_ttl = 1;
267 } else {
268 if (ro->ro_rt == 0)
269 rtalloc(ro);
270 if (ro->ro_rt == 0) {
271 ipstat.ips_noroute++;
272 error = EHOSTUNREACH;
273 goto bad;
274 }
275 ia = ifatoia(ro->ro_rt->rt_ifa);
276 ifp = ro->ro_rt->rt_ifp;
277 if ((mtu = ro->ro_rt->rt_rmx.rmx_mtu) == 0)
278 mtu = ifp->if_mtu;
279 ro->ro_rt->rt_use++;
280 if (ro->ro_rt->rt_flags & RTF_GATEWAY)
281 dst = satosin(ro->ro_rt->rt_gateway);
282 }
283 if (IN_MULTICAST(ip->ip_dst.s_addr) ||
284 (ip->ip_dst.s_addr == INADDR_BROADCAST)) {
285 struct in_multi *inm;
286
287 m->m_flags |= (ip->ip_dst.s_addr == INADDR_BROADCAST) ?
288 M_BCAST : M_MCAST;
289 /*
290 * IP destination address is multicast. Make sure "dst"
291 * still points to the address in "ro". (It may have been
292 * changed to point to a gateway address, above.)
293 */
294 dst = satosin(&ro->ro_dst);
295 /*
296 * See if the caller provided any multicast options
297 */
298 if (imo != NULL) {
299 ip->ip_ttl = imo->imo_multicast_ttl;
300 if (imo->imo_multicast_ifp != NULL) {
301 ifp = imo->imo_multicast_ifp;
302 mtu = ifp->if_mtu;
303 }
304 } else
305 ip->ip_ttl = IP_DEFAULT_MULTICAST_TTL;
306 /*
307 * Confirm that the outgoing interface supports multicast.
308 */
309 if (((m->m_flags & M_MCAST) &&
310 (ifp->if_flags & IFF_MULTICAST) == 0) ||
311 ((m->m_flags & M_BCAST) &&
312 (ifp->if_flags & IFF_BROADCAST) == 0)) {
313 ipstat.ips_noroute++;
314 error = ENETUNREACH;
315 goto bad;
316 }
317 /*
318 * If source address not specified yet, use an address
319 * of outgoing interface.
320 */
321 if (in_nullhost(ip->ip_src)) {
322 struct in_ifaddr *ia;
323
324 IFP_TO_IA(ifp, ia);
325 if (!ia) {
326 error = EADDRNOTAVAIL;
327 goto bad;
328 }
329 ip->ip_src = ia->ia_addr.sin_addr;
330 }
331
332 IN_LOOKUP_MULTI(ip->ip_dst, ifp, inm);
333 if (inm != NULL &&
334 (imo == NULL || imo->imo_multicast_loop)) {
335 /*
336 * If we belong to the destination multicast group
337 * on the outgoing interface, and the caller did not
338 * forbid loopback, loop back a copy.
339 */
340 ip_mloopback(ifp, m, dst);
341 }
342 #ifdef MROUTING
343 else {
344 /*
345 * If we are acting as a multicast router, perform
346 * multicast forwarding as if the packet had just
347 * arrived on the interface to which we are about
348 * to send. The multicast forwarding function
349 * recursively calls this function, using the
350 * IP_FORWARDING flag to prevent infinite recursion.
351 *
352 * Multicasts that are looped back by ip_mloopback(),
353 * above, will be forwarded by the ip_input() routine,
354 * if necessary.
355 */
356 extern struct socket *ip_mrouter;
357
358 if (ip_mrouter && (flags & IP_FORWARDING) == 0) {
359 if (ip_mforward(m, ifp) != 0) {
360 m_freem(m);
361 goto done;
362 }
363 }
364 }
365 #endif
366 /*
367 * Multicasts with a time-to-live of zero may be looped-
368 * back, above, but must not be transmitted on a network.
369 * Also, multicasts addressed to the loopback interface
370 * are not sent -- the above call to ip_mloopback() will
371 * loop back a copy if this host actually belongs to the
372 * destination group on the loopback interface.
373 */
374 if (ip->ip_ttl == 0 || (ifp->if_flags & IFF_LOOPBACK) != 0) {
375 m_freem(m);
376 goto done;
377 }
378
379 goto sendit;
380 }
381 #ifndef notdef
382 /*
383 * If source address not specified yet, use address
384 * of outgoing interface.
385 */
386 if (in_nullhost(ip->ip_src))
387 ip->ip_src = ia->ia_addr.sin_addr;
388 #endif
389
390 /*
391 * packets with Class-D address as source are not valid per
392 * RFC 1112
393 */
394 if (IN_MULTICAST(ip->ip_src.s_addr)) {
395 ipstat.ips_odropped++;
396 error = EADDRNOTAVAIL;
397 goto bad;
398 }
399
400 /*
401 * Look for broadcast address and
402 * and verify user is allowed to send
403 * such a packet.
404 */
405 if (in_broadcast(dst->sin_addr, ifp)) {
406 if ((ifp->if_flags & IFF_BROADCAST) == 0) {
407 error = EADDRNOTAVAIL;
408 goto bad;
409 }
410 if ((flags & IP_ALLOWBROADCAST) == 0) {
411 error = EACCES;
412 goto bad;
413 }
414 /* don't allow broadcast messages to be fragmented */
415 if ((u_int16_t)ip->ip_len > ifp->if_mtu) {
416 error = EMSGSIZE;
417 goto bad;
418 }
419 m->m_flags |= M_BCAST;
420 } else
421 m->m_flags &= ~M_BCAST;
422
423 sendit:
424
425 #ifdef IPSEC
426 /* get SP for this packet */
427 if (so == NULL)
428 sp = ipsec4_getpolicybyaddr(m, IPSEC_DIR_OUTBOUND, flags, &error);
429 else
430 sp = ipsec4_getpolicybysock(m, IPSEC_DIR_OUTBOUND, so, &error);
431
432 if (sp == NULL) {
433 ipsecstat.out_inval++;
434 goto bad;
435 }
436
437 error = 0;
438
439 /* check policy */
440 switch (sp->policy) {
441 case IPSEC_POLICY_DISCARD:
442 /*
443 * This packet is just discarded.
444 */
445 ipsecstat.out_polvio++;
446 goto bad;
447
448 case IPSEC_POLICY_BYPASS:
449 case IPSEC_POLICY_NONE:
450 /* no need to do IPsec. */
451 goto skip_ipsec;
452
453 case IPSEC_POLICY_IPSEC:
454 if (sp->req == NULL) {
455 /* XXX should be panic ? */
456 printf("ip_output: No IPsec request specified.\n");
457 error = EINVAL;
458 goto bad;
459 }
460 break;
461
462 case IPSEC_POLICY_ENTRUST:
463 default:
464 printf("ip_output: Invalid policy found. %d\n", sp->policy);
465 }
466
467 ip->ip_len = htons((u_short)ip->ip_len);
468 ip->ip_off = htons((u_short)ip->ip_off);
469 ip->ip_sum = 0;
470
471 {
472 struct ipsec_output_state state;
473 bzero(&state, sizeof(state));
474 state.m = m;
475 if (flags & IP_ROUTETOIF) {
476 state.ro = &iproute;
477 bzero(&iproute, sizeof(iproute));
478 } else
479 state.ro = ro;
480 state.dst = (struct sockaddr *)dst;
481
482 error = ipsec4_output(&state, sp, flags);
483
484 m = state.m;
485 if (flags & IP_ROUTETOIF) {
486 /*
487 * if we have tunnel mode SA, we may need to ignore
488 * IP_ROUTETOIF.
489 */
490 if (state.ro != &iproute || state.ro->ro_rt != NULL) {
491 flags &= ~IP_ROUTETOIF;
492 ro = state.ro;
493 }
494 } else
495 ro = state.ro;
496 dst = (struct sockaddr_in *)state.dst;
497 if (error) {
498 /* mbuf is already reclaimed in ipsec4_output. */
499 m0 = NULL;
500 switch (error) {
501 case EHOSTUNREACH:
502 case ENETUNREACH:
503 case EMSGSIZE:
504 case ENOBUFS:
505 case ENOMEM:
506 break;
507 default:
508 printf("ip4_output (ipsec): error code %d\n", error);
509 /*fall through*/
510 case ENOENT:
511 /* don't show these error codes to the user */
512 error = 0;
513 break;
514 }
515 goto bad;
516 }
517 }
518
519 /* be sure to update variables that are affected by ipsec4_output() */
520 ip = mtod(m, struct ip *);
521 #ifdef _IP_VHL
522 hlen = IP_VHL_HL(ip->ip_vhl) << 2;
523 #else
524 hlen = ip->ip_hl << 2;
525 #endif
526 if (ro->ro_rt == NULL) {
527 if ((flags & IP_ROUTETOIF) == 0) {
528 printf("ip_output: "
529 "can't update route after IPsec processing\n");
530 error = EHOSTUNREACH; /*XXX*/
531 goto bad;
532 }
533 } else {
534 /* nobody uses ia beyond here */
535 ifp = ro->ro_rt->rt_ifp;
536 }
537
538 /* make it flipped, again. */
539 ip->ip_len = ntohs((u_short)ip->ip_len);
540 ip->ip_off = ntohs((u_short)ip->ip_off);
541 skip_ipsec:
542 #endif /*IPSEC*/
543
544 #ifdef PFIL_HOOKS
545 /*
546 * Run through list of hooks for output packets.
547 */
548 m1 = m;
549 pfh = pfil_hook_get(PFIL_OUT, &inetsw[ip_protox[IPPROTO_IP]].pr_pfh);
550 for (; pfh; pfh = pfh->pfil_link.tqe_next)
551 if (pfh->pfil_func) {
552 rv = pfh->pfil_func(ip, hlen, ifp, 1, &m1);
553 if (rv) {
554 error = EHOSTUNREACH;
555 goto done;
556 }
557 m = m1;
558 if (m == NULL)
559 goto done;
560 ip = mtod(m, struct ip *);
561 }
562 #endif /* PFIL_HOOKS */
563
564 /*
565 * If small enough for mtu of path, can just send directly.
566 */
567 if ((u_int16_t)ip->ip_len <= mtu) {
568 #if IFA_STATS
569 /*
570 * search for the source address structure to
571 * maintain output statistics.
572 */
573 bzero((caddr_t*) &src, sizeof(src));
574 src.sin_family = AF_INET;
575 src.sin_addr.s_addr = ip->ip_src.s_addr;
576 src.sin_len = sizeof(src);
577 ia = ifatoia(ifa_ifwithladdr(sintosa(&src)));
578 if (ia)
579 ia->ia_ifa.ifa_data.ifad_outbytes += ntohs(ip->ip_len);
580 #endif
581 HTONS(ip->ip_len);
582 HTONS(ip->ip_off);
583 ip->ip_sum = 0;
584 ip->ip_sum = in_cksum(m, hlen);
585 #ifdef IPSEC
586 /* clean ipsec history once it goes out of the node */
587 ipsec_delaux(m);
588 #endif
589 error = (*ifp->if_output)(ifp, m, sintosa(dst), ro->ro_rt);
590 goto done;
591 }
592
593 /*
594 * Too large for interface; fragment if possible.
595 * Must be able to put at least 8 bytes per fragment.
596 */
597 #if 0
598 /*
599 * If IPsec packet is too big for the interface, try fragment it.
600 * XXX This really is a quickhack. May be inappropriate.
601 * XXX fails if somebody is sending AH'ed packet, with:
602 * sizeof(packet without AH) < mtu < sizeof(packet with AH)
603 */
604 if (sab && ip->ip_p != IPPROTO_AH && (flags & IP_FORWARDING) == 0)
605 ip->ip_off &= ~IP_DF;
606 #endif /*IPSEC*/
607 if (ip->ip_off & IP_DF) {
608 if (flags & IP_RETURNMTU)
609 *mtu_p = mtu;
610 error = EMSGSIZE;
611 ipstat.ips_cantfrag++;
612 goto bad;
613 }
614 len = (mtu - hlen) &~ 7;
615 if (len < 8) {
616 error = EMSGSIZE;
617 goto bad;
618 }
619
620 {
621 int mhlen, firstlen = len;
622 struct mbuf **mnext = &m->m_nextpkt;
623 int fragments = 0;
624 int s;
625
626 /*
627 * Loop through length of segment after first fragment,
628 * make new header and copy data of each part and link onto chain.
629 */
630 m0 = m;
631 mhlen = sizeof (struct ip);
632 for (off = hlen + len; off < (u_int16_t)ip->ip_len; off += len) {
633 MGETHDR(m, M_DONTWAIT, MT_HEADER);
634 if (m == 0) {
635 error = ENOBUFS;
636 ipstat.ips_odropped++;
637 goto sendorfree;
638 }
639 *mnext = m;
640 mnext = &m->m_nextpkt;
641 m->m_data += max_linkhdr;
642 mhip = mtod(m, struct ip *);
643 *mhip = *ip;
644 /* we must inherit MCAST and BCAST flags */
645 m->m_flags |= m0->m_flags & (M_MCAST|M_BCAST);
646 if (hlen > sizeof (struct ip)) {
647 mhlen = ip_optcopy(ip, mhip) + sizeof (struct ip);
648 mhip->ip_hl = mhlen >> 2;
649 }
650 m->m_len = mhlen;
651 mhip->ip_off = ((off - hlen) >> 3) + (ip->ip_off & ~IP_MF);
652 if (ip->ip_off & IP_MF)
653 mhip->ip_off |= IP_MF;
654 if (off + len >= (u_int16_t)ip->ip_len)
655 len = (u_int16_t)ip->ip_len - off;
656 else
657 mhip->ip_off |= IP_MF;
658 mhip->ip_len = htons((u_int16_t)(len + mhlen));
659 m->m_next = m_copy(m0, off, len);
660 if (m->m_next == 0) {
661 error = ENOBUFS; /* ??? */
662 ipstat.ips_odropped++;
663 goto sendorfree;
664 }
665 m->m_pkthdr.len = mhlen + len;
666 m->m_pkthdr.rcvif = (struct ifnet *)0;
667 HTONS(mhip->ip_off);
668 mhip->ip_sum = 0;
669 mhip->ip_sum = in_cksum(m, mhlen);
670 ipstat.ips_ofragments++;
671 fragments++;
672 }
673 /*
674 * Update first fragment by trimming what's been copied out
675 * and updating header, then send each fragment (in order).
676 */
677 m = m0;
678 m_adj(m, hlen + firstlen - (u_int16_t)ip->ip_len);
679 m->m_pkthdr.len = hlen + firstlen;
680 ip->ip_len = htons((u_int16_t)m->m_pkthdr.len);
681 ip->ip_off |= IP_MF;
682 HTONS(ip->ip_off);
683 ip->ip_sum = 0;
684 ip->ip_sum = in_cksum(m, hlen);
685 sendorfree:
686 /*
687 * If there is no room for all the fragments, don't queue
688 * any of them.
689 */
690 s = splimp();
691 if (ifp->if_snd.ifq_maxlen - ifp->if_snd.ifq_len < fragments)
692 error = ENOBUFS;
693 splx(s);
694 for (m = m0; m; m = m0) {
695 m0 = m->m_nextpkt;
696 m->m_nextpkt = 0;
697 if (error == 0) {
698 #if IFA_STATS
699 /*
700 * search for the source address structure to
701 * maintain output statistics.
702 */
703 bzero((caddr_t*) &src, sizeof(src));
704 src.sin_family = AF_INET;
705 src.sin_addr.s_addr = ip->ip_src.s_addr;
706 src.sin_len = sizeof(src);
707 ia = ifatoia(ifa_ifwithladdr(sintosa(&src)));
708 if (ia) {
709 ia->ia_ifa.ifa_data.ifad_outbytes +=
710 ntohs(ip->ip_len);
711 }
712 #endif
713 #ifdef IPSEC
714 /* clean ipsec history once it goes out of the node */
715 ipsec_delaux(m);
716 #endif
717 error = (*ifp->if_output)(ifp, m, sintosa(dst),
718 ro->ro_rt);
719 } else
720 m_freem(m);
721 }
722
723 if (error == 0)
724 ipstat.ips_fragmented++;
725 }
726 done:
727 if (ro == &iproute && (flags & IP_ROUTETOIF) == 0 && ro->ro_rt) {
728 RTFREE(ro->ro_rt);
729 ro->ro_rt = 0;
730 }
731
732 #ifdef IPSEC
733 if (sp != NULL) {
734 KEYDEBUG(KEYDEBUG_IPSEC_STAMP,
735 printf("DP ip_output call free SP:%p\n", sp));
736 key_freesp(sp);
737 }
738 #endif /* IPSEC */
739
740 return (error);
741 bad:
742 m_freem(m);
743 goto done;
744 }
745
746 /*
747 * Determine the maximum length of the options to be inserted;
748 * we would far rather allocate too much space rather than too little.
749 */
750
751 u_int
752 ip_optlen(inp)
753 struct inpcb *inp;
754 {
755 struct mbuf *m = inp->inp_options;
756
757 if (m && m->m_len > offsetof(struct ipoption, ipopt_dst))
758 return(m->m_len - offsetof(struct ipoption, ipopt_dst));
759 else
760 return 0;
761 }
762
763
764 /*
765 * Insert IP options into preformed packet.
766 * Adjust IP destination as required for IP source routing,
767 * as indicated by a non-zero in_addr at the start of the options.
768 */
769 static struct mbuf *
770 ip_insertoptions(m, opt, phlen)
771 struct mbuf *m;
772 struct mbuf *opt;
773 int *phlen;
774 {
775 struct ipoption *p = mtod(opt, struct ipoption *);
776 struct mbuf *n;
777 struct ip *ip = mtod(m, struct ip *);
778 unsigned optlen;
779
780 optlen = opt->m_len - sizeof(p->ipopt_dst);
781 if (optlen + (u_int16_t)ip->ip_len > IP_MAXPACKET)
782 return (m); /* XXX should fail */
783 if (!in_nullhost(p->ipopt_dst))
784 ip->ip_dst = p->ipopt_dst;
785 if (m->m_flags & M_EXT || m->m_data - optlen < m->m_pktdat) {
786 MGETHDR(n, M_DONTWAIT, MT_HEADER);
787 if (n == 0)
788 return (m);
789 n->m_pkthdr.len = m->m_pkthdr.len + optlen;
790 m->m_len -= sizeof(struct ip);
791 m->m_data += sizeof(struct ip);
792 n->m_next = m;
793 m = n;
794 m->m_len = optlen + sizeof(struct ip);
795 m->m_data += max_linkhdr;
796 bcopy((caddr_t)ip, mtod(m, caddr_t), sizeof(struct ip));
797 } else {
798 m->m_data -= optlen;
799 m->m_len += optlen;
800 m->m_pkthdr.len += optlen;
801 memmove(mtod(m, caddr_t), ip, sizeof(struct ip));
802 }
803 ip = mtod(m, struct ip *);
804 bcopy((caddr_t)p->ipopt_list, (caddr_t)(ip + 1), (unsigned)optlen);
805 *phlen = sizeof(struct ip) + optlen;
806 ip->ip_len += optlen;
807 return (m);
808 }
809
810 /*
811 * Copy options from ip to jp,
812 * omitting those not copied during fragmentation.
813 */
814 int
815 ip_optcopy(ip, jp)
816 struct ip *ip, *jp;
817 {
818 u_char *cp, *dp;
819 int opt, optlen, cnt;
820
821 cp = (u_char *)(ip + 1);
822 dp = (u_char *)(jp + 1);
823 cnt = (ip->ip_hl << 2) - sizeof (struct ip);
824 for (; cnt > 0; cnt -= optlen, cp += optlen) {
825 opt = cp[0];
826 if (opt == IPOPT_EOL)
827 break;
828 if (opt == IPOPT_NOP) {
829 /* Preserve for IP mcast tunnel's LSRR alignment. */
830 *dp++ = IPOPT_NOP;
831 optlen = 1;
832 continue;
833 }
834 #ifdef DIAGNOSTIC
835 if (cnt < IPOPT_OLEN + sizeof(*cp))
836 panic("malformed IPv4 option passed to ip_optcopy");
837 #endif
838 optlen = cp[IPOPT_OLEN];
839 #ifdef DIAGNOSTIC
840 if (optlen < IPOPT_OLEN + sizeof(*cp) || optlen > cnt)
841 panic("malformed IPv4 option passed to ip_optcopy");
842 #endif
843 /* bogus lengths should have been caught by ip_dooptions */
844 if (optlen > cnt)
845 optlen = cnt;
846 if (IPOPT_COPIED(opt)) {
847 bcopy((caddr_t)cp, (caddr_t)dp, (unsigned)optlen);
848 dp += optlen;
849 }
850 }
851 for (optlen = dp - (u_char *)(jp+1); optlen & 0x3; optlen++)
852 *dp++ = IPOPT_EOL;
853 return (optlen);
854 }
855
856 /*
857 * IP socket option processing.
858 */
859 int
860 ip_ctloutput(op, so, level, optname, mp)
861 int op;
862 struct socket *so;
863 int level, optname;
864 struct mbuf **mp;
865 {
866 struct inpcb *inp = sotoinpcb(so);
867 struct mbuf *m = *mp;
868 int optval = 0;
869 int error = 0;
870 #ifdef IPSEC
871 #ifdef __NetBSD__
872 struct proc *p = curproc; /*XXX*/
873 #endif
874 #endif
875
876 if (level != IPPROTO_IP) {
877 error = EINVAL;
878 if (op == PRCO_SETOPT && *mp)
879 (void) m_free(*mp);
880 } else switch (op) {
881
882 case PRCO_SETOPT:
883 switch (optname) {
884 case IP_OPTIONS:
885 #ifdef notyet
886 case IP_RETOPTS:
887 return (ip_pcbopts(optname, &inp->inp_options, m));
888 #else
889 return (ip_pcbopts(&inp->inp_options, m));
890 #endif
891
892 case IP_TOS:
893 case IP_TTL:
894 case IP_RECVOPTS:
895 case IP_RECVRETOPTS:
896 case IP_RECVDSTADDR:
897 case IP_RECVIF:
898 if (m == NULL || m->m_len != sizeof(int))
899 error = EINVAL;
900 else {
901 optval = *mtod(m, int *);
902 switch (optname) {
903
904 case IP_TOS:
905 inp->inp_ip.ip_tos = optval;
906 break;
907
908 case IP_TTL:
909 inp->inp_ip.ip_ttl = optval;
910 break;
911 #define OPTSET(bit) \
912 if (optval) \
913 inp->inp_flags |= bit; \
914 else \
915 inp->inp_flags &= ~bit;
916
917 case IP_RECVOPTS:
918 OPTSET(INP_RECVOPTS);
919 break;
920
921 case IP_RECVRETOPTS:
922 OPTSET(INP_RECVRETOPTS);
923 break;
924
925 case IP_RECVDSTADDR:
926 OPTSET(INP_RECVDSTADDR);
927 break;
928
929 case IP_RECVIF:
930 OPTSET(INP_RECVIF);
931 break;
932 }
933 }
934 break;
935 #undef OPTSET
936
937 case IP_MULTICAST_IF:
938 case IP_MULTICAST_TTL:
939 case IP_MULTICAST_LOOP:
940 case IP_ADD_MEMBERSHIP:
941 case IP_DROP_MEMBERSHIP:
942 error = ip_setmoptions(optname, &inp->inp_moptions, m);
943 break;
944
945 case IP_PORTRANGE:
946 if (m == 0 || m->m_len != sizeof(int))
947 error = EINVAL;
948 else {
949 optval = *mtod(m, int *);
950
951 switch (optval) {
952
953 case IP_PORTRANGE_DEFAULT:
954 case IP_PORTRANGE_HIGH:
955 inp->inp_flags &= ~(INP_LOWPORT);
956 break;
957
958 case IP_PORTRANGE_LOW:
959 inp->inp_flags |= INP_LOWPORT;
960 break;
961
962 default:
963 error = EINVAL;
964 break;
965 }
966 }
967 break;
968
969 #ifdef IPSEC
970 case IP_IPSEC_POLICY:
971 {
972 caddr_t req = NULL;
973 size_t len = 0;
974 int priv = 0;
975
976 #ifdef __NetBSD__
977 if (p == 0 || suser(p->p_ucred, &p->p_acflag))
978 priv = 0;
979 else
980 priv = 1;
981 #else
982 priv = (in6p->in6p_socket->so_state & SS_PRIV);
983 #endif
984 if (m) {
985 req = mtod(m, caddr_t);
986 len = m->m_len;
987 }
988 error = ipsec4_set_policy(inp, optname, req, len, priv);
989 break;
990 }
991 #endif /*IPSEC*/
992
993 default:
994 error = ENOPROTOOPT;
995 break;
996 }
997 if (m)
998 (void)m_free(m);
999 break;
1000
1001 case PRCO_GETOPT:
1002 switch (optname) {
1003 case IP_OPTIONS:
1004 case IP_RETOPTS:
1005 *mp = m = m_get(M_WAIT, MT_SOOPTS);
1006 if (inp->inp_options) {
1007 m->m_len = inp->inp_options->m_len;
1008 bcopy(mtod(inp->inp_options, caddr_t),
1009 mtod(m, caddr_t), (unsigned)m->m_len);
1010 } else
1011 m->m_len = 0;
1012 break;
1013
1014 case IP_TOS:
1015 case IP_TTL:
1016 case IP_RECVOPTS:
1017 case IP_RECVRETOPTS:
1018 case IP_RECVDSTADDR:
1019 case IP_RECVIF:
1020 case IP_ERRORMTU:
1021 *mp = m = m_get(M_WAIT, MT_SOOPTS);
1022 m->m_len = sizeof(int);
1023 switch (optname) {
1024
1025 case IP_TOS:
1026 optval = inp->inp_ip.ip_tos;
1027 break;
1028
1029 case IP_TTL:
1030 optval = inp->inp_ip.ip_ttl;
1031 break;
1032
1033 case IP_ERRORMTU:
1034 optval = inp->inp_errormtu;
1035 break;
1036
1037 #define OPTBIT(bit) (inp->inp_flags & bit ? 1 : 0)
1038
1039 case IP_RECVOPTS:
1040 optval = OPTBIT(INP_RECVOPTS);
1041 break;
1042
1043 case IP_RECVRETOPTS:
1044 optval = OPTBIT(INP_RECVRETOPTS);
1045 break;
1046
1047 case IP_RECVDSTADDR:
1048 optval = OPTBIT(INP_RECVDSTADDR);
1049 break;
1050
1051 case IP_RECVIF:
1052 optval = OPTBIT(INP_RECVIF);
1053 break;
1054 }
1055 *mtod(m, int *) = optval;
1056 break;
1057
1058 #ifdef IPSEC
1059 case IP_IPSEC_POLICY:
1060 {
1061 caddr_t req = NULL;
1062 size_t len;
1063
1064 if (m) {
1065 req = mtod(m, caddr_t);
1066 len = m->m_len;
1067 }
1068 error = ipsec4_get_policy(inp, req, len, mp);
1069 break;
1070 }
1071 #endif /*IPSEC*/
1072
1073 case IP_MULTICAST_IF:
1074 case IP_MULTICAST_TTL:
1075 case IP_MULTICAST_LOOP:
1076 case IP_ADD_MEMBERSHIP:
1077 case IP_DROP_MEMBERSHIP:
1078 error = ip_getmoptions(optname, inp->inp_moptions, mp);
1079 break;
1080
1081 case IP_PORTRANGE:
1082 *mp = m = m_get(M_WAIT, MT_SOOPTS);
1083 m->m_len = sizeof(int);
1084
1085 if (inp->inp_flags & INP_LOWPORT)
1086 optval = IP_PORTRANGE_LOW;
1087 else
1088 optval = IP_PORTRANGE_DEFAULT;
1089
1090 *mtod(m, int *) = optval;
1091 break;
1092
1093 default:
1094 error = ENOPROTOOPT;
1095 break;
1096 }
1097 break;
1098 }
1099 return (error);
1100 }
1101
1102 /*
1103 * Set up IP options in pcb for insertion in output packets.
1104 * Store in mbuf with pointer in pcbopt, adding pseudo-option
1105 * with destination address if source routed.
1106 */
1107 int
1108 #ifdef notyet
1109 ip_pcbopts(optname, pcbopt, m)
1110 int optname;
1111 #else
1112 ip_pcbopts(pcbopt, m)
1113 #endif
1114 struct mbuf **pcbopt;
1115 struct mbuf *m;
1116 {
1117 int cnt, optlen;
1118 u_char *cp;
1119 u_char opt;
1120
1121 /* turn off any old options */
1122 if (*pcbopt)
1123 (void)m_free(*pcbopt);
1124 *pcbopt = 0;
1125 if (m == (struct mbuf *)0 || m->m_len == 0) {
1126 /*
1127 * Only turning off any previous options.
1128 */
1129 if (m)
1130 (void)m_free(m);
1131 return (0);
1132 }
1133
1134 #ifndef vax
1135 if (m->m_len % sizeof(int32_t))
1136 goto bad;
1137 #endif
1138 /*
1139 * IP first-hop destination address will be stored before
1140 * actual options; move other options back
1141 * and clear it when none present.
1142 */
1143 if (m->m_data + m->m_len + sizeof(struct in_addr) >= &m->m_dat[MLEN])
1144 goto bad;
1145 cnt = m->m_len;
1146 m->m_len += sizeof(struct in_addr);
1147 cp = mtod(m, u_char *) + sizeof(struct in_addr);
1148 memmove(cp, mtod(m, caddr_t), (unsigned)cnt);
1149 bzero(mtod(m, caddr_t), sizeof(struct in_addr));
1150
1151 for (; cnt > 0; cnt -= optlen, cp += optlen) {
1152 opt = cp[IPOPT_OPTVAL];
1153 if (opt == IPOPT_EOL)
1154 break;
1155 if (opt == IPOPT_NOP)
1156 optlen = 1;
1157 else {
1158 if (cnt < IPOPT_OLEN + sizeof(*cp))
1159 goto bad;
1160 optlen = cp[IPOPT_OLEN];
1161 if (optlen < IPOPT_OLEN + sizeof(*cp) || optlen > cnt)
1162 goto bad;
1163 }
1164 switch (opt) {
1165
1166 default:
1167 break;
1168
1169 case IPOPT_LSRR:
1170 case IPOPT_SSRR:
1171 /*
1172 * user process specifies route as:
1173 * ->A->B->C->D
1174 * D must be our final destination (but we can't
1175 * check that since we may not have connected yet).
1176 * A is first hop destination, which doesn't appear in
1177 * actual IP option, but is stored before the options.
1178 */
1179 if (optlen < IPOPT_MINOFF - 1 + sizeof(struct in_addr))
1180 goto bad;
1181 m->m_len -= sizeof(struct in_addr);
1182 cnt -= sizeof(struct in_addr);
1183 optlen -= sizeof(struct in_addr);
1184 cp[IPOPT_OLEN] = optlen;
1185 /*
1186 * Move first hop before start of options.
1187 */
1188 bcopy((caddr_t)&cp[IPOPT_OFFSET+1], mtod(m, caddr_t),
1189 sizeof(struct in_addr));
1190 /*
1191 * Then copy rest of options back
1192 * to close up the deleted entry.
1193 */
1194 memmove(&cp[IPOPT_OFFSET+1],
1195 (caddr_t)(&cp[IPOPT_OFFSET+1] + sizeof(struct in_addr)),
1196 (unsigned)cnt + sizeof(struct in_addr));
1197 break;
1198 }
1199 }
1200 if (m->m_len > MAX_IPOPTLEN + sizeof(struct in_addr))
1201 goto bad;
1202 *pcbopt = m;
1203 return (0);
1204
1205 bad:
1206 (void)m_free(m);
1207 return (EINVAL);
1208 }
1209
1210 /*
1211 * Set the IP multicast options in response to user setsockopt().
1212 */
1213 int
1214 ip_setmoptions(optname, imop, m)
1215 int optname;
1216 struct ip_moptions **imop;
1217 struct mbuf *m;
1218 {
1219 int error = 0;
1220 u_char loop;
1221 int i;
1222 struct in_addr addr;
1223 struct ip_mreq *mreq;
1224 struct ifnet *ifp;
1225 struct ip_moptions *imo = *imop;
1226 struct route ro;
1227 struct sockaddr_in *dst;
1228
1229 if (imo == NULL) {
1230 /*
1231 * No multicast option buffer attached to the pcb;
1232 * allocate one and initialize to default values.
1233 */
1234 imo = (struct ip_moptions *)malloc(sizeof(*imo), M_IPMOPTS,
1235 M_WAITOK);
1236
1237 if (imo == NULL)
1238 return (ENOBUFS);
1239 *imop = imo;
1240 imo->imo_multicast_ifp = NULL;
1241 imo->imo_multicast_ttl = IP_DEFAULT_MULTICAST_TTL;
1242 imo->imo_multicast_loop = IP_DEFAULT_MULTICAST_LOOP;
1243 imo->imo_num_memberships = 0;
1244 }
1245
1246 switch (optname) {
1247
1248 case IP_MULTICAST_IF:
1249 /*
1250 * Select the interface for outgoing multicast packets.
1251 */
1252 if (m == NULL || m->m_len != sizeof(struct in_addr)) {
1253 error = EINVAL;
1254 break;
1255 }
1256 addr = *(mtod(m, struct in_addr *));
1257 /*
1258 * INADDR_ANY is used to remove a previous selection.
1259 * When no interface is selected, a default one is
1260 * chosen every time a multicast packet is sent.
1261 */
1262 if (in_nullhost(addr)) {
1263 imo->imo_multicast_ifp = NULL;
1264 break;
1265 }
1266 /*
1267 * The selected interface is identified by its local
1268 * IP address. Find the interface and confirm that
1269 * it supports multicasting.
1270 */
1271 INADDR_TO_IFP(addr, ifp);
1272 if (ifp == NULL || (ifp->if_flags & IFF_MULTICAST) == 0) {
1273 error = EADDRNOTAVAIL;
1274 break;
1275 }
1276 imo->imo_multicast_ifp = ifp;
1277 break;
1278
1279 case IP_MULTICAST_TTL:
1280 /*
1281 * Set the IP time-to-live for outgoing multicast packets.
1282 */
1283 if (m == NULL || m->m_len != 1) {
1284 error = EINVAL;
1285 break;
1286 }
1287 imo->imo_multicast_ttl = *(mtod(m, u_char *));
1288 break;
1289
1290 case IP_MULTICAST_LOOP:
1291 /*
1292 * Set the loopback flag for outgoing multicast packets.
1293 * Must be zero or one.
1294 */
1295 if (m == NULL || m->m_len != 1 ||
1296 (loop = *(mtod(m, u_char *))) > 1) {
1297 error = EINVAL;
1298 break;
1299 }
1300 imo->imo_multicast_loop = loop;
1301 break;
1302
1303 case IP_ADD_MEMBERSHIP:
1304 /*
1305 * Add a multicast group membership.
1306 * Group must be a valid IP multicast address.
1307 */
1308 if (m == NULL || m->m_len != sizeof(struct ip_mreq)) {
1309 error = EINVAL;
1310 break;
1311 }
1312 mreq = mtod(m, struct ip_mreq *);
1313 if (!IN_MULTICAST(mreq->imr_multiaddr.s_addr)) {
1314 error = EINVAL;
1315 break;
1316 }
1317 /*
1318 * If no interface address was provided, use the interface of
1319 * the route to the given multicast address.
1320 */
1321 if (in_nullhost(mreq->imr_interface)) {
1322 bzero((caddr_t)&ro, sizeof(ro));
1323 ro.ro_rt = NULL;
1324 dst = satosin(&ro.ro_dst);
1325 dst->sin_len = sizeof(*dst);
1326 dst->sin_family = AF_INET;
1327 dst->sin_addr = mreq->imr_multiaddr;
1328 rtalloc(&ro);
1329 if (ro.ro_rt == NULL) {
1330 error = EADDRNOTAVAIL;
1331 break;
1332 }
1333 ifp = ro.ro_rt->rt_ifp;
1334 rtfree(ro.ro_rt);
1335 } else {
1336 INADDR_TO_IFP(mreq->imr_interface, ifp);
1337 }
1338 /*
1339 * See if we found an interface, and confirm that it
1340 * supports multicast.
1341 */
1342 if (ifp == NULL || (ifp->if_flags & IFF_MULTICAST) == 0) {
1343 error = EADDRNOTAVAIL;
1344 break;
1345 }
1346 /*
1347 * See if the membership already exists or if all the
1348 * membership slots are full.
1349 */
1350 for (i = 0; i < imo->imo_num_memberships; ++i) {
1351 if (imo->imo_membership[i]->inm_ifp == ifp &&
1352 in_hosteq(imo->imo_membership[i]->inm_addr,
1353 mreq->imr_multiaddr))
1354 break;
1355 }
1356 if (i < imo->imo_num_memberships) {
1357 error = EADDRINUSE;
1358 break;
1359 }
1360 if (i == IP_MAX_MEMBERSHIPS) {
1361 error = ETOOMANYREFS;
1362 break;
1363 }
1364 /*
1365 * Everything looks good; add a new record to the multicast
1366 * address list for the given interface.
1367 */
1368 if ((imo->imo_membership[i] =
1369 in_addmulti(&mreq->imr_multiaddr, ifp)) == NULL) {
1370 error = ENOBUFS;
1371 break;
1372 }
1373 ++imo->imo_num_memberships;
1374 break;
1375
1376 case IP_DROP_MEMBERSHIP:
1377 /*
1378 * Drop a multicast group membership.
1379 * Group must be a valid IP multicast address.
1380 */
1381 if (m == NULL || m->m_len != sizeof(struct ip_mreq)) {
1382 error = EINVAL;
1383 break;
1384 }
1385 mreq = mtod(m, struct ip_mreq *);
1386 if (!IN_MULTICAST(mreq->imr_multiaddr.s_addr)) {
1387 error = EINVAL;
1388 break;
1389 }
1390 /*
1391 * If an interface address was specified, get a pointer
1392 * to its ifnet structure.
1393 */
1394 if (in_nullhost(mreq->imr_interface))
1395 ifp = NULL;
1396 else {
1397 INADDR_TO_IFP(mreq->imr_interface, ifp);
1398 if (ifp == NULL) {
1399 error = EADDRNOTAVAIL;
1400 break;
1401 }
1402 }
1403 /*
1404 * Find the membership in the membership array.
1405 */
1406 for (i = 0; i < imo->imo_num_memberships; ++i) {
1407 if ((ifp == NULL ||
1408 imo->imo_membership[i]->inm_ifp == ifp) &&
1409 in_hosteq(imo->imo_membership[i]->inm_addr,
1410 mreq->imr_multiaddr))
1411 break;
1412 }
1413 if (i == imo->imo_num_memberships) {
1414 error = EADDRNOTAVAIL;
1415 break;
1416 }
1417 /*
1418 * Give up the multicast address record to which the
1419 * membership points.
1420 */
1421 in_delmulti(imo->imo_membership[i]);
1422 /*
1423 * Remove the gap in the membership array.
1424 */
1425 for (++i; i < imo->imo_num_memberships; ++i)
1426 imo->imo_membership[i-1] = imo->imo_membership[i];
1427 --imo->imo_num_memberships;
1428 break;
1429
1430 default:
1431 error = EOPNOTSUPP;
1432 break;
1433 }
1434
1435 /*
1436 * If all options have default values, no need to keep the mbuf.
1437 */
1438 if (imo->imo_multicast_ifp == NULL &&
1439 imo->imo_multicast_ttl == IP_DEFAULT_MULTICAST_TTL &&
1440 imo->imo_multicast_loop == IP_DEFAULT_MULTICAST_LOOP &&
1441 imo->imo_num_memberships == 0) {
1442 free(*imop, M_IPMOPTS);
1443 *imop = NULL;
1444 }
1445
1446 return (error);
1447 }
1448
1449 /*
1450 * Return the IP multicast options in response to user getsockopt().
1451 */
1452 int
1453 ip_getmoptions(optname, imo, mp)
1454 int optname;
1455 struct ip_moptions *imo;
1456 struct mbuf **mp;
1457 {
1458 u_char *ttl;
1459 u_char *loop;
1460 struct in_addr *addr;
1461 struct in_ifaddr *ia;
1462
1463 *mp = m_get(M_WAIT, MT_SOOPTS);
1464
1465 switch (optname) {
1466
1467 case IP_MULTICAST_IF:
1468 addr = mtod(*mp, struct in_addr *);
1469 (*mp)->m_len = sizeof(struct in_addr);
1470 if (imo == NULL || imo->imo_multicast_ifp == NULL)
1471 *addr = zeroin_addr;
1472 else {
1473 IFP_TO_IA(imo->imo_multicast_ifp, ia);
1474 *addr = ia ? ia->ia_addr.sin_addr : zeroin_addr;
1475 }
1476 return (0);
1477
1478 case IP_MULTICAST_TTL:
1479 ttl = mtod(*mp, u_char *);
1480 (*mp)->m_len = 1;
1481 *ttl = imo ? imo->imo_multicast_ttl
1482 : IP_DEFAULT_MULTICAST_TTL;
1483 return (0);
1484
1485 case IP_MULTICAST_LOOP:
1486 loop = mtod(*mp, u_char *);
1487 (*mp)->m_len = 1;
1488 *loop = imo ? imo->imo_multicast_loop
1489 : IP_DEFAULT_MULTICAST_LOOP;
1490 return (0);
1491
1492 default:
1493 return (EOPNOTSUPP);
1494 }
1495 }
1496
1497 /*
1498 * Discard the IP multicast options.
1499 */
1500 void
1501 ip_freemoptions(imo)
1502 struct ip_moptions *imo;
1503 {
1504 int i;
1505
1506 if (imo != NULL) {
1507 for (i = 0; i < imo->imo_num_memberships; ++i)
1508 in_delmulti(imo->imo_membership[i]);
1509 free(imo, M_IPMOPTS);
1510 }
1511 }
1512
1513 /*
1514 * Routine called from ip_output() to loop back a copy of an IP multicast
1515 * packet to the input queue of a specified interface. Note that this
1516 * calls the output routine of the loopback "driver", but with an interface
1517 * pointer that might NOT be &loif -- easier than replicating that code here.
1518 */
1519 static void
1520 ip_mloopback(ifp, m, dst)
1521 struct ifnet *ifp;
1522 struct mbuf *m;
1523 struct sockaddr_in *dst;
1524 {
1525 struct ip *ip;
1526 struct mbuf *copym;
1527
1528 copym = m_copy(m, 0, M_COPYALL);
1529 if (copym != NULL
1530 && (copym->m_flags & M_EXT || copym->m_len < sizeof(struct ip)))
1531 copym = m_pullup(copym, sizeof(struct ip));
1532 if (copym != NULL) {
1533 /*
1534 * We don't bother to fragment if the IP length is greater
1535 * than the interface's MTU. Can this possibly matter?
1536 */
1537 ip = mtod(copym, struct ip *);
1538 HTONS(ip->ip_len);
1539 HTONS(ip->ip_off);
1540 ip->ip_sum = 0;
1541 ip->ip_sum = in_cksum(copym, ip->ip_hl << 2);
1542 (void) looutput(ifp, copym, sintosa(dst), NULL);
1543 }
1544 }
1545