From 5e7e68c8b042d5b87b3b2a47999aa3665e1fb7f9 Mon Sep 17 00:00:00 2001 From: Pascal Menuet Date: Sat, 12 Dec 2015 22:51:49 +0100 Subject: [PATCH] For VS2013, fix an ICE by replacing dummy template type parameter by a dummy function parameter --- include/string_span.h | 71 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 71 insertions(+) diff --git a/include/string_span.h b/include/string_span.h index 6a71ce9..01c56dc 100644 --- a/include/string_span.h +++ b/include/string_span.h @@ -34,6 +34,7 @@ #if _MSC_VER <= 1800 #define GSL_MSVC_HAS_TYPE_DEDUCTION_BUG +#define GSL_MSVC2013_ICE_WHEN_USING_DUMMY_TEMPLATE_PARAMETER // noexcept is not understood #ifndef GSL_THROW_ON_CONTRACT_VIOLATION @@ -283,6 +284,74 @@ public: : span_(&(s.at(0)), narrow_cast(s.length())) {} +#ifdef GSL_MSVC2013_ICE_WHEN_USING_DUMMY_TEMPLATE_PARAMETER + template< + typename Cont, + typename DataType = typename Cont::value_type + > + constexpr basic_string_span( + Cont& cont, + std::enable_if_t< + !details::is_span::value + && !details::is_basic_string_span::value + && !(!std::is_const::value && std::is_const::value) + && std::is_convertible::value + && std::is_same().size(), *std::declval().data())>, DataType>::value + >* = nullptr + ) + : span_(cont.data(), cont.size()) + {} + + // disallow creation from temporary containers and strings + template< + typename Cont, + typename DataType = typename Cont::value_type + > + explicit basic_string_span( + Cont&& cont + , + std::enable_if_t< + !details::is_span::value + && !details::is_basic_string_span::value + && std::is_convertible::value + && std::is_same().size(), *std::declval().data())>, DataType>::value + >* = nullptr + ) = delete; + + // from span + template< + typename OtherValueType, + std::ptrdiff_t... OtherDimensions, + typename OtherBounds = static_bounds + > + constexpr basic_string_span( + span other, + typename std::enable_if< + std::is_convertible::value && + std::is_convertible::value + >::type* = nullptr + ) noexcept + : span_(other) + {} + + // from string_span + template< + typename OtherValueType, + std::ptrdiff_t OtherExtent, + typename OtherBounds = static_bounds + > + constexpr basic_string_span( + basic_string_span other, + std::enable_if_t< + std::is_convertible::value + && std::is_convertible::value + >* = nullptr + ) noexcept + : span_(other.data(), other.length()) + {} + +#else // GSL_MSVC2013_ICE_WHEN_USING_DUMMY_TEMPLATE_PARAMETER + // from containers. Containers must have .size() and .data() function signatures template ::value @@ -321,6 +390,7 @@ public: constexpr basic_string_span(basic_string_span other) noexcept : span_(other.data(), other.length()) {} +#endif // GSL_MSVC2013_ICE_WHEN_USING_DUMMY_TEMPLATE_PARAMETER constexpr bool empty() const noexcept { @@ -581,6 +651,7 @@ bool operator>=(const gsl::basic_string_span& one, const gsl::bas #pragma pop_macro("noexcept") #endif // GSL_THROW_ON_CONTRACT_VIOLATION +#undef GSL_MSVC2013_ICE_WHEN_USING_DUMMY_TEMPLATE_PARAMETER #undef GSL_MSVC_HAS_TYPE_DEDUCTION_BUG #endif // _MSC_VER <= 1800