[libc++] Fix return value of snprintf_l() on Windows when buffer is too small

When the output buffer is too small to contain the output, `vsnprintf()`
fills the buffer and returns the number of characters that __would have__
been written if the buffer was sufficiently large.

`_vnsprintf_s()` on the other hand fills the buffer and returns -1 when this
happens.  We want the former behavior, but we also want to be able to
pass in a locale to prevent having to call `setlocale()`.

`__stdio_common_vsprintf()` is the only function general enough to get
the behavior we want.

Differential Revision: https://reviews.llvm.org/D59727


git-svn-id: https://llvm.org/svn/llvm-project/libcxx/trunk@357024 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/src/support/win32/locale_win32.cpp b/src/support/win32/locale_win32.cpp
index d02d7ff..ee3a430 100644
--- a/src/support/win32/locale_win32.cpp
+++ b/src/support/win32/locale_win32.cpp
@@ -87,14 +87,15 @@
 
 int snprintf_l(char *ret, size_t n, locale_t loc, const char *format, ...)
 {
-#if !defined(_LIBCPP_MSVCRT)
-    __libcpp_locale_guard __current(loc);
-#endif
     va_list ap;
     va_start( ap, format );
 #if defined(_LIBCPP_MSVCRT)
-    int result = _vsnprintf_l( ret, n, format, loc, ap );
+    // FIXME: Remove usage of internal CRT function and globals.
+    int result = __stdio_common_vsprintf(
+        _CRT_INTERNAL_LOCAL_PRINTF_OPTIONS | _CRT_INTERNAL_PRINTF_STANDARD_SNPRINTF_BEHAVIOR,
+        ret, n, format, loc, ap);
 #else
+    __libcpp_locale_guard __current(loc);
     int result = vsnprintf( ret, n, format, ap );
 #endif
     va_end(ap);