Date: Wed, 9 Sep 2009 09:17:31 +0000 (UTC) From: Attilio Rao <attilio@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-8@freebsd.org Subject: svn commit: r197023 - stable/8/sys/kern Message-ID: <200909090917.n899HVEC079022@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: attilio Date: Wed Sep 9 09:17:31 2009 New Revision: 197023 URL: http://svn.freebsd.org/changeset/base/197023 Log: MFC r196772: fix adaptive spinning in lockmgr by using correctly GIANT_RESTORE and continue statement and improve adaptive spinning for sx lock by just doing once GIANT_SAVE. Approved by: re (kib) Modified: stable/8/sys/kern/ (props changed) stable/8/sys/kern/kern_lock.c stable/8/sys/kern/kern_sx.c Modified: stable/8/sys/kern/kern_lock.c ============================================================================== --- stable/8/sys/kern/kern_lock.c Wed Sep 9 07:45:08 2009 (r197022) +++ stable/8/sys/kern/kern_lock.c Wed Sep 9 09:17:31 2009 (r197023) @@ -467,7 +467,10 @@ __lockmgr_args(struct lock *lk, u_int fl /* * If the owner is running on another CPU, spin until * the owner stops running or the state of the lock - * changes. + * changes. We need a double-state handle here + * because for a failed acquisition the lock can be + * either held in exclusive mode or shared mode + * (for the writer starvation avoidance technique). */ if (LK_CAN_ADAPT(lk, flags) && (x & LK_SHARE) == 0 && LK_HOLDER(x) != LK_KERNPROC) { @@ -491,8 +494,10 @@ __lockmgr_args(struct lock *lk, u_int fl while (LK_HOLDER(lk->lk_lock) == (uintptr_t)owner && TD_IS_RUNNING(owner)) cpu_spinwait(); + GIANT_RESTORE(); + continue; } else if (LK_CAN_ADAPT(lk, flags) && - (x & LK_SHARE) !=0 && LK_SHARERS(x) && + (x & LK_SHARE) != 0 && LK_SHARERS(x) && spintries < alk_retries) { if (flags & LK_INTERLOCK) { class->lc_unlock(ilk); @@ -511,6 +516,7 @@ __lockmgr_args(struct lock *lk, u_int fl break; cpu_spinwait(); } + GIANT_RESTORE(); if (i != alk_loops) continue; } @@ -704,6 +710,8 @@ __lockmgr_args(struct lock *lk, u_int fl while (LK_HOLDER(lk->lk_lock) == (uintptr_t)owner && TD_IS_RUNNING(owner)) cpu_spinwait(); + GIANT_RESTORE(); + continue; } else if (LK_CAN_ADAPT(lk, flags) && (x & LK_SHARE) != 0 && LK_SHARERS(x) && spintries < alk_retries) { @@ -727,6 +735,7 @@ __lockmgr_args(struct lock *lk, u_int fl break; cpu_spinwait(); } + GIANT_RESTORE(); if (i != alk_loops) continue; } Modified: stable/8/sys/kern/kern_sx.c ============================================================================== --- stable/8/sys/kern/kern_sx.c Wed Sep 9 07:45:08 2009 (r197022) +++ stable/8/sys/kern/kern_sx.c Wed Sep 9 09:17:31 2009 (r197023) @@ -531,13 +531,13 @@ _sx_xlock_hard(struct sx *sx, uintptr_t continue; } } else if (SX_SHARERS(x) && spintries < asx_retries) { + GIANT_SAVE(); spintries++; for (i = 0; i < asx_loops; i++) { if (LOCK_LOG_TEST(&sx->lock_object, 0)) CTR4(KTR_LOCK, "%s: shared spinning on %p with %u and %u", __func__, sx, spintries, i); - GIANT_SAVE(); x = sx->sx_lock; if ((x & SX_LOCK_SHARED) == 0 || SX_SHARERS(x) == 0)
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200909090917.n899HVEC079022>