1 /** $MirOS: src/sys/net/if_tun.c,v 1.5 2014/01/11 18:16:18 tg Exp $ */
2 /* $OpenBSD: if_tun.c,v 1.68 2005/06/08 06:53:32 henning Exp $ */
3 /* $NetBSD: if_tun.c,v 1.24 1996/05/07 02:40:48 thorpej Exp $ */
4
5 /*
6 * Copyright (c) 1988, Julian Onions <Julian.Onions@nexor.co.uk>
7 * Nottingham University 1987.
8 * All rights reserved.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
20 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
21 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
22 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
23 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 */
30
31 /*
32 * This driver takes packets off the IP i/f and hands them up to a
33 * user process to have its wicked way with. This driver has its
34 * roots in a similar driver written by Phil Cockcroft (formerly) at
35 * UCL. This driver is based much more on read/write/select mode of
36 * operation though.
37 */
38
39 /* #define TUN_DEBUG 9 */
40
41 #include <sys/param.h>
42 #include <sys/kernel.h>
43 #include <sys/proc.h>
44 #include <sys/systm.h>
45 #include <sys/mbuf.h>
46 #include <sys/protosw.h>
47 #include <sys/socket.h>
48 #include <sys/ioctl.h>
49 #include <sys/errno.h>
50 #include <sys/syslog.h>
51 #include <sys/select.h>
52 #include <sys/file.h>
53 #include <sys/time.h>
54 #include <sys/device.h>
55 #include <sys/vnode.h>
56 #include <sys/signalvar.h>
57 #include <sys/poll.h>
58 #include <sys/conf.h>
59
60 #include <machine/cpu.h>
61
62 #include <net/if.h>
63 #include <net/if_types.h>
64 #include <net/netisr.h>
65 #include <net/route.h>
66
67 #ifdef INET
68 #include <netinet/in.h>
69 #include <netinet/in_systm.h>
70 #include <netinet/in_var.h>
71 #include <netinet/ip.h>
72 #include <netinet/if_ether.h>
73 #endif
74
75 #ifdef IPX
76 #include <netipx/ipx.h>
77 #include <netipx/ipx_if.h>
78 #endif
79
80 #ifdef NETATALK
81 #include <netatalk/at.h>
82 #include <netatalk/at_var.h>
83 #endif
84
85 #include "bpfilter.h"
86 #if NBPFILTER > 0
87 #include <net/bpf.h>
88 #endif
89
90 /* for arc4random() */
91 #include <dev/rndvar.h>
92
93 #include <net/if_tun.h>
94
95 struct tun_softc {
96 struct arpcom arpcom; /* ethernet common data */
97 u_short tun_flags; /* misc flags */
98 pid_t tun_pgid; /* the process group - if any */
99 uid_t tun_siguid; /* uid for process that set tun_pgid */
100 uid_t tun_sigeuid; /* euid for process that set tun_pgid */
101 struct selinfo tun_rsel; /* read select */
102 struct selinfo tun_wsel; /* write select (not used) */
103 int tun_unit;
104 LIST_ENTRY(tun_softc) tun_list; /* all tunnel interfaces */
105 #define tun_if arpcom.ac_if
106 };
107
108 #ifdef TUN_DEBUG
109 int tundebug = TUN_DEBUG;
110 #define TUNDEBUG(a) (tundebug? printf a : 0)
111 #else
112 #define TUNDEBUG(a) /* (tundebug? printf a : 0) */
113 #endif
114
115 extern int ifqmaxlen;
116
117 void tunattach(int);
118 int tunopen(dev_t, int, int, struct proc *);
119 int tunclose(dev_t, int, int, struct proc *);
120 int tun_ioctl(struct ifnet *, u_long, caddr_t);
121 int tun_output(struct ifnet *, struct mbuf *, struct sockaddr *,
122 struct rtentry *);
123 int tunioctl(dev_t, u_long, caddr_t, int, struct proc *);
124 int tunread(dev_t, struct uio *, int);
125 int tunwrite(dev_t, struct uio *, int);
126 int tunpoll(dev_t, int, struct proc *);
127 int tunkqfilter(dev_t, struct knote *);
128 int tun_clone_create(struct if_clone *, int);
129 int tun_create(struct if_clone *, int, int);
130 int tun_clone_destroy(struct ifnet *);
131 struct tun_softc *tun_lookup(int);
132 void tun_wakeup(struct tun_softc *);
133 int tun_switch(struct tun_softc *, int);
134
135 static int tuninit(struct tun_softc *);
136 static void tunstart(struct ifnet *);
137 int filt_tunread(struct knote *, long);
138 int filt_tunwrite(struct knote *, long);
139 void filt_tunrdetach(struct knote *);
140 void filt_tunwdetach(struct knote *);
141
142 struct filterops tunread_filtops =
143 { 1, NULL, filt_tunrdetach, filt_tunread};
144
145 struct filterops tunwrite_filtops =
146 { 1, NULL, filt_tunwdetach, filt_tunwrite};
147
148 LIST_HEAD(, tun_softc) tun_softc_list;
149
150 struct if_clone tun_cloner =
151 IF_CLONE_INITIALIZER("tun", tun_clone_create, tun_clone_destroy);
152
153 void
tunattach(int n)154 tunattach(int n)
155 {
156 LIST_INIT(&tun_softc_list);
157 if_clone_attach(&tun_cloner);
158 }
159
160 int
tun_clone_create(struct if_clone * ifc,int unit)161 tun_clone_create(struct if_clone *ifc, int unit)
162 {
163 return tun_create(ifc, unit, 0);
164 }
165
166 int
tun_create(struct if_clone * ifc,int unit,int flags)167 tun_create(struct if_clone *ifc, int unit, int flags)
168 {
169 struct tun_softc *tp;
170 struct ifnet *ifp;
171 u_int32_t macaddr_rnd;
172 int s;
173
174 tp = malloc(sizeof(*tp), M_DEVBUF, M_NOWAIT);
175 if (!tp)
176 return (ENOMEM);
177 bzero(tp, sizeof(*tp));
178
179 tp->tun_unit = unit;
180 tp->tun_flags = TUN_INITED;
181
182 /* generate fake MAC address: 00 bd xx xx xx unit_no */
183 tp->arpcom.ac_enaddr[0] = 0x00;
184 tp->arpcom.ac_enaddr[1] = 0xbd;
185 macaddr_rnd = arc4random();
186 bcopy(&macaddr_rnd, &tp->arpcom.ac_enaddr[2], sizeof(u_int32_t));
187 tp->arpcom.ac_enaddr[5] = (u_char)unit + 1;
188
189 ifp = &tp->tun_if;
190 snprintf(ifp->if_xname, sizeof ifp->if_xname, "%s%d", ifc->ifc_name,
191 unit);
192 ifp->if_softc = tp;
193 ifp->if_ioctl = tun_ioctl;
194 ifp->if_output = tun_output;
195 ifp->if_start = tunstart;
196 IFQ_SET_MAXLEN(&ifp->if_snd, ifqmaxlen);
197 IFQ_SET_READY(&ifp->if_snd);
198 if ((flags & TUN_LAYER2) == 0) {
199 tp->tun_flags &= ~TUN_LAYER2;
200 ifp->if_mtu = TUNMTU;
201 ifp->if_flags = IFF_POINTOPOINT;
202 ifp->if_type = IFT_PROPVIRTUAL;
203 ifp->if_hdrlen = sizeof(u_int32_t);
204 if_attach(ifp);
205 if_alloc_sadl(ifp);
206 #if NBPFILTER > 0
207 bpfattach(&ifp->if_bpf, ifp, DLT_LOOP, sizeof(u_int32_t));
208 #endif
209 } else {
210 tp->tun_flags |= TUN_LAYER2;
211 ifp->if_flags =
212 (IFF_BROADCAST|IFF_SIMPLEX|IFF_MULTICAST|IFF_LINK0);
213 if_attach(ifp);
214 ether_ifattach(ifp);
215 }
216 /* force output function to our function */
217 ifp->if_output = tun_output;
218
219 s = splimp();
220 LIST_INSERT_HEAD(&tun_softc_list, tp, tun_list);
221 splx(s);
222
223 return (0);
224 }
225
226 int
tun_clone_destroy(struct ifnet * ifp)227 tun_clone_destroy(struct ifnet *ifp)
228 {
229 struct tun_softc *tp = ifp->if_softc;
230 int s;
231
232 tun_wakeup(tp);
233
234 s = splhigh();
235 klist_invalidate(&tp->tun_rsel.si_note);
236 klist_invalidate(&tp->tun_wsel.si_note);
237 splx(s);
238
239 s = splimp();
240 LIST_REMOVE(tp, tun_list);
241 splx(s);
242
243 if (tp->tun_flags & TUN_LAYER2)
244 ether_ifdetach(ifp);
245
246 if_detach(ifp);
247
248 free(tp, M_DEVBUF);
249 return (0);
250 }
251
252 struct tun_softc *
tun_lookup(int unit)253 tun_lookup(int unit)
254 {
255 struct tun_softc *tp;
256
257 LIST_FOREACH(tp, &tun_softc_list, tun_list)
258 if (tp->tun_unit == unit)
259 return (tp);
260 return (NULL);
261 }
262
263 int
tun_switch(struct tun_softc * tp,int flags)264 tun_switch(struct tun_softc *tp, int flags)
265 {
266 struct ifnet *ifp = &tp->tun_if;
267 int unit, open, r;
268
269 if ((tp->tun_flags & TUN_LAYER2) == (flags & TUN_LAYER2))
270 return (0);
271
272 /* tp will be removed so store unit number */
273 unit = tp->tun_unit;
274 open = tp->tun_flags & TUN_OPEN;
275 TUNDEBUG(("%s: switching to layer %d\n", ifp->if_xname,
276 flags & TUN_LAYER2 ? 2 : 3));
277
278 /*
279 * remove old device
280 */
281 tun_clone_destroy(ifp);
282
283 /*
284 * attach new interface
285 */
286 r = tun_create(&tun_cloner, unit, flags);
287 if (open && r == 0) {
288 /* already opened before ifconfig tunX link0 */
289 if ((tp = tun_lookup(unit)) == NULL)
290 /* this should never fail */
291 return (ENXIO);
292 tp->tun_flags |= TUN_OPEN;
293 TUNDEBUG(("%s: already open\n", tp->tun_if.if_xname));
294 }
295 return (r);
296 }
297
298 /*
299 * tunnel open - must be superuser & the device must be
300 * configured in
301 */
302 int
tunopen(dev_t dev,int flag,int mode,struct proc * p)303 tunopen(dev_t dev, int flag, int mode, struct proc *p)
304 {
305 struct tun_softc *tp;
306 struct ifnet *ifp;
307 int error, s;
308
309 if ((error = suser(p, 0)) != 0)
310 return (error);
311
312 if ((tp = tun_lookup(minor(dev))) == NULL) { /* create on demand */
313 tun_clone_create(&tun_cloner, minor(dev));
314
315 if ((tp = tun_lookup(minor(dev))) == NULL)
316 return (ENXIO);
317 }
318
319 if (tp->tun_flags & TUN_OPEN)
320 return EBUSY;
321
322 ifp = &tp->tun_if;
323 tp->tun_flags |= TUN_OPEN;
324
325 /* automatically UP the interface on open */
326 s = splimp();
327 if_up(ifp);
328 ifp->if_flags |= IFF_RUNNING;
329 splx(s);
330
331 TUNDEBUG(("%s: open\n", ifp->if_xname));
332 return (0);
333 }
334
335 /*
336 * tunclose - close the device; if closing the real device, flush pending
337 * output and (unless set STAYUP) bring down the interface.
338 */
339 int
tunclose(dev_t dev,int flag,int mode,struct proc * p)340 tunclose(dev_t dev, int flag, int mode, struct proc *p)
341 {
342 extern int if_detach_rtdelete(struct radix_node *, void *);
343 int s, i;
344 struct tun_softc *tp;
345 struct ifnet *ifp;
346 struct radix_node_head *rnh;
347
348 if ((tp = tun_lookup(minor(dev))) == NULL)
349 return (ENXIO);
350
351 ifp = &tp->tun_if;
352 tp->tun_flags &= ~TUN_OPEN;
353
354 /*
355 * junk all pending output
356 */
357 s = splimp();
358 IFQ_PURGE(&ifp->if_snd);
359 splx(s);
360
361 if ((ifp->if_flags & IFF_UP) && !(tp->tun_flags & TUN_STAYUP)) {
362 s = splimp();
363 if_down(ifp);
364 if (ifp->if_flags & IFF_RUNNING) {
365 /* find internet addresses and delete routes */
366 struct ifaddr *ifa = NULL;
367
368 TAILQ_FOREACH(ifa, &ifp->if_addrlist, ifa_list) {
369 #ifdef INET
370 if (ifa->ifa_addr->sa_family == AF_INET) {
371 rtinit(ifa, (int)RTM_DELETE,
372 (tp->tun_flags & TUN_DSTADDR)?
373 RTF_HOST : 0);
374 }
375 # ifdef INET6
376 else
377 # endif
378 #endif
379 #ifdef INET6
380 if (ifa->ifa_addr->sa_family == AF_INET6) {
381 rtinit(ifa, (int)RTM_DELETE,
382 (tp->tun_flags & TUN_DSTADDR)?
383 RTF_HOST : 0);
384 }
385 #endif
386 }
387 /*
388 * Find and remove all routes which is using this
389 * interface. Stolen from if.c if_detach().
390 */
391 for (i = 1; i <= AF_MAX; i++) {
392 rnh = rt_tables[i];
393 if (rnh)
394 while ((*rnh->rnh_walktree)(rnh,
395 if_detach_rtdelete, ifp) == EAGAIN)
396 ;
397 }
398 ifp->if_flags &= ~IFF_RUNNING;
399 }
400 splx(s);
401 }
402 tp->tun_pgid = 0;
403 selwakeup(&tp->tun_rsel);
404 KNOTE(&tp->tun_rsel.si_note, 0);
405
406 TUNDEBUG(("%s: closed\n", ifp->if_xname));
407 return (0);
408 }
409
410 static int
tuninit(struct tun_softc * tp)411 tuninit(struct tun_softc *tp)
412 {
413 struct ifnet *ifp = &tp->tun_if;
414 struct ifaddr *ifa;
415
416 TUNDEBUG(("%s: tuninit\n", ifp->if_xname));
417
418 ifp->if_flags |= IFF_UP | IFF_RUNNING;
419 ifp->if_flags &= ~IFF_OACTIVE; /* we are never active */
420
421 tp->tun_flags &= ~(TUN_IASET|TUN_DSTADDR|TUN_BRDADDR);
422 TAILQ_FOREACH(ifa, &ifp->if_addrlist, ifa_list) {
423 #ifdef INET
424 if (ifa->ifa_addr->sa_family == AF_INET) {
425 struct sockaddr_in *sin;
426
427 sin = satosin(ifa->ifa_addr);
428 if (sin && sin->sin_addr.s_addr)
429 tp->tun_flags |= TUN_IASET;
430
431 if (ifp->if_flags & IFF_POINTOPOINT) {
432 sin = satosin(ifa->ifa_dstaddr);
433 if (sin && sin->sin_addr.s_addr)
434 tp->tun_flags |= TUN_DSTADDR;
435 } else
436 tp->tun_flags &= ~TUN_DSTADDR;
437
438 if (ifp->if_flags & IFF_BROADCAST) {
439 sin = satosin(ifa->ifa_broadaddr);
440 if (sin && sin->sin_addr.s_addr)
441 tp->tun_flags |= TUN_BRDADDR;
442 } else
443 tp->tun_flags &= ~TUN_BRDADDR;
444 }
445 #endif
446 #ifdef INET6
447 if (ifa->ifa_addr->sa_family == AF_INET6) {
448 struct sockaddr_in6 *sin;
449
450 sin = (struct sockaddr_in6 *)ifa->ifa_addr;
451 if (!IN6_IS_ADDR_UNSPECIFIED(&sin->sin6_addr))
452 tp->tun_flags |= TUN_IASET;
453
454 if (ifp->if_flags & IFF_POINTOPOINT) {
455 sin = (struct sockaddr_in6 *)ifa->ifa_dstaddr;
456 if (sin &&
457 !IN6_IS_ADDR_UNSPECIFIED(&sin->sin6_addr))
458 tp->tun_flags |= TUN_DSTADDR;
459 } else
460 tp->tun_flags &= ~TUN_DSTADDR;
461 }
462 #endif /* INET6 */
463 }
464
465 return 0;
466 }
467
468 /*
469 * Process an ioctl request.
470 */
471 int
tun_ioctl(struct ifnet * ifp,u_long cmd,caddr_t data)472 tun_ioctl(struct ifnet *ifp, u_long cmd, caddr_t data)
473 {
474 struct tun_softc *tp = (struct tun_softc *)(ifp->if_softc);
475 struct ifreq *ifr = (struct ifreq *)data;
476 int error = 0, s;
477
478 s = splimp();
479 if (tp->tun_flags & TUN_LAYER2)
480 if ((error = ether_ioctl(ifp, &tp->arpcom, cmd, data)) > 0) {
481 splx(s);
482 return (error);
483 }
484 switch (cmd) {
485 case SIOCSIFADDR:
486 tuninit(tp);
487 TUNDEBUG(("%s: address set\n", ifp->if_xname));
488 if (tp->tun_flags & TUN_LAYER2)
489 switch (((struct ifaddr *)data)->ifa_addr->sa_family) {
490 #ifdef INET
491 case AF_INET:
492 arp_ifinit(&tp->arpcom, (struct ifaddr *)data);
493 break;
494 #endif
495 default:
496 break;
497 }
498 break;
499 case SIOCSIFDSTADDR:
500 tuninit(tp);
501 TUNDEBUG(("%s: destination address set\n", ifp->if_xname));
502 break;
503 case SIOCSIFBRDADDR:
504 tuninit(tp);
505 TUNDEBUG(("%s: broadcast address set\n", ifp->if_xname));
506 break;
507 case SIOCSIFMTU:
508 if (ifr->ifr_mtu < ETHERMIN || ifr->ifr_mtu > TUNMRU)
509 error = EINVAL;
510 else
511 ifp->if_mtu = ifr->ifr_mtu;
512 break;
513 case SIOCADDMULTI:
514 case SIOCDELMULTI: {
515 if (ifr == 0) {
516 error = EAFNOSUPPORT; /* XXX */
517 break;
518 }
519
520 if (tp->tun_flags & TUN_LAYER2) {
521 error = (cmd == SIOCADDMULTI) ?
522 ether_addmulti(ifr, &tp->arpcom) :
523 ether_delmulti(ifr, &tp->arpcom);
524 if (error == ENETRESET) {
525 /*
526 * Multicast list has changed; set the hardware
527 * filter accordingly. The good thing is we do
528 * not have a hardware filter (:
529 */
530 error = 0;
531 }
532 break;
533 }
534
535 switch (ifr->ifr_addr.sa_family) {
536 #ifdef INET
537 case AF_INET:
538 break;
539 #endif
540 #ifdef INET6
541 case AF_INET6:
542 break;
543 #endif
544 default:
545 error = EAFNOSUPPORT;
546 break;
547 }
548 break;
549 }
550
551 case SIOCSIFFLAGS:
552 error = tun_switch(tp,
553 ifr->ifr_flags & IFF_LINK0 ? TUN_LAYER2 : 0);
554 break;
555 default:
556 error = EINVAL;
557 }
558 splx(s);
559 return (error);
560 }
561
562 /*
563 * tun_output - queue packets from higher level ready to put out.
564 */
565 int
tun_output(struct ifnet * ifp,struct mbuf * m0,struct sockaddr * dst,struct rtentry * rt)566 tun_output(struct ifnet *ifp, struct mbuf *m0, struct sockaddr *dst,
567 struct rtentry *rt)
568 {
569 struct tun_softc *tp = ifp->if_softc;
570 int s, len, error;
571 u_int32_t *af;
572
573 if (!(ifp->if_flags & IFF_UP)) {
574 m_freem(m0);
575 return (EHOSTDOWN);
576 }
577
578 TUNDEBUG(("%s: tun_output\n", ifp->if_xname));
579
580 if ((tp->tun_flags & TUN_READY) != TUN_READY) {
581 TUNDEBUG(("%s: not ready %#x\n", ifp->if_xname,
582 tp->tun_flags));
583 m_freem(m0);
584 return (EHOSTDOWN);
585 }
586
587 if (tp->tun_flags & TUN_LAYER2)
588 /* call ether_output and that will call tunstart at the end */
589 return (ether_output(ifp, m0, dst, rt));
590
591 M_PREPEND(m0, sizeof(*af), M_DONTWAIT);
592 af = mtod(m0, u_int32_t *);
593 *af = htonl(dst->sa_family);
594
595 #if NBPFILTER > 0
596 if (ifp->if_bpf)
597 bpf_mtap(ifp->if_bpf, m0);
598 #endif
599
600 len = m0->m_pkthdr.len + sizeof(*af);
601 s = splimp();
602 IFQ_ENQUEUE(&ifp->if_snd, m0, NULL, error);
603 if (error) {
604 splx(s);
605 ifp->if_collisions++;
606 return (error);
607 }
608 splx(s);
609 ifp->if_opackets++;
610 ifp->if_obytes += len;
611
612 tun_wakeup(tp);
613 return (0);
614 }
615
616 void
tun_wakeup(struct tun_softc * tp)617 tun_wakeup(struct tun_softc *tp)
618 {
619 if (tp->tun_flags & TUN_RWAIT) {
620 tp->tun_flags &= ~TUN_RWAIT;
621 wakeup((caddr_t)tp);
622 }
623 if (tp->tun_flags & TUN_ASYNC && tp->tun_pgid)
624 csignal(tp->tun_pgid, SIGIO,
625 tp->tun_siguid, tp->tun_sigeuid);
626 selwakeup(&tp->tun_rsel);
627 KNOTE(&tp->tun_rsel.si_note, 0);
628 }
629
630 /*
631 * the cdevsw interface is now pretty minimal.
632 */
633 int
tunioctl(dev_t dev,u_long cmd,caddr_t data,int flag,struct proc * p)634 tunioctl(dev_t dev, u_long cmd, caddr_t data, int flag, struct proc *p)
635 {
636 int s;
637 struct tun_softc *tp;
638 struct tuninfo *tunp;
639 struct mbuf *m;
640
641 if ((tp = tun_lookup(minor(dev))) == NULL)
642 return (ENXIO);
643
644 s = splimp();
645 switch (cmd) {
646 case TUNSIFINFO:
647 tunp = (struct tuninfo *)data;
648 tp->tun_if.if_mtu = tunp->mtu;
649 tp->tun_if.if_type = tunp->type;
650 tp->tun_if.if_flags = tunp->flags;
651 tp->tun_if.if_baudrate = tunp->baudrate;
652 break;
653 case TUNGIFINFO:
654 tunp = (struct tuninfo *)data;
655 tunp->mtu = tp->tun_if.if_mtu;
656 tunp->type = tp->tun_if.if_type;
657 tunp->flags = tp->tun_if.if_flags;
658 tunp->baudrate = tp->tun_if.if_baudrate;
659 break;
660 #ifdef TUN_DEBUG
661 case TUNSDEBUG:
662 tundebug = *(int *)data;
663 break;
664 case TUNGDEBUG:
665 *(int *)data = tundebug;
666 break;
667 #endif
668 case TUNSIFMODE:
669 switch (*(int *)data & (IFF_POINTOPOINT|IFF_BROADCAST)) {
670 case IFF_POINTOPOINT:
671 case IFF_BROADCAST:
672 tp->tun_if.if_flags &=
673 ~(IFF_BROADCAST|IFF_POINTOPOINT|IFF_MULTICAST);
674 tp->tun_if.if_flags |= *(int *)data;
675 break;
676 default:
677 splx(s);
678 return (EINVAL);
679 }
680 break;
681
682 case FIONBIO:
683 if (*(int *)data)
684 tp->tun_flags |= TUN_NBIO;
685 else
686 tp->tun_flags &= ~TUN_NBIO;
687 break;
688 case FIOASYNC:
689 if (*(int *)data)
690 tp->tun_flags |= TUN_ASYNC;
691 else
692 tp->tun_flags &= ~TUN_ASYNC;
693 break;
694 case FIONREAD:
695 IFQ_POLL(&tp->tun_if.if_snd, m);
696 if (m != NULL)
697 *(int *)data = m->m_pkthdr.len;
698 else
699 *(int *)data = 0;
700 break;
701 case TIOCSPGRP:
702 tp->tun_pgid = *(int *)data;
703 tp->tun_siguid = p->p_cred->p_ruid;
704 tp->tun_sigeuid = p->p_ucred->cr_uid;
705 break;
706 case TIOCGPGRP:
707 *(int *)data = tp->tun_pgid;
708 break;
709 case OSIOCGIFADDR:
710 case SIOCGIFADDR:
711 if (!(tp->tun_flags & TUN_LAYER2)) {
712 splx(s);
713 return (EINVAL);
714 }
715 bcopy(tp->arpcom.ac_enaddr, data,
716 sizeof(tp->arpcom.ac_enaddr));
717 break;
718
719 case SIOCSIFADDR:
720 if (!(tp->tun_flags & TUN_LAYER2)) {
721 splx(s);
722 return (EINVAL);
723 }
724 bcopy(data, tp->arpcom.ac_enaddr,
725 sizeof(tp->arpcom.ac_enaddr));
726 break;
727 default:
728 splx(s);
729 return (ENOTTY);
730 }
731 splx(s);
732 return (0);
733 }
734
735 /*
736 * The cdevsw read interface - reads a packet at a time, or at
737 * least as much of a packet as can be read.
738 */
739 int
tunread(dev_t dev,struct uio * uio,int ioflag)740 tunread(dev_t dev, struct uio *uio, int ioflag)
741 {
742 struct tun_softc *tp;
743 struct ifnet *ifp;
744 struct mbuf *m, *m0;
745 int error = 0, len, s;
746
747 if ((tp = tun_lookup(minor(dev))) == NULL)
748 return (ENXIO);
749
750 ifp = &tp->tun_if;
751 TUNDEBUG(("%s: read\n", ifp->if_xname));
752 if ((tp->tun_flags & TUN_READY) != TUN_READY) {
753 TUNDEBUG(("%s: not ready %#x\n", ifp->if_xname, tp->tun_flags));
754 return (EHOSTDOWN);
755 }
756
757 tp->tun_flags &= ~TUN_RWAIT;
758
759 s = splimp();
760 do {
761 while ((tp->tun_flags & TUN_READY) != TUN_READY)
762 if ((error = tsleep((caddr_t)tp,
763 (PZERO + 1)|PCATCH, "tunread", 0)) != 0) {
764 splx(s);
765 return (error);
766 }
767 IFQ_DEQUEUE(&ifp->if_snd, m0);
768 if (m0 == NULL) {
769 if (tp->tun_flags & TUN_NBIO && ioflag & IO_NDELAY) {
770 splx(s);
771 return (EWOULDBLOCK);
772 }
773 tp->tun_flags |= TUN_RWAIT;
774 if ((error = tsleep((caddr_t)tp,
775 (PZERO + 1)|PCATCH, "tunread", 0)) != 0) {
776 splx(s);
777 return (error);
778 }
779 }
780 } while (m0 == NULL);
781 splx(s);
782
783 while (m0 != NULL && uio->uio_resid > 0 && error == 0) {
784 len = min(uio->uio_resid, m0->m_len);
785 if (len != 0)
786 error = uiomove(mtod(m0, caddr_t), len, uio);
787 MFREE(m0, m);
788 m0 = m;
789 }
790
791 if (m0 != NULL) {
792 TUNDEBUG(("Dropping mbuf\n"));
793 m_freem(m0);
794 }
795 if (error)
796 ifp->if_ierrors++;
797
798 return error;
799 }
800
801 /*
802 * the cdevsw write interface - an atomic write is a packet - or else!
803 */
804 int
tunwrite(dev_t dev,struct uio * uio,int ioflag)805 tunwrite(dev_t dev, struct uio *uio, int ioflag)
806 {
807 struct tun_softc *tp;
808 struct ifnet *ifp;
809 struct ifqueue *ifq;
810 u_int32_t *th;
811 struct mbuf *top, **mp, *m;
812 int isr;
813 int error=0, s, tlen, mlen;
814
815 if ((tp = tun_lookup(minor(dev))) == NULL)
816 return (ENXIO);
817
818 ifp = &tp->tun_if;
819 TUNDEBUG(("%s: tunwrite\n", ifp->if_xname));
820
821 if (uio->uio_resid == 0 || uio->uio_resid > ifp->if_mtu +
822 (tp->tun_flags & TUN_LAYER2 ? ETHER_HDR_LEN : sizeof(*th))) {
823 TUNDEBUG(("%s: len=%d!\n", ifp->if_xname, uio->uio_resid));
824 return (EMSGSIZE);
825 }
826 tlen = uio->uio_resid;
827
828 /* get a header mbuf */
829 MGETHDR(m, M_DONTWAIT, MT_DATA);
830 if (m == NULL)
831 return (ENOBUFS);
832 mlen = MHLEN;
833
834 top = NULL;
835 mp = ⊤
836 if (tp->tun_flags & TUN_LAYER2) {
837 /*
838 * Pad so that IP header is correctly aligned
839 * this is neccessary for all strict aligned architectures.
840 */
841 mlen -= ETHER_ALIGN;
842 m_adj(m, ETHER_ALIGN);
843 }
844 while (error == 0 && uio->uio_resid > 0) {
845 m->m_len = min(mlen, uio->uio_resid);
846 error = uiomove(mtod (m, caddr_t), m->m_len, uio);
847 *mp = m;
848 mp = &m->m_next;
849 if (error == 0 && uio->uio_resid > 0) {
850 MGET(m, M_DONTWAIT, MT_DATA);
851 if (m == NULL) {
852 error = ENOBUFS;
853 break;
854 }
855 mlen = MLEN;
856 }
857 }
858 if (error) {
859 if (top != NULL)
860 m_freem(top);
861 ifp->if_ierrors++;
862 return (error);
863 }
864
865 top->m_pkthdr.len = tlen;
866 top->m_pkthdr.rcvif = ifp;
867
868 #if NBPFILTER > 0
869 if (ifp->if_bpf)
870 bpf_mtap(ifp->if_bpf, top);
871 #endif
872
873 if (tp->tun_flags & TUN_LAYER2) {
874 ether_input_mbuf(ifp, top);
875 ifp->if_ipackets++; /* ibytes are counted in ether_input */
876 return (0);
877 }
878
879 th = mtod(top, u_int32_t *);
880 /* strip the tunnel header */
881 top->m_data += sizeof(*th);
882 top->m_len -= sizeof(*th);
883 top->m_pkthdr.len -= sizeof(*th);
884
885 switch (ntohl(*th)) {
886 #ifdef INET
887 case AF_INET:
888 ifq = &ipintrq;
889 isr = NETISR_IP;
890 break;
891 #endif
892 #ifdef INET6
893 case AF_INET6:
894 ifq = &ip6intrq;
895 isr = NETISR_IPV6;
896 break;
897 #endif
898 #ifdef IPX
899 case AF_IPX:
900 ifq = &ipxintrq;
901 isr = NETISR_IPX;
902 break;
903 #endif
904 #ifdef NETATALK
905 case AF_APPLETALK:
906 ifq = &atintrq2;
907 isr = NETISR_ATALK;
908 break;
909 #endif
910 default:
911 m_freem(top);
912 return (EAFNOSUPPORT);
913 }
914
915 s = splimp();
916 if (IF_QFULL(ifq)) {
917 IF_DROP(ifq);
918 splx(s);
919 ifp->if_collisions++;
920 m_freem(top);
921 if (!ifq->ifq_congestion)
922 if_congestion(ifq);
923 return (ENOBUFS);
924 }
925 IF_ENQUEUE(ifq, top);
926 schednetisr_virtual(isr);
927 ifp->if_ipackets++;
928 ifp->if_ibytes += top->m_pkthdr.len;
929 splx(s);
930 return (error);
931 }
932
933 /*
934 * tunpoll - the poll interface, this is only useful on reads
935 * really. The write detect always returns true, write never blocks
936 * anyway, it either accepts the packet or drops it.
937 */
938 int
tunpoll(dev_t dev,int events,struct proc * p)939 tunpoll(dev_t dev, int events, struct proc *p)
940 {
941 int revents, s;
942 struct tun_softc *tp;
943 struct ifnet *ifp;
944 struct mbuf *m;
945
946 if ((tp = tun_lookup(minor(dev))) == NULL)
947 return (ENXIO);
948
949 ifp = &tp->tun_if;
950 revents = 0;
951 s = splimp();
952 TUNDEBUG(("%s: tunpoll\n", ifp->if_xname));
953
954 if (events & (POLLIN | POLLRDNORM)) {
955 IFQ_POLL(&ifp->if_snd, m);
956 if (m != NULL) {
957 TUNDEBUG(("%s: tunselect q=%d\n", ifp->if_xname,
958 ifp->if_snd.ifq_len));
959 revents |= events & (POLLIN | POLLRDNORM);
960 } else {
961 TUNDEBUG(("%s: tunpoll waiting\n", ifp->if_xname));
962 selrecord(p, &tp->tun_rsel);
963 }
964 }
965 if (events & (POLLOUT | POLLWRNORM))
966 revents |= events & (POLLOUT | POLLWRNORM);
967 splx(s);
968 return (revents);
969 }
970
971 /*
972 * kqueue(2) support.
973 *
974 * The tun driver uses an array of tun_softc's based on the minor number
975 * of the device. kn->kn_hook gets set to the specific tun_softc.
976 *
977 * filt_tunread() sets kn->kn_data to the iface qsize
978 * filt_tunwrite() sets kn->kn_data to the MTU size
979 */
980 int
tunkqfilter(dev_t dev,struct knote * kn)981 tunkqfilter(dev_t dev, struct knote *kn)
982 {
983 int s;
984 struct klist *klist;
985 struct tun_softc *tp;
986 struct ifnet *ifp;
987
988 if ((tp = tun_lookup(minor(dev))) == NULL)
989 return (ENXIO);
990
991 ifp = &tp->tun_if;
992
993 s = splimp();
994 TUNDEBUG(("%s: tunkqfilter\n", ifp->if_xname));
995 splx(s);
996
997 switch (kn->kn_filter) {
998 case EVFILT_READ:
999 klist = &tp->tun_rsel.si_note;
1000 kn->kn_fop = &tunread_filtops;
1001 break;
1002 case EVFILT_WRITE:
1003 klist = &tp->tun_wsel.si_note;
1004 kn->kn_fop = &tunwrite_filtops;
1005 break;
1006 default:
1007 return (EPERM); /* 1 */
1008 }
1009
1010 kn->kn_hook = (caddr_t)tp;
1011
1012 s = splhigh();
1013 SLIST_INSERT_HEAD(klist, kn, kn_selnext);
1014 splx(s);
1015
1016 return (0);
1017 }
1018
1019 void
filt_tunrdetach(struct knote * kn)1020 filt_tunrdetach(struct knote *kn)
1021 {
1022 int s;
1023 struct tun_softc *tp = (struct tun_softc *)kn->kn_hook;
1024
1025 s = splhigh();
1026 if (!(kn->kn_status & KN_DETACHED))
1027 SLIST_REMOVE(&tp->tun_rsel.si_note, kn, knote, kn_selnext);
1028 splx(s);
1029 }
1030
1031 int
filt_tunread(struct knote * kn,long hint)1032 filt_tunread(struct knote *kn, long hint)
1033 {
1034 int s;
1035 struct tun_softc *tp;
1036 struct ifnet *ifp;
1037 struct mbuf *m;
1038
1039 if (kn->kn_status & KN_DETACHED) {
1040 kn->kn_data = 0;
1041 return 1;
1042 }
1043
1044 tp = (struct tun_softc *)kn->kn_hook;
1045 ifp = &tp->tun_if;
1046
1047 s = splnet();
1048 IFQ_POLL(&ifp->if_snd, m);
1049 if (m != NULL) {
1050 splx(s);
1051 kn->kn_data = ifp->if_snd.ifq_len;
1052
1053 TUNDEBUG(("%s: tunkqread q=%d\n", ifp->if_xname,
1054 ifp->if_snd.ifq_len));
1055 return (1);
1056 }
1057 splx(s);
1058 TUNDEBUG(("%s: tunkqread waiting\n", ifp->if_xname));
1059 return (0);
1060 }
1061
1062 void
filt_tunwdetach(struct knote * kn)1063 filt_tunwdetach(struct knote *kn)
1064 {
1065 int s;
1066 struct tun_softc *tp = (struct tun_softc *)kn->kn_hook;
1067
1068 s = splhigh();
1069 if (!(kn->kn_status & KN_DETACHED))
1070 SLIST_REMOVE(&tp->tun_wsel.si_note, kn, knote, kn_selnext);
1071 splx(s);
1072 }
1073
1074 int
filt_tunwrite(struct knote * kn,long hint)1075 filt_tunwrite(struct knote *kn, long hint)
1076 {
1077 struct tun_softc *tp;
1078 struct ifnet *ifp;
1079
1080 if (kn->kn_status & KN_DETACHED) {
1081 kn->kn_data = 0;
1082 return (1);
1083 }
1084
1085 tp = (struct tun_softc *)kn->kn_hook;
1086 ifp = &tp->tun_if;
1087
1088 kn->kn_data = ifp->if_mtu;
1089
1090 return (1);
1091 }
1092
1093 /*
1094 * Start packet transmission on the interface.
1095 * when the interface queue is rate-limited by ALTQ or TBR,
1096 * if_start is needed to drain packets from the queue in order
1097 * to notify readers when outgoing packets become ready.
1098 * In layer 2 mode this function is called from ether_output.
1099 */
1100 static void
tunstart(struct ifnet * ifp)1101 tunstart(struct ifnet *ifp)
1102 {
1103 struct tun_softc *tp = ifp->if_softc;
1104 struct mbuf *m;
1105
1106 if (!(tp->tun_flags & TUN_LAYER2) &&
1107 !ALTQ_IS_ENABLED(&ifp->if_snd) &&
1108 !TBR_IS_ENABLED(&ifp->if_snd))
1109 return;
1110
1111 IFQ_POLL(&ifp->if_snd, m);
1112 if (m != NULL) {
1113 if (tp->tun_flags & TUN_LAYER2) {
1114 #if NBPFILTER > 0
1115 if (ifp->if_bpf)
1116 bpf_mtap(ifp->if_bpf, m);
1117 #endif
1118 ifp->if_opackets++;
1119 }
1120 tun_wakeup(tp);
1121 }
1122 }
1123