Date: Sat, 16 May 2009 06:49:05 +0000 (UTC) From: Robert Watson <rwatson@FreeBSD.org> To: src-committers@freebsd.org, svn-src-projects@freebsd.org Subject: svn commit: r192190 - projects/pnet/sys/net Message-ID: <200905160649.n4G6n6QG047364@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: rwatson Date: Sat May 16 06:49:05 2009 New Revision: 192190 URL: http://svn.freebsd.org/changeset/base/192190 Log: Add netisr2_dispatch_if() and netisr2_queue_if(), which accept an explicit ifnet argument. For now we just use it to contribute to an overall flow identifier, but in the future we might want to use it as a source of work placement policy. Implement netisr_dispatch() and netisr_queue() for netisr2, which allows existing netisr dispatch points to be used unchanged. These are simple wrappers around netisr2_*_if(), and pass in the mbuf's receieve interface pointer, which will cause netisr2 to distribute work to threads even without protocol- or driver-generated flow IDs. When there's only one netisr2 worker, don't bother with flow IDs, CPU lookups, etc, just use the one thread, avoiding overhead. Rename netisr2_deregister() to netisr2_unregister() to match existing netisr naming convention. Modified: projects/pnet/sys/net/netisr.c projects/pnet/sys/net/netisr2.c projects/pnet/sys/net/netisr2.h Modified: projects/pnet/sys/net/netisr.c ============================================================================== --- projects/pnet/sys/net/netisr.c Sat May 16 06:42:32 2009 (r192189) +++ projects/pnet/sys/net/netisr.c Sat May 16 06:49:05 2009 (r192190) @@ -28,6 +28,7 @@ */ #include "opt_device_polling.h" +#include "opt_netisr.h" #include <sys/param.h> #include <sys/bus.h> @@ -149,6 +150,7 @@ netisr_processqueue(struct netisr *ni) /* * Call the netisr directly instead of queueing the packet, if possible. */ +#ifndef NETISR2 void netisr_dispatch(int num, struct mbuf *m) { @@ -209,6 +211,7 @@ netisr_queue(int num, struct mbuf *m) schednetisr(num); return (0); } +#endif /* !NETISR2 */ static void swi_net(void *dummy) Modified: projects/pnet/sys/net/netisr2.c ============================================================================== --- projects/pnet/sys/net/netisr2.c Sat May 16 06:42:32 2009 (r192189) +++ projects/pnet/sys/net/netisr2.c Sat May 16 06:49:05 2009 (r192190) @@ -352,20 +352,20 @@ netisr2_drain_proto(struct netisr_work * /* * Remove the registration of a network protocol, which requires clearing * per-protocol fields across all workstreams, including freeing all mbufs in - * the queues at time of deregister. All work in netisr2 is briefly + * the queues at time of unregister. All work in netisr2 is briefly * suspended while this takes place. */ void -netisr2_deregister(u_int proto) +netisr2_unregister(u_int proto) { struct netisr_work *npwp; int i; NETISR_WLOCK(); KASSERT(proto < NETISR_MAXPROT, - ("netisr_deregister(%d): protocol too big", proto)); + ("netisr_unregister(%d): protocol too big", proto)); KASSERT(np[proto].np_func != NULL, - ("netisr_deregister(%d): protocol not registered", proto)); + ("netisr_unregister(%d): protocol not registered", proto)); np[proto].np_name = NULL; np[proto].np_func = NULL; @@ -401,6 +401,14 @@ netisr2_selectcpu(struct netisr_proto *n NETISR_LOCK_ASSERT(); + /* + * In the event we have only one worker, shortcut and deliver to it + * without further ado. + */ + if (nws_count == 1) { + *cpuidp = nws_array[0]; + return (m); + } if (!(m->m_flags & M_FLOWID) && npp->np_m2flow != NULL) { m = npp->np_m2flow(m); if (m == NULL) @@ -597,6 +605,20 @@ netisr2_queue(u_int proto, uintptr_t sou } int +netisr2_queue_if(u_int proto, struct ifnet *ifp, struct mbuf *m) +{ + + return (netisr2_queue(proto, (uintptr_t)ifp, m)); +} + +int +netisr_queue(int proto, struct mbuf *m) +{ + + return (netisr2_queue_if(proto, m->m_pkthdr.rcvif, m)); +} + +int netisr2_dispatch(u_int proto, uintptr_t source, struct mbuf *m) { struct netisr_workstream *nwsp; @@ -623,6 +645,20 @@ netisr2_dispatch(u_int proto, uintptr_t return (0); } +int +netisr2_dispatch_if(u_int proto, struct ifnet *ifp, struct mbuf *m) +{ + + return (netisr2_dispatch(proto, (uintptr_t)ifp, m)); +} + +void +netisr_dispatch(int proto, struct mbuf *m) +{ + + (void)netisr2_dispatch_if(proto, m->m_pkthdr.rcvif, m); +} + static void netisr2_start_swi(u_int cpuid, struct pcpu *pc) { Modified: projects/pnet/sys/net/netisr2.h ============================================================================== --- projects/pnet/sys/net/netisr2.h Sat May 16 06:42:32 2009 (r192189) +++ projects/pnet/sys/net/netisr2.h Sat May 16 06:49:05 2009 (r192190) @@ -69,15 +69,19 @@ void netisr2_register(u_int proto, const netisr_m2flow_t m2flow, netisr_flow2cpu_t flow2cpu, u_int max); /* - * Deregister a protocol handler. + * Unregister a protocol handler. */ -void netisr2_deregister(u_int proto); +void netisr2_unregister(u_int proto); /* * Process a packet destined for a protocol, and attempt direct dispatch. */ +//int netisr_dispatch(u_int proto, struct mbuf *m); +//int netisr_queue(u_int proto, struct mbuf *m); int netisr2_dispatch(u_int proto, uintptr_t source, struct mbuf *m); +int netisr2_dispatch_if(u_int proto, struct ifnet *ifp, struct mbuf *m); int netisr2_queue(u_int proto, uintptr_t source, struct mbuf *m); +int netisr2_queue_if(u_int proto, struct ifnet *ifp, struct mbuf *m); /* * Provide a default implementation of "map a flow ID to a cpu ID".
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200905160649.n4G6n6QG047364>