<div class="gmail_quote">2011/9/25 Howard Hinnant <span dir="ltr"><<a href="mailto:hhinnant@apple.com">hhinnant@apple.com</a>></span><br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex;">
<br>
On Sep 25, 2011, at 10:13 AM, Ruben Van Boxem wrote:<br>
<br>
> 2011/9/23 Howard Hinnant <<a href="mailto:hhinnant@apple.com">hhinnant@apple.com</a>><br>
> On Sep 23, 2011, at 3:14 PM, Ruben Van Boxem wrote:<br>
><br>
> > Can anything be done about this GCC incompatibility: <a href="http://gcc.gnu.org/bugzilla/show_bug.cgi?id=10980#c7" target="_blank">http://gcc.gnu.org/bugzilla/show_bug.cgi?id=10980#c7</a> ? It is preventing me from linking a functional libc++ (as Clang is not capable of producing correct object files to be linked together), and of course, testing the beast :). To fix it, this basically needs the functions in question to not be declared as "always inline", because GCC produces an error in this case. If Clang does not inline in this case, it should really also produce an error instead of silently ignoring the attribute.<br>

><br>
> Seems like the easiest thing to do would be to rewrite these without using va_list.  Only one or two arguments need to be supported.  Just make these always-inline templates.<br>
><br>
> Thanks for the valuable idea. Attached patch implements these for non-clang compiles (#ifdef __clang__). I also used the available *_l function variants for those that are available on Windows (MSVC++ runtime 8.0 and later). I also fixed up the win32 support header stuff to work with the full <locale> header things required.<br>

> I added a mingw bit to the lib/buildit script, that for now quite hackishly links to libsupc++ and allows multiple definitions due to a missing alternative. This will at least allow some testing to happen on the rest of the libc++ code, that isn't compiled into the library itself.<br>

> I envision a full LLVM alternative to libgcc and libsupc++, but that is still a looooong way off.<br>
><br>
> Comments and especially commits are very welcome!<br>
><br>
> Ruben<br>
><br>
> PS: the only thing holding back a test run is an undefined reference in mingw-w64's winpthreads library.<br>
> <windows.patch><br>
<br>
I think it is getting time for a refactoring in <locale>.<br>
<br>
What appears to be happening is that functions like asprintf_l are getting implemented for each platform, which I think is a good thing.  But it appears to be happening in an increasingly convoluted way.  For example we have:<br>

<br>
#ifdef _LIBCPP_STABLE_APPLE_ABI<br>
        __n = asprintf_l(&__bb, 0, "%.0Lf", __units);<br>
#else<br>
        __n = __asprintf_l(&__bb, __cloc(), "%.0Lf", __units);<br>
#endif<br>
<br>
The first branch is only taken by __APPLE__.  The second branch is taken by everyone else and the definition of __asprintf_l is earlier in <locale>.  This definition sometimes calls vasprintf_l, vasprintf, asprintf, and even (ironically) asprintf_l!  And it isn't easy (at least to me), to see what is happening on each platform.<br>

<br>
Suggestion:<br>
<br>
#ifdef __APPLE__<br>
#   define _LIBCPP_GET_C_LOCALE 0<br>
#else<br>
#   define _LIBCPP_GET_C_LOCALE __cloc()<br>
#endif<br>
<br>
...<br>
<br>
     __n = asprintf_l(&__bb, _LIBCPP_GET_C_LOCALE, "%.0Lf", __units);<br>
<br>
And then everyone go off and implement asprintf_l, preferably not in <locale>.  E.g. (and correct me if I'm wrong), __FreeBSD__ has done this in libc.  _WIN32 is doing it in src/support/win32/support.cpp.  I'd like to see this block of code:<br>

<br>
// OSX has nice foo_l() functions that let you turn off use of the global<br>
// locale.  Linux, not so much.  The following functions avoid the locale when<br>
// that's possible and otherwise do the wrong thing.  FIXME.<br>
#ifndef _LIBCPP_STABLE_APPLE_ABI<br>
<br>
just disappear, or at the very least become greatly reduced.<br></blockquote><div><br>If the __foo_l functions are just the wrappers that they seem to be, I can certainly live with removing this layer of indirection and me implementing the missing functions that are now wrongfully bypassed. I think expecting all xlocale functions to be present is fair for future implementations/ports. This would mean some additions to the support/win32/locale.h header only, which would concentrate any real problems there, which is a good thing. All platform-related fixme's and their future fixes (at least the win32 ones) would go in one centralized place, away from the public libc++ headers and core libc++. Other ports can do the same.<br>
<br>In that block of code, there is also a construct <br>__locale_raii __current(uselocale(__l), uselocale);<br>  int __res = sprintf(__s, __format, __args...);<br><br>Does this do the right thing; a very wasteful implementation of the correct behavior, or is this just an attempt to not make things worse. This would be important for me implementing missing *_l functions. If the above worked like I hope it does, that becomes very easy, albeit unperformant.<br>
<br>Thanks!<br><br>Ruben<br> </div><blockquote class="gmail_quote" style="margin: 0pt 0pt 0pt 0.8ex; border-left: 1px solid rgb(204, 204, 204); padding-left: 1ex;">
<br>
Thoughts?<br>
<font color="#888888"><br>
Howard<br>
<br>
</font></blockquote></div><br>