From owner-cvs-src Wed Mar 5 10:55:37 2003 Delivered-To: cvs-src@freebsd.org Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id 2B98837B405 for ; Wed, 5 Mar 2003 10:55:31 -0800 (PST) Received: from mail.speakeasy.net (mail16.speakeasy.net [216.254.0.216]) by mx1.FreeBSD.org (Postfix) with ESMTP id 556CC43FA3 for ; Wed, 5 Mar 2003 10:55:29 -0800 (PST) (envelope-from jhb@FreeBSD.org) Received: (qmail 27192 invoked from network); 5 Mar 2003 18:55:34 -0000 Received: from unknown (HELO server.baldwin.cx) ([216.27.160.63]) (envelope-sender ) by mail16.speakeasy.net (qmail-ldap-1.03) with DES-CBC3-SHA encrypted SMTP for ; 5 Mar 2003 18:55:34 -0000 Received: from laptop.baldwin.cx (gw1.twc.weather.com [216.133.140.1]) by server.baldwin.cx (8.12.6/8.12.6) with ESMTP id h25IqmhT049162; Wed, 5 Mar 2003 13:52:48 -0500 (EST) (envelope-from jhb@FreeBSD.org) Message-ID: X-Mailer: XFMail 1.5.2 on FreeBSD X-Priority: 3 (Normal) Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 8bit MIME-Version: 1.0 In-Reply-To: Date: Wed, 05 Mar 2003 13:55:43 -0500 (EST) From: John Baldwin To: Nate Lawson Subject: Re: cvs commit: src/sys/kern kern_mutex.c Cc: src-committers@FreeBSD.org, cvs-src@FreeBSD.org, cvs-all@FreeBSD.org Sender: owner-cvs-src@FreeBSD.ORG Precedence: bulk List-ID: List-Archive: (Web Archive) List-Help: (List Instructions) List-Subscribe: List-Unsubscribe: X-Loop: FreeBSD.ORG On 05-Mar-2003 Nate Lawson wrote: > On Wed, 5 Mar 2003, John Baldwin wrote: >> If they want to block on a lock they should use mtx_lock(). Cases >> where one might use mtx_trylock() that I can think of is for >> optional optimizations for cases that might otherwise be a lock >> order violation. I.e., if I can lock two X objects, then I can >> bypass having to lock one, stick it on a queue so that some other >> thread can connect it to the other. The only time I have used it >> is in the OOM killer where I need to be able to lock a process I >> am checking while keeping the current target process locked for >> the whole loop. Really, I want the programmer to think carefully >> when they use mtx_trylock() and blindly recursing on a lock might >> result in some hard to track down bugs. > > I have a situation where I am not quite sure if mtx_trylock() is the right > answer. There is a single-phase process for SCSI target instances where > you create a named endpoint and then enable traffic to it. On the disable > route, it is 2-phase where you disable traffic and abort all outstanding > commands. Later, you close the device and the endpoint is freed. The > endpoint needs to stay allocated to accept freed resources as they are > released by aborted commands. > > My issue is with contention for a named endpoint. If one thread enables > traffic to an endpoint and then disables it, it still has the endpoint > allocated. If another thread tries to enable the same endpoint, it needs > to lock the OTHER endpoint, check if it's disabled (freeing it if it is), > and then unlock it. My current locking approach is to lock my own softc, > lock the driver global mtx, and then lock the OTHER thread's softc before > checking if it is enabled. This last bit is a reversal. What if your two threads each have two different endpoints and contend against each other, how would you prevent the deadlock? (i.e. thread A locks A softc, global, block on B softc, while thread B locks B softc and blocks on global). My lack of CAM is probably going to show in this next question, but it seems that you have this endpoint object that both the thread has a pointer to, and CAM has a name table with a pointer to. Why can't you just tell CAM to change its pointer for the given name to yours and leave the old endpoint alone if it's disabled? The old thread can free the data structure later when the device is closed. I suppose you need to be able to read the flag to see if it is disabled or not. One trick you can do that for case is to require that both the softc lock of the owning thread and the global lock be held when that flag is set and then either lock alone is sufficient to test the state of the flag. I'm not sure I have a firm understanding of what exactly you are trying to accomplish though. I wonder why you can't leave the state of enabled/disabled in the actual periph and just move the single periph around between threads. -- John Baldwin <>< http://www.FreeBSD.org/~jhb/ "Power Users Use the Power to Serve!" - http://www.FreeBSD.org/ To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe cvs-src" in the body of the message