changeset 10887:25ca697b9a84

6895172 CR 6762445 was too aggressive; signals are blocked in lwp_mutex_lock()
author Roger A. Faulkner <Roger.Faulkner@Sun.COM>
date Tue, 27 Oct 2009 10:50:50 -0700
parents 552a766979f8
children a32f4a9013e5
files usr/src/cmd/truss/systable.c usr/src/lib/brand/solaris10/s10_brand/common/s10_brand.c usr/src/lib/libc/common/sys/syslwp.s usr/src/lib/libc/inc/thr_uberdata.h usr/src/lib/libc/port/sys/lwp.c usr/src/lib/libc/port/sys/lwp_cond.c usr/src/lib/libc/port/threads/synch.c usr/src/uts/common/brand/solaris10/s10_brand.c usr/src/uts/common/os/sysent.c usr/src/uts/common/syscall/lwp_sobj.c
diffstat 10 files changed, 90 insertions(+), 75 deletions(-) [+]
line wrap: on
line diff
--- a/usr/src/cmd/truss/systable.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/cmd/truss/systable.c	Tue Oct 27 10:50:50 2009 -0700
@@ -430,7 +430,7 @@
 {"pset",	5, DEC, NOV, DEC, HEX, HEX, HEX, HEX},		/* 207 */
 {"sparc_utrap_install", 5, DEC, NOV, UTT, UTH, UTH, HEX, HEX},	/* 208 */
 {"resolvepath",	3, DEC, NOV, STG, RLK, DEC},			/* 209 */
-{"lwp_mutex_timedlock", 2, DEC, NOV, HEX, HEX},			/* 210 */
+{"lwp_mutex_timedlock", 3, DEC, NOV, HEX, HEX, HEX},		/* 210 */
 {"lwp_sema_timedwait", 3, DEC, NOV, HEX, HEX, DEC},		/* 211 */
 {"lwp_rwlock_sys", 3, DEC, NOV, DEC, HEX, HEX},			/* 212 */
 {"getdents64",	3, DEC, NOV, DEC, HEX, UNS},			/* 213 */
@@ -471,7 +471,7 @@
 {"ntp_gettime",	1, DEC, NOV, HEX},				/* 248 */
 {"ntp_adjtime",	1, DEC, NOV, HEX},				/* 249 */
 {"lwp_mutex_unlock", 1, DEC, NOV, HEX},				/* 250 */
-{"lwp_mutex_trylock", 1, DEC, NOV, HEX},			/* 251 */
+{"lwp_mutex_trylock", 2, DEC, NOV, HEX, HEX},			/* 251 */
 {"lwp_mutex_register", 2, DEC, NOV, HEX, HEX},			/* 252 */
 {"cladm",	3, DEC, NOV, CLC, CLF, HEX},			/* 253 */
 {"uucopy",	3, DEC, NOV, HEX, HEX, UNS},			/* 254 */
--- a/usr/src/lib/brand/solaris10/s10_brand/common/s10_brand.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/lib/brand/solaris10/s10_brand/common/s10_brand.c	Tue Oct 27 10:50:50 2009 -0700
@@ -1233,6 +1233,25 @@
 #endif	/* __x86 */
 
 /*
+ * The Opensolaris versions of lwp_mutex_timedlock() and lwp_mutex_trylock()
+ * add an extra argument to the interfaces, a uintptr_t value for the mutex's
+ * mutex_owner field.  The Solaris 10 libc assigns the mutex_owner field at
+ * user-level, so we just make the extra argument be zero in both syscalls.
+ */
+
+static int
+s10_lwp_mutex_timedlock(sysret_t *rval, lwp_mutex_t *lp, timespec_t *tsp)
+{
+	return (__systemcall(rval, SYS_lwp_mutex_timedlock + 1024, lp, tsp, 0));
+}
+
+static int
+s10_lwp_mutex_trylock(sysret_t *rval, lwp_mutex_t *lp)
+{
+	return (__systemcall(rval, SYS_lwp_mutex_trylock + 1024, lp, 0));
+}
+
+/*
  * If the emul_global_zone flag is set then emulate some aspects of the
  * zone system call.  In particular, emulate the global zone ID on the
  * ZONE_LOOKUP subcommand and emulate some of the global zone attributes
@@ -1775,7 +1794,7 @@
 	NOSYS,					/* 207 */
 	NOSYS,					/* 208 */
 	NOSYS,					/* 209 */
-	NOSYS,					/* 210 */
+	EMULATE(s10_lwp_mutex_timedlock, 2 | RV_DEFAULT),	/* 210 */
 	NOSYS,					/* 211 */
 	NOSYS,					/* 212 */
 	NOSYS,					/* 213 */
@@ -1820,7 +1839,7 @@
 	NOSYS,					/* 248 */
 	NOSYS,					/* 249 */
 	NOSYS,					/* 250 */
-	NOSYS,					/* 251 */
+	EMULATE(s10_lwp_mutex_trylock, 1 | RV_DEFAULT),		/* 251 */
 	NOSYS,					/* 252 */
 	NOSYS,					/* 253 */
 	NOSYS,					/* 254 */
--- a/usr/src/lib/libc/common/sys/syslwp.s	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/lib/libc/common/sys/syslwp.s	Tue Oct 27 10:50:50 2009 -0700
@@ -107,7 +107,7 @@
 
 /*
  * int
- * ___lwp_mutex_timedlock(lwp_mutex_t *, timespec_t *)
+ * ___lwp_mutex_timedlock(lwp_mutex_t *, timespec_t *, uintptr_t)
  */
 	SYSREENTRY(___lwp_mutex_timedlock)
 	SYSTRAP_RVAL1(lwp_mutex_timedlock)
@@ -205,7 +205,7 @@
 
 /*
  * int
- * ___lwp_mutex_trylock(lwp_mutex_t *mp)
+ * ___lwp_mutex_trylock(lwp_mutex_t *mp, uintptr_t)
  */
 	ENTRY(___lwp_mutex_trylock)
 	SYSTRAP_RVAL1(lwp_mutex_trylock)
--- a/usr/src/lib/libc/inc/thr_uberdata.h	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/lib/libc/inc/thr_uberdata.h	Tue Oct 27 10:50:50 2009 -0700
@@ -1417,8 +1417,8 @@
  * System call wrappers (direct interfaces to the kernel)
  */
 extern	int	___lwp_mutex_register(mutex_t *, mutex_t **);
-extern	int	___lwp_mutex_trylock(mutex_t *);
-extern	int	___lwp_mutex_timedlock(mutex_t *, timespec_t *);
+extern	int	___lwp_mutex_trylock(mutex_t *, ulwp_t *);
+extern	int	___lwp_mutex_timedlock(mutex_t *, timespec_t *, ulwp_t *);
 extern	int	___lwp_mutex_unlock(mutex_t *);
 extern	int	___lwp_mutex_wakeup(mutex_t *, int);
 extern	int	___lwp_cond_wait(cond_t *, mutex_t *, timespec_t *, int);
--- a/usr/src/lib/libc/port/sys/lwp.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/lib/libc/port/sys/lwp.c	Tue Oct 27 10:50:50 2009 -0700
@@ -20,12 +20,10 @@
  */
 
 /*
- * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 #include "lint.h"
 #include "thr_uberdata.h"
 #include <sys/types.h>
@@ -35,15 +33,12 @@
 #include <sys/synch32.h>
 #include <sys/lwp.h>
 
-extern int ___lwp_mutex_timedlock(mutex_t *, timespec_t *);
-extern int ___lwp_sema_timedwait(lwp_sema_t *, timespec_t *, int);
-
 int
 _lwp_mutex_lock(mutex_t *mp)
 {
 	if (set_lock_byte(&mp->mutex_lockw) == 0)
 		return (0);
-	return (___lwp_mutex_timedlock(mp, NULL));
+	return (___lwp_mutex_timedlock(mp, NULL, NULL));
 }
 
 int
--- a/usr/src/lib/libc/port/sys/lwp_cond.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/lib/libc/port/sys/lwp_cond.c	Tue Oct 27 10:50:50 2009 -0700
@@ -20,24 +20,19 @@
  */
 
 /*
- * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
+ * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
  * Use is subject to license terms.
  */
 
-#pragma ident	"%Z%%M%	%I%	%E% SMI"
-
 #include "lint.h"
+#include "thr_uberdata.h"
 #include <sys/types.h>
-
 #include <time.h>
 #include <errno.h>
 #include <synch.h>
 #include <sys/synch32.h>
 #include <pthread.h>
 
-extern int ___lwp_cond_wait(lwp_cond_t *, lwp_mutex_t *, timespec_t *, int);
-extern int ___lwp_mutex_timedlock(lwp_mutex_t *, timespec_t *);
-
 int
 _lwp_cond_wait(cond_t *cv, mutex_t *mp)
 {
@@ -45,7 +40,7 @@
 
 	error = ___lwp_cond_wait(cv, mp, NULL, 0);
 	if (mp->mutex_type & (PTHREAD_PRIO_INHERIT|PTHREAD_PRIO_PROTECT))
-		(void) ___lwp_mutex_timedlock(mp, NULL);
+		(void) ___lwp_mutex_timedlock(mp, NULL, NULL);
 	else
 		(void) _lwp_mutex_lock(mp);
 	return (error);
@@ -61,7 +56,7 @@
 		return (EINVAL);
 	error = ___lwp_cond_wait(cv, mp, relts, 0);
 	if (mp->mutex_type & (PTHREAD_PRIO_INHERIT|PTHREAD_PRIO_PROTECT))
-		(void) ___lwp_mutex_timedlock(mp, NULL);
+		(void) ___lwp_mutex_timedlock(mp, NULL, NULL);
 	else
 		(void) _lwp_mutex_lock(mp);
 	return (error);
--- a/usr/src/lib/libc/port/threads/synch.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/lib/libc/port/threads/synch.c	Tue Oct 27 10:50:50 2009 -0700
@@ -443,8 +443,7 @@
 	 * Give up and block in the kernel for the mutex.
 	 */
 	INCR32(self->ul_spin_lock_sleep);
-	(void) ___lwp_mutex_timedlock(mp, NULL);
-	mp->mutex_owner = (uintptr_t)self;
+	(void) ___lwp_mutex_timedlock(mp, NULL, self);
 }
 
 void
@@ -1002,14 +1001,12 @@
 
 	DTRACE_PROBE1(plockstat, mutex__block, mp);
 
-	/* defer signals until the assignment of mp->mutex_owner */
-	sigoff(self);
 	for (;;) {
 		/*
 		 * A return value of EOWNERDEAD or ELOCKUNMAPPED
 		 * means we successfully acquired the lock.
 		 */
-		if ((error = ___lwp_mutex_timedlock(mp, tsp)) != 0 &&
+		if ((error = ___lwp_mutex_timedlock(mp, tsp, self)) != 0 &&
 		    error != EOWNERDEAD && error != ELOCKUNMAPPED) {
 			acquired = 0;
 			break;
@@ -1022,19 +1019,16 @@
 			 */
 			enter_critical(self);
 			if (mp->mutex_ownerpid == udp->pid) {
-				mp->mutex_owner = (uintptr_t)self;
 				exit_critical(self);
 				acquired = 1;
 				break;
 			}
 			exit_critical(self);
 		} else {
-			mp->mutex_owner = (uintptr_t)self;
 			acquired = 1;
 			break;
 		}
 	}
-	sigon(self);
 
 	if (msp)
 		msp->mutex_sleep_time += gethrtime() - begin_sleep;
@@ -1042,6 +1036,7 @@
 	self->ul_sp = 0;
 
 	if (acquired) {
+		ASSERT(mp->mutex_owner == (uintptr_t)self);
 		DTRACE_PROBE2(plockstat, mutex__blocked, mp, 1);
 		DTRACE_PROBE3(plockstat, mutex__acquire, mp, 0, 0);
 	} else {
@@ -1065,13 +1060,12 @@
 	int error;
 	int acquired;
 
-	sigoff(self);
 	for (;;) {
 		/*
 		 * A return value of EOWNERDEAD or ELOCKUNMAPPED
 		 * means we successfully acquired the lock.
 		 */
-		if ((error = ___lwp_mutex_trylock(mp)) != 0 &&
+		if ((error = ___lwp_mutex_trylock(mp, self)) != 0 &&
 		    error != EOWNERDEAD && error != ELOCKUNMAPPED) {
 			acquired = 0;
 			break;
@@ -1084,21 +1078,19 @@
 			 */
 			enter_critical(self);
 			if (mp->mutex_ownerpid == udp->pid) {
-				mp->mutex_owner = (uintptr_t)self;
 				exit_critical(self);
 				acquired = 1;
 				break;
 			}
 			exit_critical(self);
 		} else {
-			mp->mutex_owner = (uintptr_t)self;
 			acquired = 1;
 			break;
 		}
 	}
-	sigon(self);
 
 	if (acquired) {
+		ASSERT(mp->mutex_owner == (uintptr_t)self);
 		DTRACE_PROBE3(plockstat, mutex__acquire, mp, 0, 0);
 	} else if (error != EBUSY) {
 		DTRACE_PROBE2(plockstat, mutex__error, mp, error);
--- a/usr/src/uts/common/brand/solaris10/s10_brand.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/uts/common/brand/solaris10/s10_brand.c	Tue Oct 27 10:50:50 2009 -0700
@@ -978,8 +978,10 @@
 	s10_emulation_table[SYS_pwrite] = 1;			/* 174 */
 	s10_emulation_table[SYS_auditsys] = 1;			/* 186 */
 	s10_emulation_table[SYS_sigqueue] = 1;			/* 190 */
+	s10_emulation_table[SYS_lwp_mutex_timedlock] = 1;	/* 210 */
 	s10_emulation_table[SYS_pwrite64] = 1;			/* 223 */
 	s10_emulation_table[SYS_zone] = 1;			/* 227 */
+	s10_emulation_table[SYS_lwp_mutex_trylock] = 1;		/* 251 */
 
 	err = mod_install(&modlinkage);
 	if (err) {
--- a/usr/src/uts/common/os/sysent.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/uts/common/os/sysent.c	Tue Oct 27 10:50:50 2009 -0700
@@ -698,7 +698,7 @@
 		SYSENT_CI("sparc_utrap_install", sparc_utrap_install, 5),
 		SYSENT_NOSYS()),
 	/* 209 */ SYSENT_CI("resolvepath",	resolvepath,	3),
-	/* 210 */ SYSENT_CI("lwp_mutex_timedlock", lwp_mutex_timedlock,	2),
+	/* 210 */ SYSENT_CI("lwp_mutex_timedlock", lwp_mutex_timedlock,	3),
 	/* 211 */ SYSENT_CI("lwp_sema_timedwait", lwp_sema_timedwait,	3),
 	/* 212 */ SYSENT_CI("lwp_rwlock_sys",	lwp_rwlock_sys,	3),
 	/*
@@ -772,7 +772,7 @@
 	/* 248 */ SYSENT_CI("ntp_gettime",	ntp_gettime,	1),
 	/* 249 */ SYSENT_CI("ntp_adjtime",	ntp_adjtime,	1),
 	/* 250 */ SYSENT_CI("lwp_mutex_unlock",	lwp_mutex_unlock,	1),
-	/* 251 */ SYSENT_CI("lwp_mutex_trylock", lwp_mutex_trylock,	1),
+	/* 251 */ SYSENT_CI("lwp_mutex_trylock", lwp_mutex_trylock,	2),
 	/* 252 */ SYSENT_CI("lwp_mutex_register", lwp_mutex_register,	2),
 	/* 253 */ SYSENT_CI("cladm",		cladm,		3),
 	/* 254 */ SYSENT_CI("uucopy",		uucopy,		3),
@@ -1074,7 +1074,7 @@
 	/* 207 */ SYSENT_LOADABLE32(),		/* pset */
 	/* 208 */ SYSENT_LOADABLE32(),
 	/* 209 */ SYSENT_CI("resolvepath",	resolvepath,	3),
-	/* 210 */ SYSENT_CI("lwp_mutex_timedlock", lwp_mutex_timedlock, 2),
+	/* 210 */ SYSENT_CI("lwp_mutex_timedlock", lwp_mutex_timedlock, 3),
 	/* 211 */ SYSENT_CI("lwp_sema_timedwait", lwp_sema_timedwait,	3),
 	/* 212 */ SYSENT_CI("lwp_rwlock_sys",	lwp_rwlock_sys,	3),
 	/*
@@ -1118,7 +1118,7 @@
 	/* 248 */ SYSENT_CI("ntp_gettime",	ntp_gettime,	1),
 	/* 249 */ SYSENT_CI("ntp_adjtime",	ntp_adjtime,	1),
 	/* 250 */ SYSENT_CI("lwp_mutex_unlock",	lwp_mutex_unlock,	1),
-	/* 251 */ SYSENT_CI("lwp_mutex_trylock", lwp_mutex_trylock,	1),
+	/* 251 */ SYSENT_CI("lwp_mutex_trylock", lwp_mutex_trylock,	2),
 	/* 252 */ SYSENT_CI("lwp_mutex_register", lwp_mutex_register,	2),
 	/* 253 */ SYSENT_CI("cladm",		cladm,		3),
 	/* 254 */ SYSENT_CI("uucopy",		uucopy,		3),
--- a/usr/src/uts/common/syscall/lwp_sobj.c	Tue Oct 27 07:43:08 2009 -0700
+++ b/usr/src/uts/common/syscall/lwp_sobj.c	Tue Oct 27 10:50:50 2009 -0700
@@ -67,6 +67,8 @@
 static void lwp_change_pri(kthread_t *t, pri_t pri, pri_t *t_prip);
 static void lwp_mutex_cleanup(lwpchan_entry_t *ent, uint16_t lockflg);
 static void lwp_mutex_unregister(void *uaddr);
+static void set_owner_pid(lwp_mutex_t *, uintptr_t, pid_t);
+static int iswanted(kthread_t *, lwpchan_t *);
 
 extern int lwp_cond_signal(lwp_cond_t *cv);
 
@@ -1011,8 +1013,7 @@
 		flag |= LOCK_NOTRECOVERABLE;
 		suword16_noerr(&lp->mutex_flag, flag);
 	}
-	if (type & USYNC_PROCESS)
-		suword32_noerr(&lp->mutex_ownerpid, 0);
+	set_owner_pid(lp, 0, 0);
 	upimutex_unlock((upimutex_t *)upimutex, flag);
 	upilocked = 0;
 out:
@@ -1021,6 +1022,31 @@
 }
 
 /*
+ * Set the owner and ownerpid fields of a user-level mutex.
+ */
+static void
+set_owner_pid(lwp_mutex_t *lp, uintptr_t owner, pid_t pid)
+{
+	union {
+		uint64_t word64;
+		uint32_t word32[2];
+	} un;
+
+	un.word64 = (uint64_t)owner;
+
+	suword32_noerr(&lp->mutex_ownerpid, pid);
+#if defined(_LP64)
+	if (((uintptr_t)lp & (_LONG_LONG_ALIGNMENT - 1)) == 0) { /* aligned */
+		suword64_noerr(&lp->mutex_owner, un.word64);
+		return;
+	}
+#endif
+	/* mutex is unaligned or we are running on a 32-bit kernel */
+	suword32_noerr((uint32_t *)&lp->mutex_owner, un.word32[0]);
+	suword32_noerr((uint32_t *)&lp->mutex_owner + 1, un.word32[1]);
+}
+
+/*
  * Clear the contents of a user-level mutex; return the flags.
  * Used only by upi_dead() and lwp_mutex_cleanup(), below.
  */
@@ -1035,9 +1061,7 @@
 		flag |= lockflg;
 		suword16_noerr(&lp->mutex_flag, flag);
 	}
-	suword32_noerr((uint32_t *)&lp->mutex_owner, 0);
-	suword32_noerr((uint32_t *)&lp->mutex_owner + 1, 0);
-	suword32_noerr(&lp->mutex_ownerpid, 0);
+	set_owner_pid(lp, 0, 0);
 	suword8_noerr(&lp->mutex_rcount, 0);
 
 	return (flag);
@@ -1116,9 +1140,8 @@
 	}
 }
 
-static int iswanted();
 int
-lwp_mutex_timedlock(lwp_mutex_t *lp, timespec_t *tsp)
+lwp_mutex_timedlock(lwp_mutex_t *lp, timespec_t *tsp, uintptr_t owner)
 {
 	kthread_t *t = curthread;
 	klwp_t *lwp = ttolwp(t);
@@ -1178,10 +1201,9 @@
 	if (UPIMUTEX(type)) {
 		no_fault();
 		error = lwp_upimutex_lock(lp, type, UPIMUTEX_BLOCK, &lwpt);
-		if ((type & USYNC_PROCESS) &&
-		    (error == 0 ||
-		    error == EOWNERDEAD || error == ELOCKUNMAPPED))
-			(void) suword32(&lp->mutex_ownerpid, p->p_pid);
+		if (error == 0 || error == EOWNERDEAD || error == ELOCKUNMAPPED)
+			set_owner_pid(lp, owner,
+			    (type & USYNC_PROCESS)? p->p_pid : 0);
 		if (tsp && !time_error)	/* copyout the residual time left */
 			error = lwp_timer_copyout(&lwpt, error);
 		if (error)
@@ -1309,8 +1331,7 @@
 		(void) new_mstate(t, LMS_SYSTEM);
 
 	if (error == 0) {
-		if (type & USYNC_PROCESS)
-			suword32_noerr(&lp->mutex_ownerpid, p->p_pid);
+		set_owner_pid(lp, owner, (type & USYNC_PROCESS)? p->p_pid : 0);
 		if (type & LOCK_ROBUST) {
 			fuword16_noerr(&lp->mutex_flag, &flag);
 			if (flag & (LOCK_OWNERDEAD | LOCK_UNMAPPED)) {
@@ -1339,7 +1360,7 @@
 
 /*
  * Obsolete lwp_mutex_lock() interface, no longer called from libc.
- * libc now calls lwp_mutex_timedlock(lp, NULL).
+ * libc now calls lwp_mutex_timedlock(lp, NULL, NULL).
  * This system call trap continues to exist solely for the benefit
  * of old statically-linked binaries from Solaris 9 and before.
  * It should be removed from the system when we no longer care
@@ -1348,7 +1369,7 @@
 int
 lwp_mutex_lock(lwp_mutex_t *lp)
 {
-	return (lwp_mutex_timedlock(lp, NULL));
+	return (lwp_mutex_timedlock(lp, NULL, NULL));
 }
 
 static int
@@ -1673,8 +1694,7 @@
 		 * unlock the condition variable's mutex. (pagefaults are
 		 * possible here.)
 		 */
-		if (mtype & USYNC_PROCESS)
-			suword32_noerr(&mp->mutex_ownerpid, 0);
+		set_owner_pid(mp, 0, 0);
 		ulock_clear(&mp->mutex_lockw);
 		fuword8_noerr(&mp->mutex_waiters, &waiters);
 		if (waiters != 0) {
@@ -1790,8 +1810,7 @@
 	if (UPIMUTEX(mtype) == 0) {
 		lwpchan_lock(&m_lwpchan, LWPCHAN_MPPOOL);
 		m_locked = 1;
-		if (mtype & USYNC_PROCESS)
-			suword32_noerr(&mp->mutex_ownerpid, 0);
+		set_owner_pid(mp, 0, 0);
 		ulock_clear(&mp->mutex_lockw);
 		fuword8_noerr(&mp->mutex_waiters, &waiters);
 		if (waiters != 0) {
@@ -2567,9 +2586,7 @@
 	/*
 	 * Unlock the rwlock's mutex (pagefaults are possible here).
 	 */
-	suword32_noerr((uint32_t *)&mp->mutex_owner, 0);
-	suword32_noerr((uint32_t *)&mp->mutex_owner + 1, 0);
-	suword32_noerr(&mp->mutex_ownerpid, 0);
+	set_owner_pid(mp, 0, 0);
 	ulock_clear(&mp->mutex_lockw);
 	fuword8_noerr(&mp->mutex_waiters, &mwaiters);
 	if (mwaiters != 0) {
@@ -2668,9 +2685,7 @@
 		lwpchan_lock(&mlwpchan, LWPCHAN_MPPOOL);
 		mlocked = 1;
 	}
-	suword32_noerr((uint32_t *)&mp->mutex_owner, 0);
-	suword32_noerr((uint32_t *)&mp->mutex_owner + 1, 0);
-	suword32_noerr(&mp->mutex_ownerpid, 0);
+	set_owner_pid(mp, 0, 0);
 	ulock_clear(&mp->mutex_lockw);
 	fuword8_noerr(&mp->mutex_waiters, &mwaiters);
 	if (mwaiters != 0) {
@@ -3024,7 +3039,7 @@
 }
 
 int
-lwp_mutex_trylock(lwp_mutex_t *lp)
+lwp_mutex_trylock(lwp_mutex_t *lp, uintptr_t owner)
 {
 	kthread_t *t = curthread;
 	proc_t *p = ttoproc(t);
@@ -3057,10 +3072,9 @@
 	if (UPIMUTEX(type)) {
 		no_fault();
 		error = lwp_upimutex_lock(lp, type, UPIMUTEX_TRY, NULL);
-		if ((type & USYNC_PROCESS) &&
-		    (error == 0 ||
-		    error == EOWNERDEAD || error == ELOCKUNMAPPED))
-			(void) suword32(&lp->mutex_ownerpid, p->p_pid);
+		if (error == 0 || error == EOWNERDEAD || error == ELOCKUNMAPPED)
+			set_owner_pid(lp, owner,
+			    (type & USYNC_PROCESS)? p->p_pid : 0);
 		if (error)
 			return (set_errno(error));
 		return (0);
@@ -3086,8 +3100,7 @@
 	if (!ulock_try(&lp->mutex_lockw))
 		error = EBUSY;
 	else {
-		if (type & USYNC_PROCESS)
-			suword32_noerr(&lp->mutex_ownerpid, p->p_pid);
+		set_owner_pid(lp, owner, (type & USYNC_PROCESS)? p->p_pid : 0);
 		if (type & LOCK_ROBUST) {
 			fuword16_noerr(&lp->mutex_flag, &flag);
 			if (flag & (LOCK_OWNERDEAD | LOCK_UNMAPPED)) {
@@ -3175,8 +3188,7 @@
 			suword16_noerr(&lp->mutex_flag, flag);
 		}
 	}
-	if (type & USYNC_PROCESS)
-		suword32_noerr(&lp->mutex_ownerpid, 0);
+	set_owner_pid(lp, 0, 0);
 	ulock_clear(&lp->mutex_lockw);
 	/*
 	 * Always wake up an lwp (if any) waiting on lwpchan. The woken lwp will