Fix an issue where the locale and rune locale could become out of sync,

causing mb* functions (and similar) to be called with the wrong data
(possibly a null pointer, causing a crash).

PR:		standards/188036
MFC after:	1 week
This commit is contained in:
David Chisnall 2014-04-02 11:10:46 +00:00
parent 07a5254736
commit 8d07b7deff
2 changed files with 9 additions and 9 deletions

View File

@ -202,6 +202,8 @@ __set_thread_rune_locale(locale_t loc)
if (loc == NULL) {
_ThreadRuneLocale = &_DefaultRuneLocale;
} else if (loc == LC_GLOBAL_LOCALE) {
_ThreadRuneLocale = 0;
} else {
_ThreadRuneLocale = XLOCALE_CTYPE(loc)->runes;
}

View File

@ -154,23 +154,24 @@ __get_locale(void)
static void
set_thread_locale(locale_t loc)
{
locale_t l = (loc == LC_GLOBAL_LOCALE) ? 0 : loc;
_once(&once_control, init_key);
if (NULL != loc) {
xlocale_retain((struct xlocale_refcounted*)loc);
if (NULL != l) {
xlocale_retain((struct xlocale_refcounted*)l);
}
locale_t old = pthread_getspecific(locale_info_key);
if ((NULL != old) && (loc != old)) {
if ((NULL != old) && (l != old)) {
xlocale_release((struct xlocale_refcounted*)old);
}
if (fake_tls) {
thread_local_locale = loc;
thread_local_locale = l;
} else {
pthread_setspecific(locale_info_key, loc);
pthread_setspecific(locale_info_key, l);
}
#ifndef __NO_TLS
__thread_locale = loc;
__thread_locale = l;
__set_thread_rune_locale(loc);
#endif
}
@ -361,9 +362,6 @@ locale_t uselocale(locale_t loc)
{
locale_t old = get_thread_locale();
if (NULL != loc) {
if (LC_GLOBAL_LOCALE == loc) {
loc = NULL;
}
set_thread_locale(loc);
}
return (old ? old : LC_GLOBAL_LOCALE);