diff --git a/include/boost/regex/v4/regex_traits_defaults.hpp b/include/boost/regex/v4/regex_traits_defaults.hpp index fe42420b..2a516c8e 100644 --- a/include/boost/regex/v4/regex_traits_defaults.hpp +++ b/include/boost/regex/v4/regex_traits_defaults.hpp @@ -209,41 +209,58 @@ std::ptrdiff_t global_length(const charT* p) } return n; } -inline std::ptrdiff_t global_length(const char* p) +template<> +inline std::ptrdiff_t global_length(const char* p) { return (std::strlen)(p); } #ifndef BOOST_NO_WREGEX -inline std::ptrdiff_t global_length(const wchar_t* p) +template<> +inline std::ptrdiff_t global_length(const wchar_t* p) { return (std::wcslen)(p); } #endif template -#if !BOOST_WORKAROUND(__EDG_VERSION__, <= 245) -inline -#endif -charT BOOST_REGEX_CALL global_lower(charT c) +inline charT BOOST_REGEX_CALL global_lower(charT c) { return c; } template -#if !BOOST_WORKAROUND(__EDG_VERSION__, <= 245) -inline -#endif -charT BOOST_REGEX_CALL global_upper(charT c) +inline charT BOOST_REGEX_CALL global_upper(charT c) { return c; } -BOOST_REGEX_DECL char BOOST_REGEX_CALL global_lower(char c); -BOOST_REGEX_DECL char BOOST_REGEX_CALL global_upper(char c); + +BOOST_REGEX_DECL char BOOST_REGEX_CALL do_global_lower(char c); +BOOST_REGEX_DECL char BOOST_REGEX_CALL do_global_upper(char c); #ifndef BOOST_NO_WREGEX -BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL global_lower(wchar_t c); -BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL global_upper(wchar_t c); +BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL do_global_lower(wchar_t c); +BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL do_global_upper(wchar_t c); #endif #ifdef BOOST_REGEX_HAS_OTHER_WCHAR_T -BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL global_lower(unsigned short c); -BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL global_upper(unsigned short c); +BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL do_global_lower(unsigned short c); +BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL do_global_upper(unsigned short c); +#endif +// +// This sucks: declare template specialisations of global_lower/global_upper +// that just forward to the non-template implementation functions. We do +// this because there is one compiler (Compaq Tru64 C++) that doesn't seem +// to differentiate between templates and non-template overloads.... +// what's more, the primary template, plus all overloads have to be +// defined in the same translation unit (if one is inline they all must be) +// otherwise the "local template instantiation" compiler option can pick +// the wrong instantiation when linking: +// +template<> inline char global_lower(char c){ return do_global_lower(c); } +template<> inline char global_upper(char c){ return do_global_upper(c); } +#ifndef BOOST_NO_WREGEX +template<> inline wchar_t global_lower(wchar_t c){ return do_global_lower(c); } +template<> inline wchar_t global_upper(wchar_t c){ return do_global_upper(c); } +#endif +#ifdef BOOST_REGEX_HAS_OTHER_WCHAR_T +template<> inline unsigned short global_lower(unsigned short c){ return do_global_lower(c); } +template<> inline unsigned short global_upper(unsigned short c){ return do_global_upper(c); } #endif template diff --git a/src/regex_traits_defaults.cpp b/src/regex_traits_defaults.cpp index 7ef24a04..8f5a980c 100644 --- a/src/regex_traits_defaults.cpp +++ b/src/regex_traits_defaults.cpp @@ -260,32 +260,32 @@ BOOST_REGEX_DECL std::string BOOST_REGEX_CALL lookup_default_collate_name(const return std::string(); } -BOOST_REGEX_DECL char BOOST_REGEX_CALL global_lower(char c) +BOOST_REGEX_DECL char BOOST_REGEX_CALL do_global_lower(char c) { return static_cast((std::tolower)((unsigned char)c)); } -BOOST_REGEX_DECL char BOOST_REGEX_CALL global_upper(char c) +BOOST_REGEX_DECL char BOOST_REGEX_CALL do_global_upper(char c) { return static_cast((std::toupper)((unsigned char)c)); } #ifndef BOOST_NO_WREGEX -BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL global_lower(wchar_t c) +BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL do_global_lower(wchar_t c) { return (std::towlower)(c); } -BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL global_upper(wchar_t c) +BOOST_REGEX_DECL wchar_t BOOST_REGEX_CALL do_global_upper(wchar_t c) { return (std::towupper)(c); } #ifdef BOOST_REGEX_HAS_OTHER_WCHAR_T -BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL global_lower(unsigned short c) +BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL do_global_lower(unsigned short c) { return (std::towlower)(c); } -BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL global_upper(unsigned short c) +BOOST_REGEX_DECL unsigned short BOOST_REGEX_CALL do_global_upper(unsigned short c) { return (std::towupper)(c); } diff --git a/test/regress/test_locale.cpp b/test/regress/test_locale.cpp index 1f1b49d5..703e76d5 100644 --- a/test/regress/test_locale.cpp +++ b/test/regress/test_locale.cpp @@ -140,13 +140,13 @@ void test_en_locale(const char* name, boost::uint32_t lcid) #if !BOOST_WORKAROUND(__BORLANDC__, < 0x600) // these tests are disabled for Borland C++: a bug in std::collate // causes these tests to crash (pointer overrun in std::collate::do_transform). - TEST_REGEX_SEARCH_L("[a-z]+", perl|collate, "\xdf\xe0\xe1\xe2\xe3\xe4\xe5\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf8\xf9\xfa\xfb\xfc", match_default, make_array(0, 28, -2, -2)); - TEST_REGEX_SEARCH_L("[a-z]+", perl|collate, "\xbf\xc0\xc1\xc2\xc3\xc4\xc5\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd8\xd9\xda\xdb\xdc", match_default, make_array(1, 28, -2, -2)); + TEST_REGEX_SEARCH_L("[a-z]+", perl|::boost::regex_constants::collate, "\xdf\xe0\xe1\xe2\xe3\xe4\xe5\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf8\xf9\xfa\xfb\xfc", match_default, make_array(0, 28, -2, -2)); + TEST_REGEX_SEARCH_L("[a-z]+", perl|::boost::regex_constants::collate, "\xbf\xc0\xc1\xc2\xc3\xc4\xc5\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd8\xd9\xda\xdb\xdc", match_default, make_array(1, 28, -2, -2)); // and equivalence classes: TEST_REGEX_SEARCH_L("[[=a=]]+", perl, "aA\xe0\xe1\xe2\xe3\xe4\xe5\xc0\xc1\xc2\xc3\xc4\xc5", match_default, make_array(0, 14, -2, -2)); // case mapping: - TEST_REGEX_SEARCH_L("[A-Z]+", perl|icase|collate, "\xdf\xe0\xe1\xe2\xe3\xe4\xe5\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf8\xf9\xfa\xfb\xfc", match_default, make_array(0, 28, -2, -2)); - TEST_REGEX_SEARCH_L("[a-z]+", perl|icase|collate, "\xbf\xc0\xc1\xc2\xc3\xc4\xc5\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd8\xd9\xda\xdb\xdc", match_default, make_array(1, 28, -2, -2)); + TEST_REGEX_SEARCH_L("[A-Z]+", perl|icase|::boost::regex_constants::collate, "\xdf\xe0\xe1\xe2\xe3\xe4\xe5\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf8\xf9\xfa\xfb\xfc", match_default, make_array(0, 28, -2, -2)); + TEST_REGEX_SEARCH_L("[a-z]+", perl|icase|::boost::regex_constants::collate, "\xbf\xc0\xc1\xc2\xc3\xc4\xc5\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd8\xd9\xda\xdb\xdc", match_default, make_array(1, 28, -2, -2)); TEST_REGEX_SEARCH_L("\xc0\xc1\xc2\xc3\xc4\xc5\xc6\xc7\xc8\xc9\xca\xcb\xcc\xcd\xce\xcf\xd0\xd1\xd2\xd3\xd4\xd5\xd6\xd8\xd9\xda\xdb\xdc\xdd", perl|icase, "\xdf\xe0\xe1\xe2\xe3\xe4\xe5\xe6\xe7\xe8\xe9\xea\xeb\xec\xed\xee\xef\xf0\xf1\xf2\xf3\xf4\xf5\xf6\xf8\xf9\xfa\xfb\xfc\xfd\xfe", match_default, make_array(1, 30, -2, -2)); #endif } diff --git a/test/regress/test_sets.cpp b/test/regress/test_sets.cpp index b1cd7066..5d692092 100644 --- a/test/regress/test_sets.cpp +++ b/test/regress/test_sets.cpp @@ -56,7 +56,7 @@ void test_sets() TEST_REGEX_SEARCH("a[^-3]c", extended, "a-c", match_default, make_array(-2, -2)); TEST_REGEX_SEARCH("a[^-3]c", extended, "a3c", match_default, make_array(-2, -2)); TEST_REGEX_SEARCH("a[^-3]c", extended, "axc", match_default, make_array(0, 3, -2, -2)); - TEST_INVALID_REGEX("a[3-1]c", extended & ~collate); + TEST_INVALID_REGEX("a[3-1]c", extended & ~::boost::regex_constants::collate); TEST_INVALID_REGEX("a[1-3-5]c", extended); TEST_INVALID_REGEX("a[1-", extended); TEST_INVALID_REGEX("a[\\9]", perl);