From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from dedi548.your-server.de (dedi548.your-server.de [85.10.215.148]) by sourceware.org (Postfix) with ESMTPS id E58773857415 for ; Tue, 21 Jun 2022 12:49:39 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.1 sourceware.org E58773857415 Authentication-Results: sourceware.org; dmarc=none (p=none dis=none) header.from=embedded-brains.de Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=embedded-brains.de Received: from sslproxy02.your-server.de ([78.47.166.47]) by dedi548.your-server.de with esmtpsa (TLS1.3) tls TLS_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1o3dK6-0003Zd-De for newlib@sourceware.org; Tue, 21 Jun 2022 14:49:38 +0200 Received: from [82.100.198.138] (helo=mail.embedded-brains.de) by sslproxy02.your-server.de with esmtpsa (TLSv1.3:TLS_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1o3dK6-000MCo-K0 for newlib@sourceware.org; Tue, 21 Jun 2022 14:49:38 +0200 Received: from localhost (localhost [127.0.0.1]) by mail.embedded-brains.de (Postfix) with ESMTP id 5A59648005A for ; Tue, 21 Jun 2022 14:49:38 +0200 (CEST) Received: from mail.embedded-brains.de ([127.0.0.1]) by localhost (zimbra.eb.localhost [127.0.0.1]) (amavisd-new, port 10032) with ESMTP id hzLEPf1f9hBh for ; Tue, 21 Jun 2022 14:49:37 +0200 (CEST) Received: from localhost (localhost [127.0.0.1]) by mail.embedded-brains.de (Postfix) with ESMTP id 1A21B4801DF for ; Tue, 21 Jun 2022 14:49:35 +0200 (CEST) X-Virus-Scanned: amavisd-new at zimbra.eb.localhost Received: from mail.embedded-brains.de ([127.0.0.1]) by localhost (zimbra.eb.localhost [127.0.0.1]) (amavisd-new, port 10026) with ESMTP id 2RF8x8hchjDj for ; Tue, 21 Jun 2022 14:49:35 +0200 (CEST) Received: from zimbra.eb.localhost (unknown [192.168.96.242]) by mail.embedded-brains.de (Postfix) with ESMTPSA id E65754801E1 for ; Tue, 21 Jun 2022 14:49:34 +0200 (CEST) From: Sebastian Huber To: newlib@sourceware.org Subject: [PATCH 14/14] Add --enable-newlib-reent-thread-local option Date: Tue, 21 Jun 2022 14:49:31 +0200 Message-Id: <20220621124931.36450-15-sebastian.huber@embedded-brains.de> X-Mailer: git-send-email 2.35.3 In-Reply-To: <20220621124931.36450-1-sebastian.huber@embedded-brains.de> References: <20220621124931.36450-1-sebastian.huber@embedded-brains.de> MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable X-Authenticated-Sender: smtp-embedded@poldinet.de X-Virus-Scanned: Clear (ClamAV 0.103.6/26579/Tue Jun 21 10:15:30 2022) X-Spam-Status: No, score=-11.6 required=5.0 tests=BAYES_00, GIT_PATCH_0, KAM_DMARC_STATUS, SPF_HELO_NONE, SPF_PASS, TXREP, T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: newlib@sourceware.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Newlib mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 21 Jun 2022 12:49:43 -0000 From: Matt Joyce By default, Newlib uses a huge object of type struct _reent to store thread-specific data. This object is returned by __getreent() if the __DYNAMIC_REENT__ Newlib configuration option is defined. The reentrancy structure contains for example errno and the standard inpu= t, output, and error file streams. This means that if an application only u= ses errno it has a dependency on the file stream support even if it does not = use it. This is an issue for lower end targets and applications which need t= o qualify the software according to safety standards (for example ECSS-E-ST= -40C, ECSS-Q-ST-80C, IEC 61508, ISO 26262, DO-178, DO-330, DO-333). If the new _REENT_THREAD_LOCAL configuration option is enabled, then stru= ct _reent is replaced by dedicated thread-local objects for each struct _ree= nt member. The thread-local objects are defined in translation units which = use the corresponding object. --- newlib/README | 8 +++ newlib/configure | 21 ++++++++ newlib/configure.ac | 15 ++++++ newlib/libc/errno/errno.c | 6 +++ newlib/libc/include/sys/config.h | 6 +++ newlib/libc/include/sys/errno.h | 6 +++ newlib/libc/include/sys/reent.h | 92 ++++++++++++++++++++++++++++++++ newlib/libc/locale/locale.c | 4 ++ newlib/libc/reent/impure.c | 4 ++ newlib/libc/reent/reent.c | 2 + newlib/libc/signal/signal.c | 4 ++ newlib/libc/stdio/findfp.c | 7 +++ newlib/libc/stdio/tmpnam.c | 5 ++ newlib/libc/stdlib/dtoa.c | 5 ++ newlib/libc/stdlib/ecvtbuf.c | 5 ++ newlib/libc/stdlib/l64a.c | 4 ++ newlib/libc/stdlib/lcong48.c | 8 +++ newlib/libc/stdlib/mblen.c | 4 ++ newlib/libc/stdlib/mbrlen.c | 4 ++ newlib/libc/stdlib/mbrtowc.c | 4 ++ newlib/libc/stdlib/mbsnrtowcs.c | 4 ++ newlib/libc/stdlib/mbtowc.c | 4 ++ newlib/libc/stdlib/mprec.c | 5 ++ newlib/libc/stdlib/rand.c | 4 ++ newlib/libc/stdlib/wcrtomb.c | 4 ++ newlib/libc/stdlib/wcsnrtombs.c | 4 ++ newlib/libc/stdlib/wctomb.c | 4 ++ newlib/libc/string/strsignal.c | 4 ++ newlib/libc/string/strtok.c | 4 ++ newlib/libc/time/asctime.c | 4 ++ newlib/libc/time/gmtime.c | 4 ++ newlib/libm/math/w_lgamma.c | 4 ++ newlib/newlib.hin | 4 ++ 33 files changed, 267 insertions(+) diff --git a/newlib/README b/newlib/README index dd4686eeb..1b2c16cd4 100644 --- a/newlib/README +++ b/newlib/README @@ -304,6 +304,14 @@ One feature can be enabled by specifying `--enable-F= EATURE=3Dyes' or layout. Disabled by default. =20 +`--enable-newlib-reent-thread-local' + Enable thread-local storage objects as a replacement for struct _re= ent + members. If enabled, then struct _reent is not defined and dedicat= ed + thread-local storage objects are provided for each member of the de= fault + struct _reent. For statically linked executables only the objects + required by the application are linked in. + Disabled by default. + `--disable-newlib-fvwrite-in-streamio' NEWLIB implements the vector buffer mechanism to support stream IO buffering required by C standard. This feature is possibly diff --git a/newlib/configure b/newlib/configure index 82c256694..e493eb293 100755 --- a/newlib/configure +++ b/newlib/configure @@ -973,6 +973,7 @@ enable_newlib_atexit_dynamic_alloc enable_newlib_global_atexit enable_newlib_reent_small enable_newlib_reent_binary_compat +enable_newlib_reent_thread_local enable_newlib_global_stdio_streams enable_newlib_fvwrite_in_streamio enable_newlib_fseek_optimization @@ -1641,6 +1642,7 @@ Optional Features: --enable-newlib-global-atexit enable atexit data structure as global --enable-newlib-reent-small enable small reentrant struct support --enable-newlib-reent-binary-compat enable backward binary compatibi= lity for struct _reent + --enable-newlib-reent-thread-local enable thread-local storage objec= ts as a replacment for struct _reent members --enable-newlib-global-stdio-streams enable global stdio streams --disable-newlib-fvwrite-in-streamio disable iov in streamio --disable-newlib-fseek-optimization disable fseek optimization @@ -2404,6 +2406,19 @@ else newlib_reent_binary_compat=3Dno fi =20 +# Check whether --enable-newlib-reent-thread-local was given. +if test "${enable_newlib_reent_thread_local+set}" =3D set; then : + enableval=3D$enable_newlib_reent_thread_local; if test "${newlib_reent= _thread_local+set}" !=3D set; then + case "${enableval}" in + yes) newlib_reent_thread_local=3Dyes ;; + no) newlib_reent_thread_local=3Dno ;; + *) as_fn_error $? "bad value ${enableval} for newlib-enable-reent-= thread-local option" "$LINENO" 5 ;; + esac + fi +else + newlib_reent_thread_local=3Dno +fi + # Check whether --enable-newlib-global-stdio-streams was given. if test "${enable_newlib_global_stdio_streams+set}" =3D set; then : enableval=3D$enable_newlib_global_stdio_streams; case "${enableval}" i= n @@ -6437,6 +6452,12 @@ $as_echo "#define _WANT_REENT_BACKWARD_BINARY_COMP= AT 1" >>confdefs.h =20 fi =20 +if test "${newlib_reent_thread_local}" =3D "yes"; then + +$as_echo "#define _WANT_REENT_THREAD_LOCAL 1" >>confdefs.h + +fi + _mb_len_max=3D1 if test "${newlib_mb}" =3D "yes"; then =20 diff --git a/newlib/configure.ac b/newlib/configure.ac index 1951aab0c..bed444db0 100644 --- a/newlib/configure.ac +++ b/newlib/configure.ac @@ -173,6 +173,17 @@ AC_ARG_ENABLE(newlib-reent-binary-compat, esac fi], [newlib_reent_binary_compat=3Dno])dnl =20 +dnl Support --enable-newlib-reent-thread-local +AC_ARG_ENABLE(newlib-reent-thread-local, +[ --enable-newlib-reent-thread-local enable thread-local storage obje= cts as a replacment for struct _reent members], +[if test "${newlib_reent_thread_local+set}" !=3D set; then + case "${enableval}" in + yes) newlib_reent_thread_local=3Dyes ;; + no) newlib_reent_thread_local=3Dno ;; + *) AC_MSG_ERROR(bad value ${enableval} for newlib-enable-reent-thr= ead-local option) ;; + esac + fi], [newlib_reent_thread_local=3Dno])dnl + dnl Support --enable-newlib-global-stdio-streams dnl This is no longer optional. It is enabled in all Newlib configurati= ons. AC_ARG_ENABLE(newlib-global-stdio-streams, @@ -435,6 +446,10 @@ if test "${newlib_reent_binary_compat}" =3D "yes"; t= hen AC_DEFINE(_WANT_REENT_BACKWARD_BINARY_COMPAT, 1, [Define to enable bac= kward binary compatibility for struct _reent.]) fi =20 +if test "${newlib_reent_thread_local}" =3D "yes"; then + AC_DEFINE(_WANT_REENT_THREAD_LOCAL, 1, [Define to enable thread-local = storage objects as a replacment for struct _reent members.]) +fi + _mb_len_max=3D1 if test "${newlib_mb}" =3D "yes"; then AC_DEFINE(_MB_CAPABLE, 1, [Multibyte supported.]) diff --git a/newlib/libc/errno/errno.c b/newlib/libc/errno/errno.c index 70402924b..384b07f2c 100644 --- a/newlib/libc/errno/errno.c +++ b/newlib/libc/errno/errno.c @@ -5,6 +5,10 @@ #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local int _tls_errno; +#else /* !_REENT_THREAD_LOCAL */ + #ifndef _REENT_ONLY =20 int * @@ -14,3 +18,5 @@ __errno () } =20 #endif + +#endif /* _REENT_THREAD_LOCAL */ diff --git a/newlib/libc/include/sys/config.h b/newlib/libc/include/sys/c= onfig.h index 4bce10de3..5dcc77a80 100644 --- a/newlib/libc/include/sys/config.h +++ b/newlib/libc/include/sys/config.h @@ -297,6 +297,12 @@ #endif #endif =20 +#ifdef _WANT_REENT_THREAD_LOCAL +#ifndef _REENT_THREAD_LOCAL +#define _REENT_THREAD_LOCAL +#endif +#endif + /* If _MB_EXTENDED_CHARSETS_ALL is set, we want all of the extended charsets. The extended charsets add a few functions and a couple of tables of a few K each. */ diff --git a/newlib/libc/include/sys/errno.h b/newlib/libc/include/sys/er= rno.h index 995f30e05..f1509712e 100644 --- a/newlib/libc/include/sys/errno.h +++ b/newlib/libc/include/sys/errno.h @@ -10,11 +10,17 @@ extern "C" { =20 #include =20 +#ifdef _REENT_THREAD_LOCAL +#define errno (_tls_errno) +#else /* _REENT_THREAD_LOCAL */ + #ifndef _REENT_ONLY #define errno (*__errno()) extern int *__errno (void); #endif =20 +#endif /* _REENT_THREAD_LOCAL */ + /* Please don't use these variables directly. Use strerror instead. */ extern __IMPORT const char * const _sys_errlist[]; diff --git a/newlib/libc/include/sys/reent.h b/newlib/libc/include/sys/re= ent.h index 90f848180..71342bebc 100644 --- a/newlib/libc/include/sys/reent.h +++ b/newlib/libc/include/sys/reent.h @@ -301,6 +301,8 @@ struct _rand48 { #define _REENT_ASCTIME_SIZE 26 #define _REENT_SIGNAL_SIZE 24 =20 +#ifndef _REENT_THREAD_LOCAL + #ifdef _REENT_BACKWARD_BINARY_COMPAT #define _REENT_INIT_RESERVED_0 0, #define _REENT_INIT_RESERVED_1 0, @@ -767,6 +769,96 @@ extern struct _reent _impure_data __ATTRIBUTE_IMPURE= _DATA__; =20 #define _GLOBAL_REENT (&_impure_data) =20 +#else /* _REENT_THREAD_LOCAL */ + +#define _REENT NULL +#define _GLOBAL_REENT NULL + +/* + * Since _REENT is defined as NULL, this macro ensures that calls to + * CHECK_INIT() do not automatically fail. + */ +#define _REENT_IS_NULL(_ptr) 0 + +#define _REENT_CHECK_RAND48(ptr) /* nothing */ +#define _REENT_CHECK_MP(ptr) /* nothing */ +#define _REENT_CHECK_TM(ptr) /* nothing */ +#define _REENT_CHECK_ASCTIME_BUF(ptr) /* nothing */ +#define _REENT_CHECK_EMERGENCY(ptr) /* nothing */ +#define _REENT_CHECK_MISC(ptr) /* nothing */ +#define _REENT_CHECK_SIGNAL_BUF(ptr) /* nothing */ + +extern _Thread_local char _tls_asctime_buf[_REENT_ASCTIME_SIZE]; +#define _REENT_ASCTIME_BUF(_ptr) (_tls_asctime_buf) +extern _Thread_local char *_tls_cvtbuf; +#define _REENT_CVTBUF(_ptr) (_tls_cvtbuf) +extern _Thread_local int _tls_cvtlen; +#define _REENT_CVTLEN(_ptr) (_tls_cvtlen) +extern _Thread_local void (*_tls_cleanup)(struct _reent *); +#define _REENT_CLEANUP(_ptr) (_tls_cleanup) +extern _Thread_local char _tls_emergency; +#define _REENT_EMERGENCY(_ptr) (_tls_emergency) +extern _Thread_local int _tls_errno; +#define _REENT_ERRNO(_ptr) (_tls_errno) +extern _Thread_local int _tls_getdate_err; +#define _REENT_GETDATE_ERR_P(_ptr) (&_tls_getdate_err) +extern _Thread_local int _tls_inc; +#define _REENT_INC(_ptr) (_tls_inc) +extern _Thread_local char _tls_l64a_buf[8]; +#define _REENT_L64A_BUF(_ptr) (_tls_l64a_buf) +extern _Thread_local struct __locale_t *_tls_locale; +#define _REENT_LOCALE(_ptr) (_tls_locale) +extern _Thread_local _mbstate_t _tls_mblen_state; +#define _REENT_MBLEN_STATE(_ptr) (_tls_mblen_state) +extern _Thread_local _mbstate_t _tls_mbrlen_state; +#define _REENT_MBRLEN_STATE(_ptr) (_tls_mbrlen_state) +extern _Thread_local _mbstate_t _tls_mbrtowc_state; +#define _REENT_MBRTOWC_STATE(_ptr) (_tls_mbrtowc_state) +extern _Thread_local _mbstate_t _tls_mbsrtowcs_state; +#define _REENT_MBSRTOWCS_STATE(_ptr) (_tls_mbsrtowcs_state) +extern _Thread_local _mbstate_t _tls_mbtowc_state; +#define _REENT_MBTOWC_STATE(_ptr) (_tls_mbtowc_state) +extern _Thread_local struct _Bigint **_tls_mp_freelist; +#define _REENT_MP_FREELIST(_ptr) (_tls_mp_freelist) +extern _Thread_local struct _Bigint *_tls_mp_p5s; +#define _REENT_MP_P5S(_ptr) (_tls_mp_p5s) +extern _Thread_local struct _Bigint *_tls_mp_result; +#define _REENT_MP_RESULT(_ptr) (_tls_mp_result) +extern _Thread_local int _tls_mp_result_k; +#define _REENT_MP_RESULT_K(_ptr) (_tls_mp_result_k) +extern _Thread_local unsigned short _tls_rand48_add; +#define _REENT_RAND48_ADD(_ptr) (_tls_rand48_add) +extern _Thread_local unsigned short _tls_rand48_mult[3]; +#define _REENT_RAND48_MULT(_ptr) (_tls_rand48_mult) +extern _Thread_local unsigned short _tls_rand48_seed[3]; +#define _REENT_RAND48_SEED(_ptr) (_tls_rand48_seed) +extern _Thread_local unsigned long long _tls_rand_next; +#define _REENT_RAND_NEXT(_ptr) (_tls_rand_next) +extern _Thread_local void (**_tls_sig_func)(int); +#define _REENT_SIG_FUNC(_ptr) (_tls_sig_func) +extern _Thread_local char _tls_signal_buf[_REENT_SIGNAL_SIZE]; +#define _REENT_SIGNAL_BUF(_ptr) (_tls_signal_buf) +extern _Thread_local int _tls_gamma_signgam; +#define _REENT_SIGNGAM(_ptr) (_tls_gamma_signgam) +extern _Thread_local __FILE *_tls_stdin; +#define _REENT_STDIN(_ptr) (_tls_stdin) +extern _Thread_local __FILE *_tls_stdout; +#define _REENT_STDOUT(_ptr) (_tls_stdout) +extern _Thread_local __FILE *_tls_stderr; +#define _REENT_STDERR(_ptr) (_tls_stderr) +extern _Thread_local char *_tls_strtok_last; +#define _REENT_STRTOK_LAST(_ptr) (_tls_strtok_last) +extern _Thread_local struct __tm _tls_localtime_buf; +#define _REENT_TM(_ptr) (&_tls_localtime_buf) +extern _Thread_local _mbstate_t _tls_wctomb_state; +#define _REENT_WCTOMB_STATE(_ptr) (_tls_wctomb_state) +extern _Thread_local _mbstate_t _tls_wcrtomb_state; +#define _REENT_WCRTOMB_STATE(_ptr) (_tls_wcrtomb_state) +extern _Thread_local _mbstate_t _tls_wcsrtombs_state; +#define _REENT_WCSRTOMBS_STATE(_ptr) (_tls_wcsrtombs_state) + +#endif /* !_REENT_THREAD_LOCAL */ + /* This value is used in stdlib/misc.c. reent/reent.c has to know it as well to make sure the freelist is correctly free'd. Therefore we define it here, rather than in stdlib/misc.c, as before. */ diff --git a/newlib/libc/locale/locale.c b/newlib/libc/locale/locale.c index 968642745..e523d2366 100644 --- a/newlib/libc/locale/locale.c +++ b/newlib/libc/locale/locale.c @@ -166,6 +166,10 @@ No supporting OS subroutines are required. #include "../ctype/ctype_.h" #include "../stdlib/local.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local struct __locale_t *_tls_locale; +#endif + #ifdef __CYGWIN__ /* Has to be kept available as exported symbol for backward compatibility. Set it in setlocale, but otherwise ignore it. Applications compiled after diff --git a/newlib/libc/reent/impure.c b/newlib/libc/reent/impure.c index 9290c9cd5..a87b91feb 100644 --- a/newlib/libc/reent/impure.c +++ b/newlib/libc/reent/impure.c @@ -1,5 +1,7 @@ #include =20 +#ifndef _REENT_THREAD_LOCAL + /* Redeclare these symbols locally as weak so that the file containing their definitions (along with a lot of other stuff) isn't sucked in unless they are actually used by other compilation units. This is @@ -14,3 +16,5 @@ struct _reent __ATTRIBUTE_IMPURE_DATA__ _impure_data =3D= _REENT_INIT (_impure_data extern struct _reent reent_data __attribute__ ((alias("_impure_data"))); #endif struct _reent *__ATTRIBUTE_IMPURE_PTR__ _impure_ptr =3D &_impure_data; + +#endif /* _REENT_THREAD_LOCAL */ diff --git a/newlib/libc/reent/reent.c b/newlib/libc/reent/reent.c index 4e9485c7a..db80ca06e 100644 --- a/newlib/libc/reent/reent.c +++ b/newlib/libc/reent/reent.c @@ -30,7 +30,9 @@ int errno; void _reclaim_reent (struct _reent *ptr) { +#ifndef _REENT_THREAD_LOCAL if (ptr !=3D _impure_ptr) +#endif { /* used by mprec routines. */ #ifdef _REENT_SMALL diff --git a/newlib/libc/signal/signal.c b/newlib/libc/signal/signal.c index 3f14b4712..77d78f04a 100644 --- a/newlib/libc/signal/signal.c +++ b/newlib/libc/signal/signal.c @@ -88,6 +88,10 @@ int _dummy_simulated_signal; #include #include <_syslist.h> =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local void (**_tls_sig_func)(int); +#endif + int _init_signal_r (struct _reent *ptr) { diff --git a/newlib/libc/stdio/findfp.c b/newlib/libc/stdio/findfp.c index fbdb7f2f2..c43028209 100644 --- a/newlib/libc/stdio/findfp.c +++ b/newlib/libc/stdio/findfp.c @@ -32,6 +32,13 @@ __FILE __sf[3]; =20 struct _glue __sglue =3D {NULL, 3, &__sf[0]}; =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local __FILE *_tls_stdin =3D &__sf[0]; +_Thread_local __FILE *_tls_stdout =3D &__sf[1]; +_Thread_local __FILE *_tls_stderr =3D &__sf[2]; +_Thread_local void (*_tls_cleanup)(struct _reent *); +#endif + #ifdef _STDIO_BSD_SEMANTICS /* BSD and Glibc systems only flush streams which have been written to at exit time. Calling flush rather than close for speed, as on diff --git a/newlib/libc/stdio/tmpnam.c b/newlib/libc/stdio/tmpnam.c index 2767b4b20..51dfd1cea 100644 --- a/newlib/libc/stdio/tmpnam.c +++ b/newlib/libc/stdio/tmpnam.c @@ -82,6 +82,11 @@ The global pointer <> is also required. #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local int _tls_inc; +_Thread_local char _tls_emergency; +#endif + /* Try to open the file specified, if it can't be opened then try another one. Return nonzero if successful, otherwise zero. */ =20 diff --git a/newlib/libc/stdlib/dtoa.c b/newlib/libc/stdlib/dtoa.c index e47a8bc77..198fa663a 100644 --- a/newlib/libc/stdlib/dtoa.c +++ b/newlib/libc/stdlib/dtoa.c @@ -32,6 +32,11 @@ #include #include "mprec.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local struct _Bigint *_tls_mp_result; +_Thread_local int _tls_mp_result_k; +#endif + static int quorem (_Bigint * b, _Bigint * S) { diff --git a/newlib/libc/stdlib/ecvtbuf.c b/newlib/libc/stdlib/ecvtbuf.c index 05f315108..514896682 100644 --- a/newlib/libc/stdlib/ecvtbuf.c +++ b/newlib/libc/stdlib/ecvtbuf.c @@ -57,6 +57,11 @@ Supporting OS subroutines required: <>, <>, <>, #include "mprec.h" #include "local.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local char *_tls_cvtbuf; +_Thread_local int _tls_cvtlen; +#endif + static void print_f (struct _reent *ptr, char *buf, diff --git a/newlib/libc/stdlib/l64a.c b/newlib/libc/stdlib/l64a.c index 45282e32d..6f12b6151 100644 --- a/newlib/libc/stdlib/l64a.c +++ b/newlib/libc/stdlib/l64a.c @@ -24,6 +24,10 @@ #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local char _tls_l64a_buf[8]; +#endif + static const char R64_ARRAY[] =3D "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXY= Zabcdefghijklmnopqrstuvwxyz"; =20 char * diff --git a/newlib/libc/stdlib/lcong48.c b/newlib/libc/stdlib/lcong48.c index 78e9e5746..d1109f0ac 100644 --- a/newlib/libc/stdlib/lcong48.c +++ b/newlib/libc/stdlib/lcong48.c @@ -13,6 +13,14 @@ =20 #include "rand48.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local unsigned short _tls_rand48_seed[3] =3D {_RAND48_SEED_0, _R= AND48_SEED_1, + _RAND48_SEED_2}; +_Thread_local unsigned short _tls_rand48_mult[3] =3D {_RAND48_MULT_0, _R= AND48_MULT_1, + _RAND48_MULT_2}; +_Thread_local unsigned short _tls_rand48_add =3D _RAND48_ADD; +#endif + void _lcong48_r (struct _reent *r, unsigned short p[7]) diff --git a/newlib/libc/stdlib/mblen.c b/newlib/libc/stdlib/mblen.c index 3753d3673..24df61519 100644 --- a/newlib/libc/stdlib/mblen.c +++ b/newlib/libc/stdlib/mblen.c @@ -42,6 +42,10 @@ effects vary with the locale. #include #include "local.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_mblen_state; +#endif + int mblen (const char *s, size_t n) diff --git a/newlib/libc/stdlib/mbrlen.c b/newlib/libc/stdlib/mbrlen.c index 57a733fed..39e175e43 100644 --- a/newlib/libc/stdlib/mbrlen.c +++ b/newlib/libc/stdlib/mbrlen.c @@ -5,6 +5,10 @@ #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_mbrlen_state; +#endif + size_t mbrlen(const char *__restrict s, size_t n, mbstate_t *__restrict ps) { diff --git a/newlib/libc/stdlib/mbrtowc.c b/newlib/libc/stdlib/mbrtowc.c index 521b7a5f4..e641b8cd6 100644 --- a/newlib/libc/stdlib/mbrtowc.c +++ b/newlib/libc/stdlib/mbrtowc.c @@ -7,6 +7,10 @@ #include #include "local.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_mbrtowc_state; +#endif + size_t _mbrtowc_r (struct _reent *ptr, wchar_t *pwc, diff --git a/newlib/libc/stdlib/mbsnrtowcs.c b/newlib/libc/stdlib/mbsnrto= wcs.c index 8f94b1da5..2effc501c 100644 --- a/newlib/libc/stdlib/mbsnrtowcs.c +++ b/newlib/libc/stdlib/mbsnrtowcs.c @@ -70,6 +70,10 @@ PORTABILITY #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_mbsrtowcs_state; +#endif + size_t _mbsnrtowcs_r (struct _reent *r, wchar_t *dst, diff --git a/newlib/libc/stdlib/mbtowc.c b/newlib/libc/stdlib/mbtowc.c index 2dc413f2d..fbd8df61d 100644 --- a/newlib/libc/stdlib/mbtowc.c +++ b/newlib/libc/stdlib/mbtowc.c @@ -49,6 +49,10 @@ effects vary with the locale. #include #include "local.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_mbtowc_state; +#endif + int mbtowc (wchar_t *__restrict pwc, const char *__restrict s, diff --git a/newlib/libc/stdlib/mprec.c b/newlib/libc/stdlib/mprec.c index 930c984ca..1f534b068 100644 --- a/newlib/libc/stdlib/mprec.c +++ b/newlib/libc/stdlib/mprec.c @@ -86,6 +86,11 @@ #include #include "mprec.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local struct _Bigint *_tls_mp_p5s; +_Thread_local struct _Bigint **_tls_mp_freelist; +#endif + /* This is defined in sys/reent.h as (sizeof (size_t) << 3) now, as in N= etBSD. The old value of 15 was wrong and made newlib vulnerable against buff= er overrun attacks (CVE-2009-0689), same as other implementations of gdt= oa diff --git a/newlib/libc/stdlib/rand.c b/newlib/libc/stdlib/rand.c index 209cb32ff..ba9cc80f2 100644 --- a/newlib/libc/stdlib/rand.c +++ b/newlib/libc/stdlib/rand.c @@ -58,6 +58,10 @@ on two different systems. #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local unsigned long long _tls_rand_next =3D 1; +#endif + void srand (unsigned int seed) { diff --git a/newlib/libc/stdlib/wcrtomb.c b/newlib/libc/stdlib/wcrtomb.c index 6d670e23a..1b84720ac 100644 --- a/newlib/libc/stdlib/wcrtomb.c +++ b/newlib/libc/stdlib/wcrtomb.c @@ -6,6 +6,10 @@ #include #include "local.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_wcrtomb_state; +#endif + size_t _wcrtomb_r (struct _reent *ptr, char *s, diff --git a/newlib/libc/stdlib/wcsnrtombs.c b/newlib/libc/stdlib/wcsnrto= mbs.c index dfd974f24..abef7ac36 100644 --- a/newlib/libc/stdlib/wcsnrtombs.c +++ b/newlib/libc/stdlib/wcsnrtombs.c @@ -72,6 +72,10 @@ PORTABILITY #include "local.h" #include "../locale/setlocale.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_wcsrtombs_state; +#endif + size_t _wcsnrtombs_l (struct _reent *r, char *dst, const wchar_t **src, size_t = nwc, size_t len, mbstate_t *ps, struct __locale_t *loc) diff --git a/newlib/libc/stdlib/wctomb.c b/newlib/libc/stdlib/wctomb.c index e908d22c2..f56dccf25 100644 --- a/newlib/libc/stdlib/wctomb.c +++ b/newlib/libc/stdlib/wctomb.c @@ -45,6 +45,10 @@ effects vary with the locale. #include #include "local.h" =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local _mbstate_t _tls_wctomb_state; +#endif + int wctomb (char *s, wchar_t wchar) diff --git a/newlib/libc/string/strsignal.c b/newlib/libc/string/strsigna= l.c index 544857b14..89d39fe3c 100644 --- a/newlib/libc/string/strsignal.c +++ b/newlib/libc/string/strsignal.c @@ -52,6 +52,10 @@ QUICKREF #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local char _tls_signal_buf[_REENT_SIGNAL_SIZE]; +#endif + char * strsignal (int signal) { diff --git a/newlib/libc/string/strtok.c b/newlib/libc/string/strtok.c index 801f51aca..2a11c9196 100644 --- a/newlib/libc/string/strtok.c +++ b/newlib/libc/string/strtok.c @@ -74,6 +74,10 @@ QUICKREF #include <_ansi.h> #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local char *_tls_strtok_last; +#endif + #ifndef _REENT_ONLY =20 extern char *__strtok_r (char *, const char *, char **, int); diff --git a/newlib/libc/time/asctime.c b/newlib/libc/time/asctime.c index 9aa26c3dc..a81506181 100644 --- a/newlib/libc/time/asctime.c +++ b/newlib/libc/time/asctime.c @@ -45,6 +45,10 @@ ANSI C requires <>. #include <_ansi.h> #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local char _tls_asctime_buf[_REENT_ASCTIME_SIZE]; +#endif + #ifndef _REENT_ONLY =20 char * diff --git a/newlib/libc/time/gmtime.c b/newlib/libc/time/gmtime.c index 08e011129..a78d55433 100644 --- a/newlib/libc/time/gmtime.c +++ b/newlib/libc/time/gmtime.c @@ -47,6 +47,10 @@ ANSI C requires <>. =20 #define _GMT_OFFSET 0 =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local struct __tm _tls_localtime_buf; +#endif + #ifndef _REENT_ONLY =20 struct tm * diff --git a/newlib/libm/math/w_lgamma.c b/newlib/libm/math/w_lgamma.c index c07804779..c075a4fc1 100644 --- a/newlib/libm/math/w_lgamma.c +++ b/newlib/libm/math/w_lgamma.c @@ -22,6 +22,10 @@ #include #include =20 +#ifdef _REENT_THREAD_LOCAL +_Thread_local int _tls_gamma_signgam; +#endif + #ifndef _DOUBLE_IS_32BITS =20 #ifdef __STDC__ diff --git a/newlib/newlib.hin b/newlib/newlib.hin index 30f59ddba..e87a5eabb 100644 --- a/newlib/newlib.hin +++ b/newlib/newlib.hin @@ -406,6 +406,10 @@ restricted storage. */ #undef _WANT_REENT_SMALL =20 +/* Define to enable thread-local storage objects as a replacment for str= uct + _reent members. */ +#undef _WANT_REENT_THREAD_LOCAL + /* Register application finalization function using atexit. */ #undef _WANT_REGISTER_FINI =20 --=20 2.35.3