Skip to content
Snippets Groups Projects
Commit 5dfbc522 authored by Jonathan Wakely's avatar Jonathan Wakely
Browse files

libstdc++: Avoid bad_alloc exceptions when changing locales

For the --enable-clocale=generic configuration, the current code can
fail with a bad_alloc exception. This patch uses the nothrow version of
operator new and reports allocation failures by setting failbit in the
iostate variable.

	* config/locale/generic/c_locale.cc (__set_C_locale()): New function
	to set the "C" locale and return the name of the previous locale.
	(__convert_to_v<float>, __convert_to_v<double>)
	(__convert_to_v<long double>): Use __set_C_locale and set failbit on
	error.
parent 8c0c83fe
No related branches found
No related tags found
No related merge requests found
...@@ -52,6 +52,22 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION ...@@ -52,6 +52,22 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
~_Save_errno() { if (errno == 0) errno = _M_errno; } ~_Save_errno() { if (errno == 0) errno = _M_errno; }
int _M_errno; int _M_errno;
}; };
// calls setlocale(LC_ALL, "C") and returns a string containing the old
// locale name. Caller must delete[] the string. Returns NULL on error.
const char*
__set_C_locale()
{
char* __old = setlocale(LC_ALL, 0);
const size_t __len = strlen(__old) + 1;
char* __sav = new(nothrow) char[__len];
if (__sav)
{
memcpy(__sav, __old, __len);
setlocale(LC_ALL, "C");
}
return __sav;
}
} }
template<> template<>
...@@ -60,11 +76,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION ...@@ -60,11 +76,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
const __c_locale&) throw() const __c_locale&) throw()
{ {
// Assumes __s formatted for "C" locale. // Assumes __s formatted for "C" locale.
char* __old = setlocale(LC_ALL, 0); const char* __sav = __set_C_locale();
const size_t __len = strlen(__old) + 1; if (!__sav)
char* __sav = new char[__len]; {
memcpy(__sav, __old, __len); __err = ios_base::failbit;
setlocale(LC_ALL, "C"); return;
}
char* __sanity; char* __sanity;
bool __overflow = false; bool __overflow = false;
...@@ -125,11 +142,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION ...@@ -125,11 +142,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
const __c_locale&) throw() const __c_locale&) throw()
{ {
// Assumes __s formatted for "C" locale. // Assumes __s formatted for "C" locale.
char* __old = setlocale(LC_ALL, 0); const char* __sav = __set_C_locale();
const size_t __len = strlen(__old) + 1; if (!__sav)
char* __sav = new char[__len]; {
memcpy(__sav, __old, __len); __err = ios_base::failbit;
setlocale(LC_ALL, "C"); return;
}
char* __sanity; char* __sanity;
#if !__DBL_HAS_INFINITY__ #if !__DBL_HAS_INFINITY__
...@@ -170,11 +188,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION ...@@ -170,11 +188,12 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
ios_base::iostate& __err, const __c_locale&) throw() ios_base::iostate& __err, const __c_locale&) throw()
{ {
// Assumes __s formatted for "C" locale. // Assumes __s formatted for "C" locale.
char* __old = setlocale(LC_ALL, 0); const char* __sav = __set_C_locale();
const size_t __len = strlen(__old) + 1; if (!__sav)
char* __sav = new char[__len]; {
memcpy(__sav, __old, __len); __err = ios_base::failbit;
setlocale(LC_ALL, "C"); return;
}
#if !__LDBL_HAS_INFINITY__ #if !__LDBL_HAS_INFINITY__
const _Save_errno __save_errno; const _Save_errno __save_errno;
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment