diff options
-rw-r--r-- | share/man/man9/netisr.9 | 9 | ||||
-rw-r--r-- | sys/net/netisr.c | 4 | ||||
-rw-r--r-- | sys/net/netisr.h | 2 |
3 files changed, 14 insertions, 1 deletions
diff --git a/share/man/man9/netisr.9 b/share/man/man9/netisr.9 index d54b6ff..b4062e0 100644 --- a/share/man/man9/netisr.9 +++ b/share/man/man9/netisr.9 @@ -27,7 +27,7 @@ .\" .\" $FreeBSD$ .\" -.Dd June 7, 2009 +.Dd June 14, 2009 .Dt NETISR 9 .Os .Sh NAME @@ -137,6 +137,13 @@ Will be used only with Protocol function to determine what CPU a packet should be processed on. Will be used only with .Dv NETISR_POLICY_CPU . +.It Vt netisr_drainedcpu_t Va nh_drainedcpu +Optional callback function that will be invoked when a per-CPU queue +was drained. +It will never fire for directly dispatched packets. +Unless fully understood, this special-purpose function should not be used. +.\" In case you intend to use this please send 50 chocolate bars to each +.\" of rwatson and bz and wait for an answer. .It Vt u_int Va nh_proto Protocol number used by both protocols to identify themselves to .Nm , diff --git a/sys/net/netisr.c b/sys/net/netisr.c index da5dac4..5dc4c90 100644 --- a/sys/net/netisr.c +++ b/sys/net/netisr.c @@ -197,6 +197,7 @@ struct netisr_proto { netisr_handler_t *np_handler; /* Protocol handler. */ netisr_m2flow_t *np_m2flow; /* Query flow for untagged packet. */ netisr_m2cpuid_t *np_m2cpuid; /* Query CPU to process packet on. */ + netisr_drainedcpu_t *np_drainedcpu; /* Callback when drained a queue. */ u_int np_qlimit; /* Maximum per-CPU queue depth. */ u_int np_policy; /* Work placement policy. */ }; @@ -380,6 +381,7 @@ netisr_register(const struct netisr_handler *nhp) np[proto].np_handler = nhp->nh_handler; np[proto].np_m2flow = nhp->nh_m2flow; np[proto].np_m2cpuid = nhp->nh_m2cpuid; + np[proto].np_drainedcpu = nhp->nh_drainedcpu; if (nhp->nh_qlimit == 0) np[proto].np_qlimit = netisr_defaultqlimit; else if (nhp->nh_qlimit > netisr_maxqlimit) { @@ -705,6 +707,8 @@ netisr_process_workstream_proto(struct netisr_workstream *nwsp, u_int proto) } KASSERT(local_npw.nw_len == 0, ("%s(%u): len %u", __func__, proto, local_npw.nw_len)); + if (np[proto].np_drainedcpu) + np[proto].np_drainedcpu(nwsp->nws_cpu); NWS_LOCK(nwsp); npwp->nw_handled += handled; return (handled); diff --git a/sys/net/netisr.h b/sys/net/netisr.h index 5894d3d..ec7df3a 100644 --- a/sys/net/netisr.h +++ b/sys/net/netisr.h @@ -88,6 +88,7 @@ typedef void netisr_handler_t (struct mbuf *m); typedef struct mbuf *netisr_m2cpuid_t(struct mbuf *m, uintptr_t source, u_int *cpuid); typedef struct mbuf *netisr_m2flow_t(struct mbuf *m, uintptr_t source); +typedef void netisr_drainedcpu_t(u_int cpuid); #define NETISR_POLICY_SOURCE 1 /* Maintain source ordering. */ #define NETISR_POLICY_FLOW 2 /* Maintain flow ordering. */ @@ -101,6 +102,7 @@ struct netisr_handler { netisr_handler_t *nh_handler; /* Protocol handler. */ netisr_m2flow_t *nh_m2flow; /* Query flow for untagged packet. */ netisr_m2cpuid_t *nh_m2cpuid; /* Query CPU to process mbuf on. */ + netisr_drainedcpu_t *nh_drainedcpu; /* Callback when drained a queue. */ u_int nh_proto; /* Integer protocol ID. */ u_int nh_qlimit; /* Maximum per-CPU queue depth. */ u_int nh_policy; /* Work placement policy. */ |