Date: Fri, 4 Mar 2005 00:24:58 +0100 From: Pawel Jakub Dawidek <pjd@FreeBSD.org> To: Luigi Rizzo <rizzo@icir.org> Cc: net@FreeBSD.org Subject: Re: Giant-free polling [PATCH] Message-ID: <20050303232458.GO9291@darkness.comp.waw.pl> In-Reply-To: <20050301162949.A64187@xorpc.icir.org> References: <E1D1nPr-000IE5-00._pppp-mail-ru@f37.mail.ru> <20050217161031.A46700@xorpc.icir.org> <200503011642.48813.jhb@FreeBSD.org> <20050301162949.A64187@xorpc.icir.org>
next in thread | previous in thread | raw e-mail | index | archive | help
[-- Attachment #1 --]
On Tue, Mar 01, 2005 at 04:29:49PM -0800, Luigi Rizzo wrote:
+> [cc-ing net@freebsd.org to get more opinions]
+>
+> On Tue, Mar 01, 2005 at 04:42:48PM -0500, John Baldwin wrote:
+> > On Thursday 17 February 2005 07:10 pm, Luigi Rizzo wrote:
+> > > i am no expert about the locking but i see places where
+> > > you grab polling_lock followed by ifnet_lock, and others where
+> > > you use the opposite order. This seems prone to deadlock...
+> >
+> > Yes, it basically seems that the polling_lock should be removed and just the
+> > ifnet_lock used because the the ifnet_lock is already always held when the
+> > polling_lock is locked.
Yeah, but we cannot grap ifnet_lock in polling code, because this is
internal mutex, not visible from outside.
I was thinking about moving ifnet_lock into ifnet structure...
+> this said, if the lock requests are blocking, you basically end
+> up with the polling loops always contending for the locks, with only one
+> doing actual work and the other one always busy-waiting.
+>
+> Assuming the primitive exists, I think the correct way to implement
+> SMP polling is to use non-blocking locks, something like this
+> (in pseudocode)
+>
+> poll_loop() {
+> have_polling_lock = try_get_lock(polling_lock)
+> foreach(ifp in polled_interfaces) {
+> if (have_polling_lock)
+> have_ifp_lock = get_lock(ifp) // returns true
+> else
+> have_ifp_lock = try_get_lock(ifp)
+> if (have_ifp_lock) {
+> ifp->poll();
+> release_lock(ifp)
+> }
+> }
+> if (have_polling_lock)
+> release_lock(polling_lock);
+> }
+>
+> so additional polling processes after the first one will not
+> block on busy interfaces and move forward instead.
+> This should remove a bit of contention, and let separate processes actually
+> work on different interfaces.
I think we should just implement per-interface idlepoll threads, so we can
run polling code on many CPUs for many interfaces.
--
Pawel Jakub Dawidek http://www.wheel.pl
pjd@FreeBSD.org http://www.FreeBSD.org
FreeBSD committer Am I Evil? Yes, I Am!
[-- Attachment #2 --]
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.4 (FreeBSD)
iD8DBQFCJ5zKForvXbEpPzQRAi2lAKC2NdMRuUkUm/0YQuu8bJo6fEM/HwCg0OZy
axqDwvGKiDlorK9INal9ask=
=wq7q
-----END PGP SIGNATURE-----
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20050303232458.GO9291>
