From owner-freebsd-hackers@FreeBSD.ORG Thu Sep 4 12:19:08 2008 Return-Path: Delivered-To: freebsd-hackers@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id 79242106564A for ; Thu, 4 Sep 2008 12:19:08 +0000 (UTC) (envelope-from prvs=113326f63d=marc.loerner@hob.de) Received: from mailgate.hob.de (mailgate.hob.de [212.185.199.3]) by mx1.freebsd.org (Postfix) with ESMTP id 329728FC1B for ; Thu, 4 Sep 2008 12:19:08 +0000 (UTC) (envelope-from prvs=113326f63d=marc.loerner@hob.de) Received: from imap.hob.de (mail2.hob.de [172.25.1.102]) by mailgate.hob.de (Postfix) with ESMTP id B752F52010D for ; Thu, 4 Sep 2008 13:59:45 +0200 (CEST) Received: from linux03.hob.de (linux03.hob.de [172.22.0.190]) by imap.hob.de (Postfix on SuSE eMail Server 2.0) with ESMTP id 64945FD217 for ; Thu, 4 Sep 2008 13:59:45 +0200 (CEST) From: Marc =?iso-8859-1?q?L=F6rner?= Organization: hob To: freebsd-hackers@freebsd.org Date: Thu, 4 Sep 2008 14:00:04 +0200 User-Agent: KMail/1.6.2 MIME-Version: 1.0 Content-Disposition: inline Content-Type: text/plain; charset="iso-8859-1" Content-Transfer-Encoding: 7bit Message-Id: <200809041400.04575.marc.loerner@hob.de> Subject: question on asymmetric mtx_[un]lock_sleep X-BeenThere: freebsd-hackers@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: Technical Discussions relating to FreeBSD List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 04 Sep 2008 12:19:08 -0000 Hello, I just read through the code of mutexes and turnstiles and it seems to me that _mtx_lock_sleep and _mtx_unlock_sleep are some kind of asymmetric when turning SMP and adaptive mutexes on in kernel-configuration. On locking the mutex, we try to "quick" obtain the lock. If we can't do this, we look, whether some other thread, that's running, holds the lock and spin until either lock is freed or thread is not running anymore. In that case we try again to obtain the lock "quick". If the thread only stopped running but still holds the lock, we use turnstiles to wake us up, when the thread unlocks the mutex. => That seems to be fine and quite symmetric with _mtx_unlock_sleep!! But if we're spinning and the other thread gave the mutex free, we quick-lock the mutex and don't set up a turnstile. Now on mtx_unlock_sleep: - in FreeBSD6/until revision 1.200 turnstiles were tested on existence. => if turnstile_lookup return NULL we only released the lock quick. - But now, it's never tested if turnstile exists instead we broadcast/wakeup all threads pending on the turnstile. If this turnstile is NULL => we access wrong memory. Now my question is: Why can we be sure (in new source) that turnstile_lookup always returns a valid pointer to an turnstile and can use returned pointer to call turnstile_broadcast? Am I missing something? Because it seems that following scenario may occur: - on locking same scenario as above (=> thread1 now holds the lock) - thread1 is put off the runqueue - thread2 now tries to quick unlock mutex and sees that thread1 holds it => call to mtx_unlock_sleep - now we try to use turnstile-mechanism and call turnstile_lookup => returns NULL because no thread waits for wakeup => we call turnstile_broadcast and crash. Regards, Marc Loerner