Merge branch 'vendor/DHCPCD'
[dragonfly.git] / sys / net / tap / if_tap.c
1 /*
2  * Copyright (C) 1999-2000 by Maksim Yevmenkin <m_evmenkin@yahoo.com>
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24  * SUCH DAMAGE.
25  *
26  * BASED ON:
27  * -------------------------------------------------------------------------
28  *
29  * Copyright (c) 1988, Julian Onions <jpo@cs.nott.ac.uk>
30  * Nottingham University 1987.
31  */
32
33 /*
34  * $FreeBSD: src/sys/net/if_tap.c,v 1.3.2.3 2002/04/14 21:41:48 luigi Exp $
35  * $Id: if_tap.c,v 0.21 2000/07/23 21:46:02 max Exp $
36  */
37
38 #include "opt_inet.h"
39
40 #include <sys/param.h>
41 #include <sys/conf.h>
42 #include <sys/device.h>
43 #include <sys/filedesc.h>
44 #include <sys/filio.h>
45 #include <sys/kernel.h>
46 #include <sys/malloc.h>
47 #include <sys/mbuf.h>
48 #include <sys/proc.h>
49 #include <sys/priv.h>
50 #include <sys/signalvar.h>
51 #include <sys/socket.h>
52 #include <sys/sockio.h>
53 #include <sys/sysctl.h>
54 #include <sys/systm.h>
55 #include <sys/ttycom.h>
56 #include <sys/uio.h>
57 #include <sys/vnode.h>
58 #include <sys/serialize.h>
59 #include <sys/thread2.h>
60 #include <sys/mplock2.h>
61 #include <sys/devfs.h>
62 #include <sys/queue.h>
63
64 #include <net/bpf.h>
65 #include <net/ethernet.h>
66 #include <net/if.h>
67 #include <net/if_types.h>
68 #include <net/if_arp.h>
69 #include <net/if_clone.h>
70 #include <net/if_media.h>
71 #include <net/ifq_var.h>
72 #include <net/route.h>
73
74 #include <netinet/in.h>
75
76 #include "if_tapvar.h"
77 #include "if_tap.h"
78
79 #define TAP_IFFLAGS     (IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST)
80
81 #define TAP             "tap"
82 #define TAPDEBUG        if (tapdebug) if_printf
83
84 /* module */
85 static int              tapmodevent(module_t, int, void *);
86
87 /* device */
88 static struct tap_softc *tapcreate(cdev_t, int);
89 static void             tapdestroy(struct tap_softc *);
90
91 /* clone */
92 static int              tap_clone_create(struct if_clone *, int,
93                                          caddr_t, caddr_t);
94 static int              tap_clone_destroy(struct ifnet *);
95
96 /* network interface */
97 static void             tapifinit(void *);
98 static void             tapifstart(struct ifnet *, struct ifaltq_subque *);
99 static int              tapifioctl(struct ifnet *, u_long, caddr_t,
100                                    struct ucred *);
101 static void             tapifstop(struct tap_softc *, int);
102 static void             tapifflags(struct tap_softc *);
103
104 /* character device */
105 static d_open_t         tapopen;
106 static d_clone_t        tapclone;
107 static d_close_t        tapclose;
108 static d_read_t         tapread;
109 static d_write_t        tapwrite;
110 static d_ioctl_t        tapioctl;
111 static d_kqfilter_t     tapkqfilter;
112
113 static struct dev_ops   tap_ops = {
114         { TAP, 0, 0 },
115         .d_open =       tapopen,
116         .d_close =      tapclose,
117         .d_read =       tapread,
118         .d_write =      tapwrite,
119         .d_ioctl =      tapioctl,
120         .d_kqfilter =   tapkqfilter
121 };
122
123 /* kqueue support */
124 static void             tap_filter_detach(struct knote *);
125 static int              tap_filter_read(struct knote *, long);
126 static int              tap_filter_write(struct knote *, long);
127
128 static struct filterops tapread_filtops = {
129         FILTEROP_ISFD,
130         NULL,
131         tap_filter_detach,
132         tap_filter_read
133 };
134 static struct filterops tapwrite_filtops = {
135         FILTEROP_ISFD,
136         NULL,
137         tap_filter_detach,
138         tap_filter_write
139 };
140
141 static int              tapdebug = 0;           /* debug flag */
142 static int              taprefcnt = 0;          /* module ref. counter */
143 static int              tapuopen = 0;           /* allow user open() */
144 static int              tapuponopen = 0;        /* IFF_UP when opened */
145
146 static MALLOC_DEFINE(M_TAP, TAP, "Ethernet tunnel interface");
147
148 static DEVFS_DEFINE_CLONE_BITMAP(tap);
149
150 struct if_clone tap_cloner = IF_CLONE_INITIALIZER(
151         TAP, tap_clone_create, tap_clone_destroy, 0, IF_MAXUNIT);
152
153 static SLIST_HEAD(,tap_softc) tap_listhead =
154         SLIST_HEAD_INITIALIZER(&tap_listhead);
155
156 SYSCTL_INT(_debug, OID_AUTO, if_tap_debug, CTLFLAG_RW, &tapdebug, 0, "");
157 SYSCTL_DECL(_net_link);
158 SYSCTL_NODE(_net_link, OID_AUTO, tap, CTLFLAG_RW, 0,
159             "Ethernet tunnel software network interface");
160 SYSCTL_INT(_net_link_tap, OID_AUTO, user_open, CTLFLAG_RW, &tapuopen, 0,
161            "Allow user to open /dev/tap (based on node permissions)");
162 SYSCTL_INT(_net_link_tap, OID_AUTO, up_on_open, CTLFLAG_RW, &tapuponopen, 0,
163            "Bring interface up when /dev/tap is opened");
164 SYSCTL_INT(_net_link_tap, OID_AUTO, debug, CTLFLAG_RW, &tapdebug, 0, "");
165 SYSCTL_INT(_net_link_tap, OID_AUTO, refcnt, CTLFLAG_RD, &taprefcnt, 0,
166            "Number of opened devices");
167
168 DEV_MODULE(if_tap, tapmodevent, NULL);
169
170 /*
171  * tapmodevent
172  *
173  * module event handler
174  */
175 static int
176 tapmodevent(module_t mod, int type, void *data)
177 {
178         static cdev_t dev = NULL;
179         struct tap_softc *sc, *sc_tmp;
180
181         switch (type) {
182         case MOD_LOAD:
183                 dev = make_autoclone_dev(&tap_ops, &DEVFS_CLONE_BITMAP(tap),
184                                          tapclone, UID_ROOT, GID_WHEEL,
185                                          0600, TAP);
186                 SLIST_INIT(&tap_listhead);
187                 if_clone_attach(&tap_cloner);
188                 break;
189
190         case MOD_UNLOAD:
191                 if (taprefcnt > 0)
192                         return (EBUSY);
193
194                 if_clone_detach(&tap_cloner);
195
196                 SLIST_FOREACH_MUTABLE(sc, &tap_listhead, tap_link, sc_tmp)
197                         tapdestroy(sc);
198
199                 dev_ops_remove_all(&tap_ops);
200                 destroy_autoclone_dev(dev, &DEVFS_CLONE_BITMAP(tap));
201                 break;
202
203         default:
204                 return (EOPNOTSUPP);
205         }
206
207         return (0);
208 }
209
210
211 /*
212  * Create or clone an interface
213  */
214 static struct tap_softc *
215 tapcreate(cdev_t dev, int flags)
216 {
217         struct tap_softc *sc;
218         struct ifnet *ifp;
219         uint8_t ether_addr[ETHER_ADDR_LEN];
220         int unit = minor(dev);
221
222         sc = kmalloc(sizeof(*sc), M_TAP, M_WAITOK | M_ZERO);
223         dev->si_drv1 = sc;
224         sc->tap_dev = dev;
225         sc->tap_flags |= flags;
226
227         reference_dev(dev); /* device association */
228
229         /* generate fake MAC address: 00 bd xx xx xx unit_no */
230         ether_addr[0] = 0x00;
231         ether_addr[1] = 0xbd;
232         bcopy(&ticks, &ether_addr[2], 3);
233         ether_addr[5] = (u_char)unit;
234
235         /* fill the rest and attach interface */
236         ifp = &sc->tap_if;
237         if_initname(ifp, TAP, unit);
238         ifp->if_type = IFT_ETHER;
239         ifp->if_init = tapifinit;
240         ifp->if_start = tapifstart;
241         ifp->if_ioctl = tapifioctl;
242         ifp->if_mtu = ETHERMTU;
243         ifp->if_flags = TAP_IFFLAGS;
244         ifp->if_softc = sc;
245         ifq_set_maxlen(&ifp->if_snd, ifqmaxlen);
246         ifq_set_ready(&ifp->if_snd);
247
248         ether_ifattach(ifp, ether_addr, NULL);
249
250         sc->tap_flags |= TAP_INITED;
251         sc->tap_devq.ifq_maxlen = ifqmaxlen;
252
253         SLIST_INSERT_HEAD(&tap_listhead, sc, tap_link);
254
255         TAPDEBUG(ifp, "created, minor = %#x, flags = 0x%x\n",
256                  unit, sc->tap_flags);
257         return (sc);
258 }
259
260 static struct tap_softc *
261 tapfind(int unit)
262 {
263         struct tap_softc *sc;
264
265         SLIST_FOREACH(sc, &tap_listhead, tap_link) {
266                 if (minor(sc->tap_dev) == unit)
267                         return (sc);
268         }
269         return (NULL);
270 }
271
272 /*
273  * Create a new tap instance via ifconfig.
274  */
275 static int
276 tap_clone_create(struct if_clone *ifc __unused, int unit,
277                  caddr_t params __unused, caddr_t data)
278 {
279         struct tap_softc *sc;
280         cdev_t dev = (cdev_t)data;
281         int flags;
282
283         if (tapfind(unit) != NULL)
284                 return (EEXIST);
285
286         if (dev == NULL) {
287                 if (!devfs_clone_bitmap_chk(&DEVFS_CLONE_BITMAP(tap), unit)) {
288                         devfs_clone_bitmap_set(&DEVFS_CLONE_BITMAP(tap), unit);
289                         dev = make_dev(&tap_ops, unit, UID_ROOT, GID_WHEEL,
290                                        0600, "%s%d", TAP, unit);
291                 } else {
292                         dev = devfs_find_device_by_name("%s%d", TAP, unit);
293                         if (dev == NULL)
294                                 return (ENOENT);
295                 }
296                 flags = TAP_MANUALMAKE;
297         } else {
298                 flags = 0;
299         }
300
301         if ((sc = tapcreate(dev, flags)) == NULL)
302                 return (ENOMEM);
303
304         sc->tap_flags |= TAP_CLONE;
305
306         TAPDEBUG(&sc->tap_if, "clone created, minor = %#x, flags = 0x%x\n",
307                  minor(sc->tap_dev), sc->tap_flags);
308
309         return (0);
310 }
311
312 /*
313  * Open the tap device.
314  */
315 static int
316 tapopen(struct dev_open_args *ap)
317 {
318         cdev_t dev = NULL;
319         struct tap_softc *sc = NULL;
320         struct ifnet *ifp = NULL;
321         int error;
322
323         if (tapuopen == 0 &&
324             (error = priv_check_cred(ap->a_cred, PRIV_ROOT, 0)) != 0)
325                 return (error);
326
327         get_mplock();
328
329         dev = ap->a_head.a_dev;
330         sc = dev->si_drv1;
331         if (sc == NULL && (sc = tapcreate(dev, 0)) == NULL) {
332                 rel_mplock();
333                 return (ENOMEM);
334         }
335         if (sc->tap_flags & TAP_OPEN) {
336                 rel_mplock();
337                 return (EBUSY);
338         }
339
340         ifp = &sc->tap_if;
341         bcopy(sc->arpcom.ac_enaddr, sc->ether_addr, sizeof(sc->ether_addr));
342
343         if (curthread->td_proc)
344                 fsetown(curthread->td_proc->p_pid, &sc->tap_sigtd);
345         sc->tap_flags |= TAP_OPEN;
346         taprefcnt++;
347
348         if (tapuponopen && (ifp->if_flags & IFF_UP) == 0) {
349                 crit_enter();
350                 if_up(ifp);
351                 crit_exit();
352
353                 ifnet_serialize_all(ifp);
354                 tapifflags(sc);
355                 ifnet_deserialize_all(ifp);
356
357                 sc->tap_flags |= TAP_CLOSEDOWN;
358         }
359
360         TAPDEBUG(ifp, "opened, minor = %#x. Module refcnt = %d\n",
361                  minor(dev), taprefcnt);
362
363         rel_mplock();
364         return (0);
365 }
366
367 static int
368 tapclone(struct dev_clone_args *ap)
369 {
370         char ifname[IFNAMSIZ];
371         int unit;
372
373         unit = devfs_clone_bitmap_get(&DEVFS_CLONE_BITMAP(tap), 0);
374         ksnprintf(ifname, IFNAMSIZ, "%s%d", TAP, unit);
375         ap->a_dev = make_only_dev(&tap_ops, unit, UID_ROOT, GID_WHEEL,
376                                   0600, "%s", ifname);
377
378         /*
379          * Use the if_clone framework to create cloned device/interface,
380          * so the two clone methods (autoclone device /dev/tap; ifconfig
381          * clone) are consistent and can be mix used.
382          *
383          * Need to pass the cdev_t because the device created by
384          * 'make_only_dev()' doesn't appear in '/dev' yet so that it can't
385          * be found by 'devfs_find_device_by_name()' in 'tap_clone_create()'.
386          */
387         return (if_clone_create(ifname, IFNAMSIZ, NULL, (caddr_t)ap->a_dev));
388 }
389
390 /*
391  * Close the tap device: bring the interface down & delete routing info.
392  */
393 static int
394 tapclose(struct dev_close_args *ap)
395 {
396         cdev_t dev = ap->a_head.a_dev;
397         struct tap_softc *sc = dev->si_drv1;
398         struct ifnet *ifp;
399         int unit = minor(dev);
400         int clear_flags = 0;
401         char ifname[IFNAMSIZ];
402
403         KASSERT(sc != NULL,
404                 ("try closing the already destroyed %s%d", TAP, unit));
405         ifp = &sc->tap_if;
406
407         get_mplock();
408
409         /* Junk all pending output */
410         ifq_purge_all(&ifp->if_snd);
411
412         /*
413          * If the interface is not cloned, we always bring it down.
414          *
415          * If the interface is cloned, then we bring it down during
416          * closing only if it was brought up during opening.
417          */
418         if ((sc->tap_flags & TAP_CLONE) == 0 ||
419             (sc->tap_flags & TAP_CLOSEDOWN)) {
420                 if (ifp->if_flags & IFF_UP)
421                         if_down(ifp);
422                 clear_flags = 1;
423         }
424         ifnet_serialize_all(ifp);
425         tapifstop(sc, clear_flags);
426         ifnet_deserialize_all(ifp);
427
428         if ((sc->tap_flags & TAP_MANUALMAKE) == 0) {
429                 if_purgeaddrs_nolink(ifp);
430
431                 EVENTHANDLER_INVOKE(ifnet_detach_event, ifp);
432
433                 /* Announce the departure of the interface. */
434                 rt_ifannouncemsg(ifp, IFAN_DEPARTURE);
435         }
436
437         funsetown(&sc->tap_sigio);
438         sc->tap_sigio = NULL;
439         KNOTE(&sc->tap_rkq.ki_note, 0);
440
441         sc->tap_flags &= ~TAP_OPEN;
442         funsetown(&sc->tap_sigtd);
443         sc->tap_sigtd = NULL;
444
445         taprefcnt--;
446         if (taprefcnt < 0) {
447                 taprefcnt = 0;
448                 if_printf(ifp, ". Module refcnt = %d is out of sync! "
449                           "Force refcnt to be 0.\n", taprefcnt);
450         }
451
452         TAPDEBUG(ifp, "closed, minor = %#x. Module refcnt = %d\n",
453                  unit, taprefcnt);
454
455         /* Only auto-destroy if the interface was not manually created. */
456         if ((sc->tap_flags & TAP_MANUALMAKE) == 0) {
457                 ksnprintf(ifname, IFNAMSIZ, "%s%d", TAP, unit);
458                 if_clone_destroy(ifname);
459         }
460
461         rel_mplock();
462         return (0);
463 }
464
465
466 /*
467  * Destroy a tap instance: the interface and the associated device.
468  */
469 static void
470 tapdestroy(struct tap_softc *sc)
471 {
472         struct ifnet *ifp = &sc->tap_if;
473         cdev_t dev = sc->tap_dev;
474         int unit = minor(dev);
475
476         TAPDEBUG(ifp, "destroyed, minor = %#x. Module refcnt = %d\n",
477                  unit, taprefcnt);
478
479         ifnet_serialize_all(ifp);
480         tapifstop(sc, 1);
481         ifnet_deserialize_all(ifp);
482         ether_ifdetach(ifp);
483
484         sc->tap_dev = NULL;
485         dev->si_drv1 = NULL;
486         release_dev(dev); /* device disassociation */
487
488         /* Also destroy the cloned device */
489         destroy_dev(dev);
490         devfs_clone_bitmap_put(&DEVFS_CLONE_BITMAP(tap), unit);
491
492         SLIST_REMOVE(&tap_listhead, sc, tap_softc, tap_link);
493         kfree(sc, M_TAP);
494 }
495
496
497 /*
498  * Destroy a tap instance that is created via ifconfig.
499  */
500 static int
501 tap_clone_destroy(struct ifnet *ifp)
502 {
503         struct tap_softc *sc = ifp->if_softc;
504
505         if (sc->tap_flags & TAP_OPEN)
506                 return (EBUSY);
507         if ((sc->tap_flags & TAP_CLONE) == 0)
508                 return (EINVAL);
509
510         TAPDEBUG(ifp, "clone destroyed, minor = %#x, flags = 0x%x\n",
511                  minor(sc->tap_dev), sc->tap_flags);
512         tapdestroy(sc);
513
514         return (0);
515 }
516
517
518 /*
519  * tapifinit
520  *
521  * Network interface initialization function (called with if serializer held)
522  *
523  * MPSAFE
524  */
525 static void
526 tapifinit(void *xtp)
527 {
528         struct tap_softc *sc = xtp;
529         struct ifnet *ifp = &sc->tap_if;
530         struct ifaltq_subque *ifsq = ifq_get_subq_default(&ifp->if_snd);
531
532         TAPDEBUG(ifp, "initializing, minor = %#x, flags = 0x%x\n",
533                  minor(sc->tap_dev), sc->tap_flags);
534
535         ASSERT_IFNET_SERIALIZED_ALL(ifp);
536
537         tapifstop(sc, 1);
538
539         ifp->if_flags |= IFF_RUNNING;
540         ifsq_clr_oactive(ifsq);
541
542         /* attempt to start output */
543         tapifstart(ifp, ifsq);
544 }
545
546 static void
547 tapifflags(struct tap_softc *sc)
548 {
549         struct ifnet *ifp = &sc->tap_if;
550
551         ASSERT_IFNET_SERIALIZED_ALL(ifp);
552
553         if (ifp->if_flags & IFF_UP) {
554                 if ((ifp->if_flags & IFF_RUNNING) == 0)
555                         tapifinit(sc);
556         } else {
557                 tapifstop(sc, 1);
558         }
559 }
560
561 /*
562  * tapifioctl
563  *
564  * Process an ioctl request on network interface (called with if serializer
565  * held).
566  *
567  * MPSAFE
568  */
569 static int
570 tapifioctl(struct ifnet *ifp, u_long cmd, caddr_t data, struct ucred *cr)
571 {
572         struct tap_softc *sc = ifp->if_softc;
573         struct ifreq *ifr = NULL;
574         struct ifstat *ifs = NULL;
575         struct ifmediareq *ifmr = NULL;
576         int error = 0;
577         int dummy;
578
579         switch (cmd) {
580         case SIOCADDMULTI:
581         case SIOCDELMULTI:
582                 break;
583
584         case SIOCSIFMTU:
585                 ifr = (struct ifreq *)data;
586                 ifp->if_mtu = ifr->ifr_mtu;
587                 TAPDEBUG(ifp, "mtu set\n");
588                 break;
589
590         case SIOCSIFADDR:
591         case SIOCGIFADDR:
592                 error = ether_ioctl(ifp, cmd, data);
593                 break;
594
595         case SIOCSIFFLAGS:
596                 tapifflags(sc);
597                 break;
598
599         case SIOCGIFMEDIA:
600                 /*
601                  * The bridge code needs this when running the
602                  * spanning tree protocol.
603                  */
604                 ifmr = (struct ifmediareq *)data;
605                 dummy = ifmr->ifm_count;
606                 ifmr->ifm_count = 1;
607                 ifmr->ifm_status = IFM_AVALID;
608                 ifmr->ifm_active = IFM_ETHER;
609                 if (sc->tap_flags & TAP_OPEN)
610                         ifmr->ifm_status |= IFM_ACTIVE;
611                 ifmr->ifm_current = ifmr->ifm_active;
612                 if (dummy >= 1) {
613                         int media = IFM_ETHER;
614                         error = copyout(&media, ifmr->ifm_ulist, sizeof(int));
615                 }
616                 break;
617
618         case SIOCGIFSTATUS:
619                 ifs = (struct ifstat *)data;
620                 dummy = strlen(ifs->ascii);
621                 if ((sc->tap_flags & TAP_OPEN) && dummy < sizeof(ifs->ascii)) {
622                         if (sc->tap_sigtd && sc->tap_sigtd->sio_proc) {
623                                 ksnprintf(ifs->ascii + dummy,
624                                     sizeof(ifs->ascii) - dummy,
625                                     "\tOpened by pid %d\n",
626                                     (int)sc->tap_sigtd->sio_proc->p_pid);
627                         } else {
628                                 ksnprintf(ifs->ascii + dummy,
629                                     sizeof(ifs->ascii) - dummy,
630                                     "\tOpened by <unknown>\n");
631                         }
632                 }
633                 break;
634
635         default:
636                 error = EINVAL;
637                 break;
638         }
639
640         return (error);
641 }
642
643 /*
644  * tapifstart
645  *
646  * Queue packets from higher level ready to put out (called with if serializer
647  * held)
648  *
649  * MPSAFE
650  */
651 static void
652 tapifstart(struct ifnet *ifp, struct ifaltq_subque *ifsq)
653 {
654         struct tap_softc *sc = ifp->if_softc;
655         struct ifqueue *ifq;
656         struct mbuf *m;
657         int has_data = 0;
658
659         ASSERT_ALTQ_SQ_DEFAULT(ifp, ifsq);
660         TAPDEBUG(ifp, "starting, minor = %#x\n", minor(sc->tap_dev));
661
662         if ((sc->tap_flags & TAP_READY) != TAP_READY) {
663                 TAPDEBUG(ifp, "not ready, minor = %#x, flags = 0x%x\n",
664                          minor(sc->tap_dev), sc->tap_flags);
665                 ifsq_purge(ifsq);
666                 return;
667         }
668
669         ifsq_set_oactive(ifsq);
670
671         ifq = &sc->tap_devq;
672         while ((m = ifsq_dequeue(ifsq)) != NULL) {
673                 if (IF_QFULL(ifq)) {
674                         IF_DROP(ifq);
675                         IFNET_STAT_INC(ifp, oerrors, 1);
676                         m_freem(m);
677                 } else {
678                         IF_ENQUEUE(ifq, m);
679                         IFNET_STAT_INC(ifp, opackets, 1);
680                         has_data = 1;
681                 }
682         }
683
684         if (has_data) {
685                 if (sc->tap_flags & TAP_RWAIT) {
686                         sc->tap_flags &= ~TAP_RWAIT;
687                         wakeup((caddr_t)sc);
688                 }
689
690                 KNOTE(&sc->tap_rkq.ki_note, 0);
691
692                 if ((sc->tap_flags & TAP_ASYNC) && (sc->tap_sigio != NULL)) {
693                         get_mplock();
694                         pgsigio(sc->tap_sigio, SIGIO, 0);
695                         rel_mplock();
696                 }
697         }
698
699         ifsq_clr_oactive(ifsq);
700 }
701
702 static void
703 tapifstop(struct tap_softc *sc, int clear_flags)
704 {
705         struct ifnet *ifp = &sc->tap_if;
706
707         ASSERT_IFNET_SERIALIZED_ALL(ifp);
708         IF_DRAIN(&sc->tap_devq);
709         sc->tap_flags &= ~TAP_CLOSEDOWN;
710         if (clear_flags) {
711                 ifp->if_flags &= ~IFF_RUNNING;
712                 ifsq_clr_oactive(ifq_get_subq_default(&ifp->if_snd));
713         }
714 }
715
716 /*
717  * tapioctl
718  *
719  * The ops interface is now pretty minimal.  Called via fileops with nothing
720  * held.
721  *
722  * MPSAFE
723  */
724 static int
725 tapioctl(struct dev_ioctl_args *ap)
726 {
727         cdev_t dev = ap->a_head.a_dev;
728         caddr_t data = ap->a_data;
729         struct tap_softc *sc = dev->si_drv1;
730         struct ifnet *ifp = &sc->tap_if;
731         struct ifreq *ifr;
732         struct tapinfo *tapp = NULL;
733         struct mbuf *mb;
734         int error;
735
736         ifnet_serialize_all(ifp);
737         error = 0;
738
739         switch (ap->a_cmd) {
740         case TAPSIFINFO:
741                 tapp = (struct tapinfo *)data;
742                 if (ifp->if_type != tapp->type)
743                         return (EPROTOTYPE);
744                 ifp->if_mtu = tapp->mtu;
745                 ifp->if_baudrate = tapp->baudrate;
746                 break;
747
748         case TAPGIFINFO:
749                 tapp = (struct tapinfo *)data;
750                 tapp->mtu = ifp->if_mtu;
751                 tapp->type = ifp->if_type;
752                 tapp->baudrate = ifp->if_baudrate;
753                 break;
754
755         case TAPGIFNAME:
756                 ifr = (struct ifreq *)data;
757                 strlcpy(ifr->ifr_name, ifp->if_xname, IFNAMSIZ);
758                 break;
759
760         case TAPSDEBUG:
761                 tapdebug = *(int *)data;
762                 break;
763
764         case TAPGDEBUG:
765                 *(int *)data = tapdebug;
766                 break;
767
768         case FIOASYNC:
769                 if (*(int *)data)
770                         sc->tap_flags |= TAP_ASYNC;
771                 else
772                         sc->tap_flags &= ~TAP_ASYNC;
773                 break;
774
775         case FIONREAD:
776                 /* Take a look at devq first */
777                 IF_POLL(&sc->tap_devq, mb);
778                 if (mb != NULL) {
779                         *(int *)data = 0;
780                         for(; mb != NULL; mb = mb->m_next)
781                                 *(int *)data += mb->m_len;
782                 } else {
783                         *(int *)data = ifsq_poll_pktlen(
784                             ifq_get_subq_default(&ifp->if_snd));
785                 }
786                 break;
787
788         case FIOSETOWN:
789                 error = fsetown(*(int *)data, &sc->tap_sigio);
790                 if (error == 0)
791                         error = fsetown(*(int *)data, &sc->tap_sigtd);
792                 break;
793
794         case FIOGETOWN:
795                 *(int *)data = fgetown(&sc->tap_sigio);
796                 break;
797
798         /* this is deprecated, FIOSETOWN should be used instead */
799         case TIOCSPGRP:
800                 error = fsetown(-(*(int *)data), &sc->tap_sigio);
801                 break;
802
803         /* this is deprecated, FIOGETOWN should be used instead */
804         case TIOCGPGRP:
805                 *(int *)data = -fgetown(&sc->tap_sigio);
806                 break;
807
808         /*
809          * Support basic control of the network interface via the device file.
810          * e.g., vke(4) currently uses the 'SIOCGIFADDR' ioctl.
811          */
812
813         case SIOCGIFFLAGS:
814                 bcopy(&ifp->if_flags, data, sizeof(ifp->if_flags));
815                 break;
816
817         case SIOCGIFADDR:
818                 bcopy(sc->ether_addr, data, sizeof(sc->ether_addr));
819                 break;
820
821         case SIOCSIFADDR:
822                 bcopy(data, sc->ether_addr, sizeof(sc->ether_addr));
823                 break;
824
825         default:
826                 error = ENOTTY;
827                 break;
828         }
829
830         ifnet_deserialize_all(ifp);
831         return (error);
832 }
833
834
835 /*
836  * tapread
837  *
838  * The ops read interface - reads a packet at a time, or at
839  * least as much of a packet as can be read.
840  *
841  * Called from the fileops interface with nothing held.
842  *
843  * MPSAFE
844  */
845 static int
846 tapread(struct dev_read_args *ap)
847 {
848         cdev_t dev = ap->a_head.a_dev;
849         struct uio *uio = ap->a_uio;
850         struct tap_softc *sc = dev->si_drv1;
851         struct ifnet *ifp = &sc->tap_if;
852         struct mbuf *m0 = NULL;
853         int error = 0, len;
854
855         TAPDEBUG(ifp, "reading, minor = %#x\n", minor(dev));
856
857         if ((sc->tap_flags & TAP_READY) != TAP_READY) {
858                 TAPDEBUG(ifp, "not ready, minor = %#x, flags = 0x%x\n",
859                          minor(dev), sc->tap_flags);
860
861                 return (EHOSTDOWN);
862         }
863
864         sc->tap_flags &= ~TAP_RWAIT;
865
866         /* sleep until we get a packet */
867         do {
868                 ifnet_serialize_all(ifp);
869                 IF_DEQUEUE(&sc->tap_devq, m0);
870                 if (m0 == NULL) {
871                         if (ap->a_ioflag & IO_NDELAY) {
872                                 ifnet_deserialize_all(ifp);
873                                 return (EWOULDBLOCK);
874                         }
875                         sc->tap_flags |= TAP_RWAIT;
876                         tsleep_interlock(sc, PCATCH);
877                         ifnet_deserialize_all(ifp);
878                         error = tsleep(sc, PCATCH | PINTERLOCKED, "taprd", 0);
879                         if (error)
880                                 return (error);
881                 } else {
882                         ifnet_deserialize_all(ifp);
883                 }
884         } while (m0 == NULL);
885
886         BPF_MTAP(ifp, m0);
887
888         /* xfer packet to user space */
889         while ((m0 != NULL) && (uio->uio_resid > 0) && (error == 0)) {
890                 len = (int)szmin(uio->uio_resid, m0->m_len);
891                 if (len == 0)
892                         break;
893
894                 error = uiomove(mtod(m0, caddr_t), (size_t)len, uio);
895                 m0 = m_free(m0);
896         }
897
898         if (m0 != NULL) {
899                 TAPDEBUG(ifp, "dropping mbuf, minor = %#x\n", minor(dev));
900                 m_freem(m0);
901         }
902
903         return (error);
904 }
905
906 /*
907  * tapwrite
908  *
909  * The ops write interface - an atomic write is a packet - or else!
910  *
911  * Called from the fileops interface with nothing held.
912  *
913  * MPSAFE
914  */
915 static int
916 tapwrite(struct dev_write_args *ap)
917 {
918         cdev_t dev = ap->a_head.a_dev;
919         struct uio *uio = ap->a_uio;
920         struct tap_softc *sc = dev->si_drv1;
921         struct ifnet *ifp = &sc->tap_if;
922         struct mbuf *top = NULL, **mp = NULL, *m = NULL;
923         int error;
924         size_t tlen, mlen;
925
926         TAPDEBUG(ifp, "writing, minor = %#x\n", minor(dev));
927
928         if ((sc->tap_flags & TAP_READY) != TAP_READY) {
929                 TAPDEBUG(ifp, "not ready, minor = %#x, flags = 0x%x\n",
930                          minor(dev), sc->tap_flags);
931                 return (EHOSTDOWN);
932         }
933
934         if (uio->uio_resid == 0)
935                 return (0);
936
937         if (uio->uio_resid > TAPMRU) {
938                 TAPDEBUG(ifp, "invalid packet len = %zu, minor = %#x\n",
939                          uio->uio_resid, minor(dev));
940
941                 return (EIO);
942         }
943         tlen = uio->uio_resid;
944
945         /* get a header mbuf */
946         MGETHDR(m, M_WAITOK, MT_DATA);
947         if (m == NULL)
948                 return (ENOBUFS);
949         mlen = MHLEN;
950
951         top = NULL;
952         mp = &top;
953         error = 0;
954
955         while (error == 0 && uio->uio_resid > 0) {
956                 m->m_len = (int)szmin(mlen, uio->uio_resid);
957                 error = uiomove(mtod(m, caddr_t), (size_t)m->m_len, uio);
958                 *mp = m;
959                 mp = &m->m_next;
960                 if (uio->uio_resid > 0) {
961                         MGET(m, M_WAITOK, MT_DATA);
962                         if (m == NULL) {
963                                 error = ENOBUFS;
964                                 break;
965                         }
966                         mlen = MLEN;
967                 }
968         }
969         if (error) {
970                 IFNET_STAT_INC(ifp, ierrors, 1);
971                 if (top)
972                         m_freem(top);
973                 return (error);
974         }
975
976         top->m_pkthdr.len = (int)tlen;
977         top->m_pkthdr.rcvif = ifp;
978
979         /*
980          * Ethernet bridge and bpf are handled in ether_input
981          *
982          * adjust mbuf and give packet to the ether_input
983          */
984         ifnet_serialize_all(ifp);
985         ifp->if_input(ifp, top, NULL, -1);
986         IFNET_STAT_INC(ifp, ipackets, 1); /* ibytes are counted in ether_input */
987         ifnet_deserialize_all(ifp);
988
989         return (0);
990 }
991
992
993 /*
994  * tapkqfilter - called from the fileops interface with nothing held
995  *
996  * MPSAFE
997  */
998 static int
999 tapkqfilter(struct dev_kqfilter_args *ap)
1000 {
1001         cdev_t dev = ap->a_head.a_dev;
1002         struct knote *kn = ap->a_kn;
1003         struct tap_softc *sc = dev->si_drv1;
1004         struct klist *list;
1005
1006         list = &sc->tap_rkq.ki_note;
1007         ap->a_result =0;
1008
1009         switch (kn->kn_filter) {
1010         case EVFILT_READ:
1011                 kn->kn_fop = &tapread_filtops;
1012                 kn->kn_hook = (void *)sc;
1013                 break;
1014         case EVFILT_WRITE:
1015                 kn->kn_fop = &tapwrite_filtops;
1016                 kn->kn_hook = (void *)sc;
1017                 break;
1018         default:
1019                 ap->a_result = EOPNOTSUPP;
1020                 return (0);
1021         }
1022
1023         knote_insert(list, kn);
1024         return (0);
1025 }
1026
1027 static int
1028 tap_filter_read(struct knote *kn, long hint)
1029 {
1030         struct tap_softc *sc = (struct tap_softc *)kn->kn_hook;
1031
1032         if (IF_QEMPTY(&sc->tap_devq) == 0)      /* XXX serializer */
1033                 return (1);
1034         else
1035                 return (0);
1036 }
1037
1038 static int
1039 tap_filter_write(struct knote *kn, long hint)
1040 {
1041         /* Always ready for a write */
1042         return (1);
1043 }
1044
1045 static void
1046 tap_filter_detach(struct knote *kn)
1047 {
1048         struct tap_softc *sc = (struct tap_softc *)kn->kn_hook;
1049
1050         knote_remove(&sc->tap_rkq.ki_note, kn);
1051 }