From owner-freebsd-threads@FreeBSD.ORG Thu Nov 19 17:55:03 2009 Return-Path: Delivered-To: threads@freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id D9420106566B; Thu, 19 Nov 2009 17:55:02 +0000 (UTC) (envelope-from jhb@freebsd.org) Received: from cyrus.watson.org (cyrus.watson.org [65.122.17.42]) by mx1.freebsd.org (Postfix) with ESMTP id A7F178FC14; Thu, 19 Nov 2009 17:55:02 +0000 (UTC) Received: from bigwig.baldwin.cx (66.111.2.69.static.nyinternet.net [66.111.2.69]) by cyrus.watson.org (Postfix) with ESMTPSA id 319BF46B51; Thu, 19 Nov 2009 12:55:02 -0500 (EST) Received: from jhbbsd.hudson-trading.com (unknown [209.249.190.8]) by bigwig.baldwin.cx (Postfix) with ESMTPA id 624A38A020; Thu, 19 Nov 2009 12:55:01 -0500 (EST) From: John Baldwin To: Daniel Eischen Date: Thu, 19 Nov 2009 12:54:50 -0500 User-Agent: KMail/1.9.7 References: <200911191030.14151.jhb@freebsd.org> <200911191202.30738.jhb@freebsd.org> In-Reply-To: MIME-Version: 1.0 Content-Type: text/plain; charset="iso-8859-1" Content-Transfer-Encoding: 7bit Content-Disposition: inline Message-Id: <200911191254.50902.jhb@freebsd.org> X-Greylist: Sender succeeded SMTP AUTH, not delayed by milter-greylist-4.0.1 (bigwig.baldwin.cx); Thu, 19 Nov 2009 12:55:01 -0500 (EST) X-Virus-Scanned: clamav-milter 0.95.1 at bigwig.baldwin.cx X-Virus-Status: Clean X-Spam-Status: No, score=-2.5 required=4.2 tests=AWL,BAYES_00,RDNS_NONE autolearn=no version=3.2.5 X-Spam-Checker-Version: SpamAssassin 3.2.5 (2008-06-10) on bigwig.baldwin.cx Cc: threads@freebsd.org Subject: Re: Using pthread_once() in libc X-BeenThere: freebsd-threads@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: Threading on FreeBSD List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 19 Nov 2009 17:55:03 -0000 On Thursday 19 November 2009 12:09:33 pm Daniel Eischen wrote: > On Thu, 19 Nov 2009, John Baldwin wrote: > > > On Thursday 19 November 2009 11:48:54 am Daniel Eischen wrote: > >> On Thu, 19 Nov 2009, John Baldwin wrote: > >> > >>> I would like to provide a pthread_once()-like facility in libc that library > >>> bits can use to initialize data safely rather than trying to home-roll their > >>> own variants (see the recent commit to stdtime in libc). Ideally what I > >>> would like to do is have libc use the "real" pthread_once() when libthr is > >>> linked in and fall back to a simple stub without libthr linked in. I know we > >>> already do something like this for _spinlock() and friends. My question is > >>> what is the most correct way to do this? Should libc grow a new _once() > >>> symbol ala _spinlock() that is a weak symbol to a stub version and > >>> pthread_once() in thr_once.c would override that, or should there be a > >>> _pthread_once() in libc that is a stub in place of the current stub_zero? I > >>> noticed a comment in thr_spinlock.c saying the spinlock stuff is kept for > >>> backwards compat. Does this mean that for the future we would like to expose > >>> pthread symbols directly in libc? Meaning would we rather have libc export a > >>> pthread_once() and that ideally libc would be using pthread_mutex_lock/unlock > >>> instead of _spinlock/unlock? > >> > >> pthread_once() is already a stub in libc that gets overloaded with the > >> real thing when libthr is linked. See libc/gen/_pthread_stubs.c. > >> Isn't that what you want or does it not serve your purpose? > > > > Hmm, the libc stub will never run the init routine. I would like to do > > something like this: > > Well, I suppose you could do that. But what happens if libthr gets > dlopen()'d and your once function needs to initialize a mutex or > something that can only be properly done by a real threads library? > Can we envision a scenario where that would be a problem? Hmmm, so I guess __is_threaded is how the dlopen() case is handled now for mutex lock/unlock as that avoids resolving the symbol until pthread_create() has been invoked? I guess then we could take an approach that works something like this: /* libc-internal function */ int _once(pthread_once_t *once_control, void (*init_routine)(void)) { if (__is_threaded) return (_pthread_once(once_control, init_routine)); return (_stub_once(once_control, init_routine)); } It is probably still a good idea to have the stub_once() patch I think so that pthread_once() DTRT in a single-threaded program. -- John Baldwin