patch (Re: ^Z during port build and hang?)

Matthew Dillon dillon at
Fri Jun 24 11:16:24 PDT 2005

    Try this patch.  There is a race during fork() where a ^Z can cause a
    newly forked process to stop as part of the fork trampoline.  That code
    path was not setting up the passive release function and the process
    retained its 'current process' designation when it went to sleep.  The
    result?  No other user processes can run.

    The thread priority was also not being properly set, possibly giving
    programs that fork a lot (e.g. a make/build) higher priority then the
    rest of the system.


Index: i386/i386/trap.c
RCS file: /cvs/src/sys/i386/i386/trap.c,v
retrieving revision 1.57
diff -u -r1.57 trap.c
--- i386/i386/trap.c	16 Jun 2005 21:12:44 -0000	1.57
+++ i386/i386/trap.c	24 Jun 2005 18:09:06 -0000
@@ -1784,6 +1784,17 @@
 	frame.tf_eflags &= ~PSL_C;	/* success */
 	frame.tf_edx = 1;
+	/*
+	 * Newly forked processes are given a kernel priority.  We have to
+	 * adjust the priority to a normal user priority and fake entry
+	 * into the kernel (call userenter()) to install a passive release
+	 * function just in case userret() decides to stop the process.  This
+	 * can occur when ^Z races a fork.  If we do not install the passive
+	 * release function the current process designation will not be
+	 * released when the thread goes to sleep.
+	 */
+	lwkt_setpri_self(TDPRI_USER_NORM);
+	userenter(p->p_thread);
 	userret(p, &frame, 0);
 #ifdef KTRACE
 	if (KTRPOINT(p->p_thread, KTR_SYSRET))

More information about the Bugs mailing list