[cfe-dev] [PATCH] Libc++ Windows fixes (Attention all libc++ ports!!!)

Ruben Van Boxem vanboxem.ruben at gmail.com
Mon Sep 26 01:38:14 PDT 2011


2011/9/25 Howard Hinnant <hhinnant at apple.com>

>
> On Sep 25, 2011, at 10:13 AM, Ruben Van Boxem wrote:
>
> > 2011/9/23 Howard Hinnant <hhinnant at apple.com>
> > On Sep 23, 2011, at 3:14 PM, Ruben Van Boxem wrote:
> >
> > > Can anything be done about this GCC incompatibility:
> http://gcc.gnu.org/bugzilla/show_bug.cgi?id=10980#c7 ? 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.
> >
> > 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.
> >
> > 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.
> > 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.
> > I envision a full LLVM alternative to libgcc and libsupc++, but that is
> still a looooong way off.
> >
> > Comments and especially commits are very welcome!
> >
> > Ruben
> >
> > PS: the only thing holding back a test run is an undefined reference in
> mingw-w64's winpthreads library.
> > <windows.patch>
>
> I think it is getting time for a refactoring in <locale>.
>
> 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:
>
> #ifdef _LIBCPP_STABLE_APPLE_ABI
>        __n = asprintf_l(&__bb, 0, "%.0Lf", __units);
> #else
>        __n = __asprintf_l(&__bb, __cloc(), "%.0Lf", __units);
> #endif
>
> 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.
>
> Suggestion:
>
> #ifdef __APPLE__
> #   define _LIBCPP_GET_C_LOCALE 0
> #else
> #   define _LIBCPP_GET_C_LOCALE __cloc()
> #endif
>
> ...
>
>     __n = asprintf_l(&__bb, _LIBCPP_GET_C_LOCALE, "%.0Lf", __units);
>
> 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:
>
> // OSX has nice foo_l() functions that let you turn off use of the global
> // locale.  Linux, not so much.  The following functions avoid the locale
> when
> // that's possible and otherwise do the wrong thing.  FIXME.
> #ifndef _LIBCPP_STABLE_APPLE_ABI
>
> just disappear, or at the very least become greatly reduced.
>

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.

In that block of code, there is also a construct
__locale_raii __current(uselocale(__l), uselocale);
  int __res = sprintf(__s, __format, __args...);

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.

Thanks!

Ruben


>
> Thoughts?
>
> Howard
>
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20110926/3082aac8/attachment.html>


More information about the cfe-dev mailing list