Date: Sun, 7 Feb 2010 04:27:18 +0000 (UTC) From: Hajimu UMEMOTO <ume@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-8@freebsd.org Subject: svn commit: r203598 - stable/8/lib/libc/string Message-ID: <201002070427.o174RITV037278@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: ume Date: Sun Feb 7 04:27:18 2010 New Revision: 203598 URL: http://svn.freebsd.org/changeset/base/203598 Log: MFC r202916: Make strsignal(3) thread-safe. Modified: stable/8/lib/libc/string/strsignal.c Directory Properties: stable/8/lib/libc/ (props changed) stable/8/lib/libc/stdtime/ (props changed) Modified: stable/8/lib/libc/string/strsignal.c ============================================================================== --- stable/8/lib/libc/string/strsignal.c Sun Feb 7 04:24:10 2010 (r203597) +++ stable/8/lib/libc/string/strsignal.c Sun Feb 7 04:27:18 2010 (r203598) @@ -33,22 +33,64 @@ static char sccsid[] = "@(#)strerror.c 8 #include <sys/cdefs.h> __FBSDID("$FreeBSD$"); +#include "namespace.h" #if defined(NLS) #include <nl_types.h> #endif - #include <limits.h> #include <errno.h> +#include <stdlib.h> #include <string.h> #include <signal.h> +#include "reentrant.h" +#include "un-namespace.h" #define UPREFIX "Unknown signal" +static char sig_ebuf[NL_TEXTMAX]; +static char sig_ebuf_err[NL_TEXTMAX]; +static once_t sig_init_once = ONCE_INITIALIZER; +static thread_key_t sig_key; +static int sig_keycreated = 0; + +static void +sig_keycreate(void) +{ + sig_keycreated = (thr_keycreate(&sig_key, free) == 0); +} + +static char * +sig_tlsalloc(void) +{ + char *ebuf = NULL; + + if (thr_main() != 0) + ebuf = sig_ebuf; + else { + if (thr_once(&sig_init_once, sig_keycreate) != 0 || + !sig_keycreated) + goto thr_err; + if ((ebuf = thr_getspecific(sig_key)) == NULL) { + if ((ebuf = malloc(sizeof(sig_ebuf))) == NULL) + goto thr_err; + if (thr_setspecific(sig_key, ebuf) != 0) { + free(ebuf); + ebuf = NULL; + goto thr_err; + } + } + } +thr_err: + if (ebuf == NULL) + ebuf = sig_ebuf_err; + return (ebuf); +} + /* XXX: negative 'num' ? (REGR) */ char * strsignal(int num) { - static char ebuf[NL_TEXTMAX]; + char *ebuf; char tmp[20]; size_t n; int signum; @@ -60,6 +102,8 @@ strsignal(int num) catd = catopen("libc", NL_CAT_LOCALE); #endif + ebuf = sig_tlsalloc(); + if (num > 0 && num < sys_nsig) { n = strlcpy(ebuf, #if defined(NLS) @@ -67,7 +111,7 @@ strsignal(int num) #else sys_siglist[num], #endif - sizeof(ebuf)); + sizeof(sig_ebuf)); } else { n = strlcpy(ebuf, #if defined(NLS) @@ -75,7 +119,7 @@ strsignal(int num) #else UPREFIX, #endif - sizeof(ebuf)); + sizeof(sig_ebuf)); } signum = num;
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201002070427.o174RITV037278>