Skip to content

Commit

Permalink
span: Work around MSVC 2019 rejecting constexpr SFINAE with integral …
Browse files Browse the repository at this point in the history
  • Loading branch information
amyspark committed May 10, 2023
1 parent a62d479 commit 0027f9a
Showing 1 changed file with 13 additions and 8 deletions.
21 changes: 13 additions & 8 deletions substrate/span
Original file line number Diff line number Diff line change
Expand Up @@ -92,20 +92,25 @@ namespace substrate

template<typename T, size_t extent_v = dynamic_extent> struct span
{
static constexpr bool matches_extent = extent_v == dynamic_extent;

template<size_t count>
using count_is_dynamic_extent = substrate::bool_constant<count == dynamic_extent>;

template<size_t offset, size_t count> static constexpr
substrate::enable_if_t<count != dynamic_extent, size_t>
substrate::enable_if_t<!count_is_dynamic_extent<count>(), size_t>
_subspanExtent() noexcept { return count; }

template<size_t offset, size_t count> static constexpr
substrate::enable_if_t<extent_v != dynamic_extent && count == dynamic_extent, size_t>
substrate::enable_if_t<!matches_extent && count_is_dynamic_extent<count>(), size_t>
_subspanExtent() noexcept { return extent_v - offset; }

template<size_t offset, size_t count> static constexpr
substrate::enable_if_t<extent_v == dynamic_extent && count == dynamic_extent, size_t>
substrate::enable_if_t<matches_extent && count_is_dynamic_extent<count>(), size_t>
_subspanExtent() noexcept { return dynamic_extent; }

template<typename type_t, size_t N> using isCompatArray_t = internal::and_t<substrate::bool_constant<
extent_v == dynamic_extent || extent_v == N>, internal::isArrayConvertible<T, type_t>>;
matches_extent || extent_v == N>, internal::isArrayConvertible<T, type_t>>;
template<typename type_t, size_t N> constexpr static bool isCompatArray ()
{ return isCompatArray_t<type_t, N>::value; }

Expand Down Expand Up @@ -239,7 +244,7 @@ namespace substrate
}

template<size_t offset, size_t count = dynamic_extent> constexpr auto subspan() const noexcept ->
substrate::enable_if_t<extent_v == dynamic_extent && count != dynamic_extent,
substrate::enable_if_t<matches_extent && !count_is_dynamic_extent<count>(),
span<T, _subspanExtent<offset, count>()>>
{
static_assert(offset <= size(), "offset must be less than or equal to the size of the span");
Expand All @@ -250,7 +255,7 @@ namespace substrate


template<size_t offset, size_t count = dynamic_extent> constexpr auto subspan() const noexcept ->
substrate::enable_if_t<extent_v != dynamic_extent && count == dynamic_extent,
substrate::enable_if_t<!matches_extent && count_is_dynamic_extent<count>(),
span<T, _subspanExtent<offset, count>()>>
{
static_assert(offset <= extent, "offset must be less than or equal to the extent of the span");
Expand All @@ -259,7 +264,7 @@ namespace substrate
}

template<size_t offset, size_t count = dynamic_extent> constexpr auto subspan() const noexcept ->
substrate::enable_if_t<extent_v == dynamic_extent && count == dynamic_extent,
substrate::enable_if_t<matches_extent && count_is_dynamic_extent<count>(),
span<T, _subspanExtent<offset, count>()>>
{
static_assert(offset <= size(), "offset must be less than or equal to the size of the span");
Expand All @@ -270,7 +275,7 @@ namespace substrate


template<size_t offset, size_t count = dynamic_extent> constexpr auto subspan() const noexcept ->
substrate::enable_if_t<extent_v != dynamic_extent && count != dynamic_extent,
substrate::enable_if_t<!matches_extent && !count_is_dynamic_extent<count>(),
span<T, _subspanExtent<offset, count>()>>
{
static_assert(offset <= extent, "offset must be less than or equal to the extent of the span");
Expand Down

0 comments on commit 0027f9a

Please sign in to comment.