tech-net archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Adding a bpf peers_present function and "peers added/gone" callback



Hey folks,

some drivers (i.e. ieee 802.11 ones) offer bpf tap points that require
quite a bit of work just for the bpf tap and are in a hot network path.

To optimize these at runtime (that is: only do the additional tap if there
are any active peers) I would like to borrow an idea from FreeBSD, but
somehow totally different:

First part is very simple:

 - add a new function bpf_peers_present() that would check for a struct bpf_if*
   if there are any active peers

If this function returns false, the device driver can skip the tap (and all
coresponding copying/setup work).

I would guess this part is non-controversial (and it could even be used
internally to shortcut some of the mtap functions).

Second part is a bit more tricky:

 - in the new IEEE 802.11 stack (due to virtual access points being separated
   from radio hardware, and modes of the VAP partially controlling the DLTs
   used for some internal taps) it would be great to be able to provide
   accumulated results for the bpf_peers_present() return result at the
   radio level (that is where the driver would use it) - this avoids iterating
   over all VAPs and collecting the data for each incoming packet.

   For this to work, we need a callback that gets invoked whenever a peer
   pops up or goes away on the bpf tap.

FreeBSD has a generic EVENTHANDLER interface that is very similar to our
pmf(9). Similar to us "abusing" pmf(9) events for various global machine
state events (lid close, "wifi" button pressed, ...) they also have several
random event types mixed into the list (including "process dumps core",
"kernel module loaded", "mount", "unmount", ...) and especially the one
I am after: bpf_track.

So I could mimic that design and add a pmf(9) event for all bpf_attachd()
and bpf_detachd() calls - but somehow this feels quite strange and I would
prefer to add a bpf specific callback here.

Something like:

#define BPF_TRACK_EVENT_ATTACH	1
#define BPF_TRACK_EVENT_DETACH	2
typedef void (*bpf_track_fn)(struct bpf_if*, struct ifnet *,
    int dlt, int event);

void bpf_register_track_event(struct bpf_if*, bpf_track_fn*);
void bpf_deregister_track_event(struct bpf_if*, bpf_track_fn*);


Implementation is straight forward, any objections or comments on the
interface?

Martin


Home | Main Index | Thread Index | Old Index