Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 17 Jun 1999 13:10:02 -0700 (PDT)
From:      Bruce Evans <bde@zeta.org.au>
To:        freebsd-bugs@FreeBSD.org
Subject:   Re: kern/12247: userlevel program let kernel hang
Message-ID:  <199906172010.NAA86851@freefall.freebsd.org>

next in thread | raw e-mail | index | archive | help
The following reply was made to PR kern/12247; it has been noted by GNATS.

From: Bruce Evans <bde@zeta.org.au>
To: dirk.meyer@dinoex.sub.org, FreeBSD-gnats-submit@FreeBSD.ORG
Cc:  
Subject: Re: kern/12247: userlevel program let kernel hang
Date: Fri, 18 Jun 1999 06:00:46 +1000

 >>Description:
 >
 >	while debugging a userlevel program
 >	The user can hang the system,
 >	no other processes seem to work.
 
 Try this fix.  tsleep()'s return codes are poorly documented and were
 misinterpreted in lf_setlock().  tsleep() can return 0 if the process
 was restarted by a debugger, `so tsleep() != 0' is not the condition for
 the lock having been removed from the blocked list.  Leaving the lock
 on the list corrupts the list.  In your program, the corrupt list
 happens to be circular and this caused an endless loop in lf_wakelock()
 when the list is traversed.
 
 Bruce
 
 diff -c2 kern_lockf.c~ kern_lockf.c
 *** kern_lockf.c~	Sun May  9 20:42:39 1999
 --- kern_lockf.c	Fri Jun 18 05:37:00 1999
 ***************
 *** 273,290 ****
   		}
   #endif /* LOCKF_DEBUG */
 ! 		if ((error = tsleep((caddr_t)lock, priority, lockstr, 0))) {
 !                         /*
 ! 			 * We may have been awakened by a signal (in
 ! 			 * which case we must remove ourselves from the
 ! 			 * blocked list) and/or by another process
 ! 			 * releasing a lock (in which case we have already
 ! 			 * been removed from the blocked list and our
 ! 			 * lf_next field set to NOLOCKF).
 !                          */
 ! 			if (lock->lf_next)
 ! 				TAILQ_REMOVE(&lock->lf_next->lf_blkhd, lock,
 ! 					lf_block);
 !                         free(lock, M_LOCKF);
 !                         return (error);
   		}
   	}
 --- 273,292 ----
   		}
   #endif /* LOCKF_DEBUG */
 ! 		error = tsleep((caddr_t)lock, priority, lockstr, 0);
 ! 		/*
 ! 		 * We may have been awakened by a signal and/or by a
 ! 		 * debugger continuing us (in which cases we must remove
 ! 		 * ourselves from the blocked list) and/or by another
 ! 		 * process releasing a lock (in which case we have
 ! 		 * already been removed from the blocked list and our
 ! 		 * lf_next field set to NOLOCKF).
 ! 		 */
 ! 		if (lock->lf_next) {
 ! 			TAILQ_REMOVE(&lock->lf_next->lf_blkhd, lock, lf_block);
 ! 			lock->lf_next = NOLOCKF;
 ! 		}
 ! 		if (error) {
 ! 			free(lock, M_LOCKF);
 ! 			return (error);
   		}
   	}
 


To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-bugs" in the body of the message




Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199906172010.NAA86851>