Rollback: Improve detection for wchar_t and wstring support.
Add a configurable `GTEST_HAS_WCHAR` option to control whether to provide `wchar_t*` overloads for `PrintTo`. Check implementation-specific standard library defines to determine proper defaults for `GTEST_HAS_WCHAR` and `GTEST_HAS_STD_WSTRING` and to produce compile errors if the users pick a configuration that depends on unavailable standard library features. PiperOrigin-RevId: 958668507 Change-Id: Ic9b78d83fb455dff7d993303d54a0bde749a8cd8
This commit is contained in:
committed by
Copybara-Service
parent
92f71eddb0
commit
51725d1111
@@ -676,13 +676,18 @@ inline void PrintTo(char32_t* s, ::std::ostream* os) {
|
|||||||
PrintTo(ImplicitCast_<const char32_t*>(s), os);
|
PrintTo(ImplicitCast_<const char32_t*>(s), os);
|
||||||
}
|
}
|
||||||
|
|
||||||
#if GTEST_HAS_WCHAR
|
// MSVC can be configured to define wchar_t as a typedef of unsigned
|
||||||
|
// short. It defines _NATIVE_WCHAR_T_DEFINED when wchar_t is a native
|
||||||
|
// type. When wchar_t is a typedef, defining an overload for const
|
||||||
|
// wchar_t* would cause unsigned short* be printed as a wide string,
|
||||||
|
// possibly causing invalid memory accesses.
|
||||||
|
#if !defined(_MSC_VER) || defined(_NATIVE_WCHAR_T_DEFINED)
|
||||||
// Overloads for wide C strings
|
// Overloads for wide C strings
|
||||||
GTEST_API_ void PrintTo(const wchar_t* s, ::std::ostream* os);
|
GTEST_API_ void PrintTo(const wchar_t* s, ::std::ostream* os);
|
||||||
inline void PrintTo(wchar_t* s, ::std::ostream* os) {
|
inline void PrintTo(wchar_t* s, ::std::ostream* os) {
|
||||||
PrintTo(ImplicitCast_<const wchar_t*>(s), os);
|
PrintTo(ImplicitCast_<const wchar_t*>(s), os);
|
||||||
}
|
}
|
||||||
#endif // GTEST_HAS_WCHAR
|
#endif
|
||||||
|
|
||||||
// Overload for C arrays. Multi-dimensional arrays are printed
|
// Overload for C arrays. Multi-dimensional arrays are printed
|
||||||
// properly.
|
// properly.
|
||||||
|
|||||||
@@ -80,11 +80,6 @@
|
|||||||
// is/isn't available.
|
// is/isn't available.
|
||||||
// GTEST_HAS_RTTI - Define it to 1/0 to indicate that RTTI is/isn't
|
// GTEST_HAS_RTTI - Define it to 1/0 to indicate that RTTI is/isn't
|
||||||
// enabled.
|
// enabled.
|
||||||
// GTEST_HAS_WCHAR - Define it to 1/0 to indicate that wide
|
|
||||||
// characters are/aren't supported. (Google Test
|
|
||||||
// can be used where std::char_traits<wchar_t> and
|
|
||||||
// libc wchar_t functions (putwc, getwc, etc.) are
|
|
||||||
// unavailable.)
|
|
||||||
// GTEST_HAS_STD_WSTRING - Define it to 1/0 to indicate that
|
// GTEST_HAS_STD_WSTRING - Define it to 1/0 to indicate that
|
||||||
// std::wstring does/doesn't work (Google Test can
|
// std::wstring does/doesn't work (Google Test can
|
||||||
// be used where std::wstring is unavailable).
|
// be used where std::wstring is unavailable).
|
||||||
@@ -504,89 +499,22 @@ typedef struct _RTL_CRITICAL_SECTION GTEST_CRITICAL_SECTION;
|
|||||||
#endif // defined(_MSC_VER) || defined(__BORLANDC__)
|
#endif // defined(_MSC_VER) || defined(__BORLANDC__)
|
||||||
#endif // GTEST_HAS_EXCEPTIONS
|
#endif // GTEST_HAS_EXCEPTIONS
|
||||||
|
|
||||||
// 1. Calculate default GTEST_HAS_WCHAR and GTEST_HAS_STD_WSTRING values based
|
#ifndef GTEST_HAS_STD_WSTRING
|
||||||
// on compiler / STL capabilities.
|
// The user didn't tell us whether ::std::wstring is available, so we need
|
||||||
#if defined(_MSC_VER)
|
// to figure it out.
|
||||||
// MSVC always supports ::std::wstring.
|
|
||||||
#define GTEST_HAS_STD_WSTRING_DEFAULT 1
|
|
||||||
// MSVC either defines wchar_t as a typedef of unsigned short, or as a native
|
|
||||||
// type (in which case, it defines _NATIVE_WCHAR_T_DEFINED). When wchar_t is a
|
|
||||||
// typedef, defining an overload for const wchar_t* would cause unsigned short*
|
|
||||||
// be printed as a wide string, possibly causing invalid memory accesses, so we
|
|
||||||
// omit wchar_t overloads in that case.
|
|
||||||
#if defined(_NATIVE_WCHAR_T_DEFINED)
|
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 1
|
|
||||||
#else
|
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 0
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#elif defined(_LIBCPP_VERSION)
|
|
||||||
#if _LIBCPP_HAS_WIDE_CHARACTERS
|
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 1
|
|
||||||
#define GTEST_HAS_STD_WSTRING_DEFAULT 1
|
|
||||||
#else
|
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 0
|
|
||||||
#define GTEST_HAS_STD_WSTRING_DEFAULT 0
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#elif defined(__GLIBCXX__)
|
|
||||||
#if _GLIBCXX_USE_WCHAR_T
|
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 1
|
|
||||||
#define GTEST_HAS_STD_WSTRING_DEFAULT 1
|
|
||||||
#else
|
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 0
|
|
||||||
#define GTEST_HAS_STD_WSTRING_DEFAULT 0
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#else
|
|
||||||
// Unknown standard library implementation; fall back to a list of OSes known to
|
|
||||||
// not support wide characters.
|
|
||||||
//
|
|
||||||
// Cygwin 1.7 and below doesn't support ::std::wstring.
|
// Cygwin 1.7 and below doesn't support ::std::wstring.
|
||||||
// Solaris' libc++ doesn't support it either. Android has
|
// Solaris' libc++ doesn't support it either. Android has
|
||||||
// no support for it at least as recent as Froyo (2.2).
|
// no support for it at least as recent as Froyo (2.2).
|
||||||
//
|
|
||||||
// Always let the user override the defaults in this case; they might have more
|
|
||||||
// information about what's supported than we do.
|
|
||||||
#if (!(defined(GTEST_OS_LINUX_ANDROID) || defined(GTEST_OS_CYGWIN) || \
|
#if (!(defined(GTEST_OS_LINUX_ANDROID) || defined(GTEST_OS_CYGWIN) || \
|
||||||
defined(GTEST_OS_SOLARIS) || defined(GTEST_OS_HAIKU) || \
|
defined(GTEST_OS_SOLARIS) || defined(GTEST_OS_HAIKU) || \
|
||||||
defined(GTEST_OS_ESP32) || defined(GTEST_OS_ESP8266) || \
|
defined(GTEST_OS_ESP32) || defined(GTEST_OS_ESP8266) || \
|
||||||
defined(GTEST_OS_XTENSA) || defined(GTEST_OS_QURT) || \
|
defined(GTEST_OS_XTENSA) || defined(GTEST_OS_QURT) || \
|
||||||
defined(GTEST_OS_NXP_QN9090) || defined(GTEST_OS_NRF52)))
|
defined(GTEST_OS_NXP_QN9090) || defined(GTEST_OS_NRF52)))
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 1
|
#define GTEST_HAS_STD_WSTRING 1
|
||||||
#define GTEST_HAS_STD_WSTRING_DEFAULT 1
|
|
||||||
#else
|
#else
|
||||||
#define GTEST_HAS_WCHAR_DEFAULT 0
|
#define GTEST_HAS_STD_WSTRING 0
|
||||||
#define GTEST_HAS_STD_WSTRING_DEFAULT 0
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// 2. Validate explicit user overrides (if user passed -DGTEST_HAS_*=1)
|
|
||||||
#if defined(GTEST_HAS_WCHAR) && GTEST_HAS_WCHAR
|
|
||||||
#if defined(_MSC_VER) && !defined(_NATIVE_WCHAR_T_DEFINED)
|
|
||||||
#error Cannot explicitly enable GTEST_HAS_WCHAR when wchar_t is a typedef.
|
|
||||||
#elif defined(_LIBCPP_VERSION) && !_LIBCPP_HAS_WIDE_CHARACTERS
|
|
||||||
#error Cannot explicitly enable GTEST_HAS_WCHAR without libc++ wide character support.
|
|
||||||
#elif defined(__GLIBCXX__) && !_GLIBCXX_USE_WCHAR_T
|
|
||||||
#error Cannot explicitly enable GTEST_HAS_WCHAR without libstdc++ wide character support.
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if defined(GTEST_HAS_STD_WSTRING) && GTEST_HAS_STD_WSTRING
|
|
||||||
#if defined(_LIBCPP_VERSION) && !_LIBCPP_HAS_WIDE_CHARACTERS
|
|
||||||
#error Cannot explicitly enable GTEST_HAS_STD_WSTRING without libc++ wide character support.
|
|
||||||
#elif defined(__GLIBCXX__) && !_GLIBCXX_USE_WCHAR_T
|
|
||||||
#error Cannot explicitly enable GTEST_HAS_STD_WSTRING without libstdc++ wide character support.
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// 3. Set final values if not explicitly overridden by user
|
|
||||||
#if !defined(GTEST_HAS_WCHAR)
|
|
||||||
#define GTEST_HAS_WCHAR GTEST_HAS_WCHAR_DEFAULT
|
|
||||||
#endif
|
|
||||||
#if !defined(GTEST_HAS_STD_WSTRING)
|
|
||||||
#define GTEST_HAS_STD_WSTRING GTEST_HAS_STD_WSTRING_DEFAULT
|
|
||||||
#endif
|
#endif
|
||||||
|
#endif // GTEST_HAS_STD_WSTRING
|
||||||
|
|
||||||
#ifndef GTEST_HAS_FILE_SYSTEM
|
#ifndef GTEST_HAS_FILE_SYSTEM
|
||||||
// Most platforms support a file system.
|
// Most platforms support a file system.
|
||||||
|
|||||||
@@ -445,10 +445,16 @@ void PrintTo(const char16_t* s, ostream* os) { PrintCStringTo(s, os); }
|
|||||||
|
|
||||||
void PrintTo(const char32_t* s, ostream* os) { PrintCStringTo(s, os); }
|
void PrintTo(const char32_t* s, ostream* os) { PrintCStringTo(s, os); }
|
||||||
|
|
||||||
#if GTEST_HAS_WCHAR
|
// MSVC compiler can be configured to define whar_t as a typedef
|
||||||
|
// of unsigned short. Defining an overload for const wchar_t* in that case
|
||||||
|
// would cause pointers to unsigned shorts be printed as wide strings,
|
||||||
|
// possibly accessing more memory than intended and causing invalid
|
||||||
|
// memory accesses. MSVC defines _NATIVE_WCHAR_T_DEFINED symbol when
|
||||||
|
// wchar_t is implemented as a native type.
|
||||||
|
#if !defined(_MSC_VER) || defined(_NATIVE_WCHAR_T_DEFINED)
|
||||||
// Prints the given wide C string to the ostream.
|
// Prints the given wide C string to the ostream.
|
||||||
void PrintTo(const wchar_t* s, ostream* os) { PrintCStringTo(s, os); }
|
void PrintTo(const wchar_t* s, ostream* os) { PrintCStringTo(s, os); }
|
||||||
#endif // GTEST_HAS_WCHAR
|
#endif // wchar_t is native
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
|||||||
@@ -648,7 +648,13 @@ TEST(PrintU32StringTest, EscapesProperly) {
|
|||||||
Print(p));
|
Print(p));
|
||||||
}
|
}
|
||||||
|
|
||||||
#if GTEST_HAS_WCHAR
|
// MSVC compiler can be configured to define whar_t as a typedef
|
||||||
|
// of unsigned short. Defining an overload for const wchar_t* in that case
|
||||||
|
// would cause pointers to unsigned shorts be printed as wide strings,
|
||||||
|
// possibly accessing more memory than intended and causing invalid
|
||||||
|
// memory accesses. MSVC defines _NATIVE_WCHAR_T_DEFINED symbol when
|
||||||
|
// wchar_t is implemented as a native type.
|
||||||
|
#if !defined(_MSC_VER) || defined(_NATIVE_WCHAR_T_DEFINED)
|
||||||
|
|
||||||
// const wchar_t*.
|
// const wchar_t*.
|
||||||
TEST(PrintWideCStringTest, Const) {
|
TEST(PrintWideCStringTest, Const) {
|
||||||
@@ -679,7 +685,7 @@ TEST(PrintWideCStringTest, EscapesProperly) {
|
|||||||
"\\n\\r\\t\\v\\xD3\\x576\\x8D3\\xC74D a\"",
|
"\\n\\r\\t\\v\\xD3\\x576\\x8D3\\xC74D a\"",
|
||||||
Print(static_cast<const wchar_t*>(s)));
|
Print(static_cast<const wchar_t*>(s)));
|
||||||
}
|
}
|
||||||
#endif // GTEST_HAS_WCHAR
|
#endif // native wchar_t
|
||||||
|
|
||||||
// Tests printing pointers to other char types.
|
// Tests printing pointers to other char types.
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user