[PATCH] Fix libstdc++ usage of __ctype_b/__ctype_to*
Jakub Jelinek
jakub@redhat.com
Thu Sep 5 01:17:00 GMT 2002
On Wed, Sep 04, 2002 at 04:05:57PM -0500, Benjamin Kosnik wrote:
> > -#if _GLIBCPP_USE_SHADOW_HEADERS
> > +#if _GLIBCPP_C_LOCALE_GNU
> > + const ctype_base::mask*
> > + ctype<char>::classic_table() throw()
> > + {
> > + if (!_S_c_locale)
> > + _S_create_c_locale(_S_c_locale, "C");
> > + return _S_c_locale->__ctype_b;
> > + }
> > +#else
>
> _S_c_locale should be created before this. I suppose this is safer.
Most probably yes, but as it is a static method I wanted to be sure.
Should I leave it in?
> > +# if _GLIBCPP_USE_SHADOW_HEADERS
> > using _C_legacy::__ctype_toupper;
> > using _C_legacy::__ctype_tolower;
> > using _C_legacy::__ctype_b;
> > -#endif
>
> Just remove all this _GLIBCPP_USE_SHADOW_HEADERS cruft.
You mean the using lines too?
> > +# endif
> >
> > const ctype_base::mask*
> > ctype<char>::classic_table() throw()
> > - { return __ctype_b; }
>
> Why not just _S_c_locale->__ctype_b?
Well, I use _S_c_locale->__ctype_b #ifdef _GLIBCPP_C_LOCALE_GNU,
otherwise _S_c_locale is NULL (config/locale/generic/c_locale.cc has:
void
locale::facet::_S_create_c_locale(__c_locale& __cloc, const char*,
__c_locale)
{ __cloc = NULL; }
) and it is a bad idea to dereference it...
>
> > -
> > + {
> > + const ctype_base::mask* __ret;
> > + char* __old = strdup(setlocale(LC_CTYPE, NULL));
> > + setlocale(LC_CTYPE, "C");
> > + __ret = __ctype_b;
BTW: This will have the effect that --enable-clocale=generic will no longer
work with glibc 2.3+. Although for everything but checking the generic
clocale gnu it makes no sense to use anything but --enable-clocale=gnu
with glibc 2.3+, we might as well consider using:
#if __GLIBC__ > 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ > 2)
__ret = *__ctype_b_loc();
#else
__ret = __ctype_b;
#endif
here (and similarly with __ctype_tolower and __ctype_toupper).
> > + setlocale(__old);
> > + free(__old);
> > + return __ret;
> > + }
> > +#endif
>
> Ok. Make sure the generic/ctype_noninline.h also does this though.
generic/ctype_noninline.h doesn't use __ctype_b and it cannot anyway,
since __ctype_b is (well, was) a glibc thing, so it has nothing to do
in generic header.
>
> > +
> > #if _GLIBCPP_C_LOCALE_GNU
>
> all these hooks are in the gnu-linux file so that --enable-clocale=generic
> will work on linux, so that I can test the generic codepath on checkins.
Jakub
More information about the Libstdc++
mailing list