David Gwynne(da...@gwynne.id.au) on 2021.01.27 17:13:09 +1000: > some of the discussion around dup-to made me think that a diff we > have here at work might be more broadly useful. > > we run a box here with a bunch of ethernet ports plugged into span > ports on switches. basically every packet going to our firewalls gets > duplicated to this host. we then have code that generates flow data from > these ports. it's also nice to have one place to ssh to and so you can > tcpdump things. anyway, that flow collector watches packets on those > interfaces via bpf, but apart from that we don't actually want to > do anythign with the packets those interfaces receive. we especially > do not want them entering the stack. we ssh to this box over the > firewall, so if the span port copies those packets to the box and > the stack tries to process them, things dont work great. > > we could enable the fildrop stuff with bpf, but there's an annoying gap > between when the interfaces come up and when the flow collector starts > running. also, if the flow collector crashes or we restart it cos we're > hacking on the code, this provides more gaps for packets to enter the > stack. > > we prevented this by adding a "monitor" interface flag. it makes the > interface input code drop all the packets rather than queuing them for > the stack to process. > > is there any interest in having this in the tree? > > if so, i need to do some work to make sure all interfaces push > packets into the stack with if_input, ifiq_input, or if_vinput. a > bunch of them like gif and gre currently call protocol input routines > directly, so they skip this check. > > so, thoughts?
I'd like this. Previously when i needed something similar, i put the interface into its own routing domain. But of course that doesnt avoid the packets entering the stack, just some consequences. I also think 'monitor' is the right keyword for ifconfig. ok benno, but manpage is missing > Index: sbin/ifconfig/ifconfig.c > =================================================================== > RCS file: /cvs/src/sbin/ifconfig/ifconfig.c,v > retrieving revision 1.432 > diff -u -p -r1.432 ifconfig.c > --- sbin/ifconfig/ifconfig.c 16 Jan 2021 17:44:29 -0000 1.432 > +++ sbin/ifconfig/ifconfig.c 27 Jan 2021 06:57:37 -0000 > @@ -469,6 +469,8 @@ const struct cmd { > { "soii", -IFXF_INET6_NOSOII, 0, setifxflags }, > { "-soii", IFXF_INET6_NOSOII, 0, setifxflags }, > #ifndef SMALL > + { "monitor", IFXF_MONITOR, 0, setifxflags }, > + { "-monitor", -IFXF_MONITOR, 0, setifxflags }, > { "hwfeatures", NEXTARG0, 0, printifhwfeatures }, > { "metric", NEXTARG, 0, setifmetric }, > { "powersave", NEXTARG0, 0, setifpowersave }, > @@ -675,7 +677,7 @@ const struct cmd { > "\7RUNNING\10NOARP\11PROMISC\12ALLMULTI\13OACTIVE\14SIMPLEX" \ > "\15LINK0\16LINK1\17LINK2\20MULTICAST" \ > "\23INET6_NOPRIVACY\24MPLS\25WOL\26AUTOCONF6\27INET6_NOSOII" \ > - "\30AUTOCONF4" > + "\30AUTOCONF4" "\32MONITOR" > > int getinfo(struct ifreq *, int); > void getsock(int); > Index: sys/net/if.c > =================================================================== > RCS file: /cvs/src/sys/net/if.c,v > retrieving revision 1.625 > diff -u -p -r1.625 if.c > --- sys/net/if.c 18 Jan 2021 09:55:43 -0000 1.625 > +++ sys/net/if.c 27 Jan 2021 06:57:37 -0000 > @@ -860,7 +860,8 @@ if_vinput(struct ifnet *ifp, struct mbuf > } > #endif > > - (*ifp->if_input)(ifp, m); > + if (__predict_true(!ISSET(ifp->if_xflags, IFXF_MONITOR))) > + (*ifp->if_input)(ifp, m); > } > > void > Index: sys/net/if.h > =================================================================== > RCS file: /cvs/src/sys/net/if.h,v > retrieving revision 1.205 > diff -u -p -r1.205 if.h > --- sys/net/if.h 18 Jan 2021 09:55:43 -0000 1.205 > +++ sys/net/if.h 27 Jan 2021 06:57:37 -0000 > @@ -230,6 +230,7 @@ struct if_status_description { > #define IFXF_AUTOCONF6 0x20 /* [N] v6 autoconf enabled */ > #define IFXF_INET6_NOSOII 0x40 /* [N] don't do RFC 7217 */ > #define IFXF_AUTOCONF4 0x80 /* [N] v4 autoconf (aka dhcp) > enabled */ > +#define IFXF_MONITOR 0x200 /* [N] only used for bpf */ > > #define IFXF_CANTCHANGE \ > (IFXF_MPSAFE|IFXF_CLONED) > Index: sys/net/ifq.c > =================================================================== > RCS file: /cvs/src/sys/net/ifq.c,v > retrieving revision 1.41 > diff -u -p -r1.41 ifq.c > --- sys/net/ifq.c 7 Jul 2020 00:00:03 -0000 1.41 > +++ sys/net/ifq.c 27 Jan 2021 06:57:37 -0000 > @@ -715,10 +715,12 @@ ifiq_input(struct ifiqueue *ifiq, struct > ifiq->ifiq_bytes += bytes; > > len = ml_len(&ifiq->ifiq_ml); > - if (len > ifiq_maxlen_drop) > - ifiq->ifiq_qdrops += ml_len(ml); > - else > - ml_enlist(&ifiq->ifiq_ml, ml); > + if (__predict_true(!ISSET(ifp->if_xflags, IFXF_MONITOR))) { > + if (len > ifiq_maxlen_drop) > + ifiq->ifiq_qdrops += ml_len(ml); > + else > + ml_enlist(&ifiq->ifiq_ml, ml); > + } > mtx_leave(&ifiq->ifiq_mtx); > > if (ml_empty(ml)) > >