diff --git a/libcxx/test/std/ranges/range.adaptors/range.common.view/begin.pass.cpp b/libcxx/test/std/ranges/range.adaptors/range.common.view/begin.pass.cpp --- a/libcxx/test/std/ranges/range.adaptors/range.common.view/begin.pass.cpp +++ b/libcxx/test/std/ranges/range.adaptors/range.common.view/begin.pass.cpp @@ -69,13 +69,8 @@ using CommonIter = std::common_iterator>; std::same_as auto begin = common.begin(); assert(begin == std::ranges::begin(view)); - } - { - SizedForwardView view{buf, buf + 8}; - std::ranges::common_view const common(view); - using CommonIter = std::common_iterator>; - std::same_as auto begin = common.begin(); - assert(begin == std::ranges::begin(view)); + std::same_as auto cbegin = std::as_const(common).begin(); + assert(cbegin == std::ranges::begin(view)); } { diff --git a/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/base.pass.cpp b/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/base.pass.cpp --- a/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/base.pass.cpp +++ b/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/base.pass.cpp @@ -24,20 +24,13 @@ constexpr bool test() { int buffer[8] = {1, 2, 3, 4, 5, 6, 7, 8}; - auto sw = sentinel_wrapper(buffer + 8); // Note: not 4, but that's OK. - { - const std::ranges::take_view tv(MoveOnlyView{buffer}, 4); - assert(base(tv.end().base()) == base(sw)); - ASSERT_SAME_TYPE(decltype(tv.end().base()), sentinel_wrapper); + std::ranges::take_view tv(MoveOnlyView(buffer), 4); + std::same_as> auto sw1 = tv.end().base(); + assert(base(sw1) == buffer + 8); + std::same_as> auto sw2 = std::as_const(tv).end().base(); + assert(base(sw2) == buffer + 8); } - - { - std::ranges::take_view tv(MoveOnlyView{buffer}, 4); - assert(base(tv.end().base()) == base(sw)); - ASSERT_SAME_TYPE(decltype(tv.end().base()), sentinel_wrapper); - } - return true; } diff --git a/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/ctor.pass.cpp b/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/ctor.pass.cpp --- a/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/ctor.pass.cpp +++ b/libcxx/test/std/ranges/range.adaptors/range.take/sentinel/ctor.pass.cpp @@ -27,27 +27,39 @@ { // Test the default ctor. - std::ranges::take_view tv(MoveOnlyView{buffer}, 4); - assert(decltype(tv.end()){} == std::ranges::next(tv.begin(), 4)); + using TakeView = std::ranges::take_view; + using Sentinel = std::ranges::sentinel_t; + Sentinel s; + TakeView tv = TakeView(MoveOnlyView(buffer), 4); + assert(tv.begin() + 4 == s); } { - std::ranges::take_view nonConst(MoveOnlyView{buffer}, 5); - const std::ranges::take_view tvConst(MoveOnlyView{buffer}, 5); - auto sent1 = nonConst.end(); - // Convert to const. Note, we cannot go the other way. - std::remove_cv_t sent2 = sent1; - - assert(sent1 == std::ranges::next(tvConst.begin(), 5)); - assert(sent2 == std::ranges::next(tvConst.begin(), 5)); + // Test the conversion from "sentinel" to "sentinel-to-const". + using TakeView = std::ranges::take_view; + using Sentinel = std::ranges::sentinel_t; + using ConstSentinel = std::ranges::sentinel_t; + static_assert(std::is_convertible_v); + TakeView tv = TakeView(MoveOnlyView(buffer), 4); + Sentinel s = tv.end(); + ConstSentinel cs = s; + cs = s; // test assignment also + assert(tv.begin() + 4 == s); + assert(tv.begin() + 4 == cs); + assert(std::as_const(tv).begin() + 4 == s); + assert(std::as_const(tv).begin() + 4 == cs); } { - std::ranges::take_view tv(CopyableView{buffer}, 6); - auto sw = sentinel_wrapper(buffer + 6); - using Sent = decltype(tv.end()); - Sent sent = Sent(sw); - assert(base(sent.base()) == base(sw)); + // Test the constructor from "base-sentinel" to "sentinel". + using TakeView = std::ranges::take_view; + using Sentinel = std::ranges::sentinel_t; + sentinel_wrapper sw1 = MoveOnlyView(buffer).end(); + static_assert( std::is_constructible_v>); + static_assert(!std::is_convertible_v, Sentinel>); + auto s = Sentinel(sw1); + std::same_as> auto sw2 = s.base(); + assert(base(sw2) == base(sw1)); } return true; diff --git a/libcxx/test/std/ranges/range.adaptors/range.transform/end.pass.cpp b/libcxx/test/std/ranges/range.adaptors/range.transform/end.pass.cpp --- a/libcxx/test/std/ranges/range.adaptors/range.transform/end.pass.cpp +++ b/libcxx/test/std/ranges/range.adaptors/range.transform/end.pass.cpp @@ -25,44 +25,58 @@ #include "types.h" template -concept EndInvocable = requires(T t) { t.end(); }; - -template -concept EndIsIter = requires(T t) { ++t.end(); }; +concept HasConstQualifiedEnd = requires(const T& t) { t.end(); }; constexpr bool test() { { - std::ranges::transform_view transformView(MoveOnlyView{}, PlusOneMutable{}); - assert(transformView.end().base() == globalBuff + 8); + using TransformView = std::ranges::transform_view; + static_assert(std::ranges::common_range); + TransformView tv; + auto end = tv.end(); + ASSERT_SAME_TYPE(decltype(end.base()), std::ranges::sentinel_t); + assert(base(end.base()) == globalBuff + 8); + static_assert(!HasConstQualifiedEnd); } - { - std::ranges::transform_view transformView(ForwardView{}, PlusOneMutable{}); - assert(transformView.end().base().base() == globalBuff + 8); + using TransformView = std::ranges::transform_view; + static_assert(!std::ranges::common_range); + TransformView tv; + auto end = tv.end(); + ASSERT_SAME_TYPE(decltype(end.base()), std::ranges::sentinel_t); + assert(base(base(end.base())) == globalBuff + 8); + static_assert(!HasConstQualifiedEnd); } - { - std::ranges::transform_view transformView(InputView{}, PlusOneMutable{}); - assert(transformView.end().base() == globalBuff + 8); + using TransformView = std::ranges::transform_view; + static_assert(!std::ranges::common_range); + TransformView tv; + auto end = tv.end(); + ASSERT_SAME_TYPE(decltype(end.base()), std::ranges::sentinel_t); + assert(base(base(end.base())) == globalBuff + 8); + auto cend = std::as_const(tv).end(); + ASSERT_SAME_TYPE(decltype(cend.base()), std::ranges::sentinel_t); + assert(base(base(cend.base())) == globalBuff + 8); } - { - const std::ranges::transform_view transformView(MoveOnlyView{}, PlusOne{}); - assert(transformView.end().base() == globalBuff + 8); + using TransformView = std::ranges::transform_view; + static_assert(std::ranges::common_range); + TransformView tv; + auto end = tv.end(); + ASSERT_SAME_TYPE(decltype(end.base()), std::ranges::sentinel_t); + assert(end.base() == globalBuff + 8); + static_assert(!HasConstQualifiedEnd); + } + { + using TransformView = std::ranges::transform_view; + static_assert(std::ranges::common_range); + TransformView tv; + auto end = tv.end(); + ASSERT_SAME_TYPE(decltype(end.base()), std::ranges::sentinel_t); + assert(end.base() == globalBuff + 8); + auto cend = std::as_const(tv).end(); + ASSERT_SAME_TYPE(decltype(cend.base()), std::ranges::sentinel_t); + assert(cend.base() == globalBuff + 8); } - - static_assert(!EndInvocable>); - static_assert( EndInvocable< std::ranges::transform_view>); - static_assert( EndInvocable>); - static_assert(!EndInvocable>); - static_assert( EndInvocable< std::ranges::transform_view>); - static_assert( EndInvocable>); - - static_assert(!EndIsIter>); - static_assert(!EndIsIter< std::ranges::transform_view>); - static_assert( EndIsIter>); - static_assert( EndIsIter< std::ranges::transform_view>); - return true; } diff --git a/libcxx/test/std/ranges/range.adaptors/range.transform/iterator/base.pass.cpp b/libcxx/test/std/ranges/range.adaptors/range.transform/iterator/base.pass.cpp --- a/libcxx/test/std/ranges/range.adaptors/range.transform/iterator/base.pass.cpp +++ b/libcxx/test/std/ranges/range.adaptors/range.transform/iterator/base.pass.cpp @@ -17,30 +17,32 @@ #include "test_macros.h" #include "../types.h" -template -concept BaseInvocable = requires(std::ranges::iterator_t> iter) { - iter.base(); +template +concept HasBase = requires(It it) { + static_cast(it).base(); }; constexpr bool test() { { - std::ranges::transform_view transformView; - auto iter = std::move(transformView).begin(); - ASSERT_SAME_TYPE(int*, decltype(iter.base())); - assert(iter.base() == globalBuff); - ASSERT_SAME_TYPE(int*, decltype(std::move(iter).base())); - assert(std::move(iter).base() == globalBuff); + using TransformView = std::ranges::transform_view; + TransformView tv; + auto begin = tv.begin(); + ASSERT_SAME_TYPE(decltype(begin.base()), int*); + assert(begin.base() == globalBuff); + ASSERT_SAME_TYPE(decltype(std::move(begin).base()), int*); + assert(std::move(begin).base() == globalBuff); } - { - std::ranges::transform_view transformView; - auto iter = transformView.begin(); - assert(std::move(iter).base() == globalBuff); - ASSERT_SAME_TYPE(cpp20_input_iterator, decltype(std::move(iter).base())); + using TransformView = std::ranges::transform_view; + TransformView tv; + auto begin = tv.begin(); + static_assert(!HasBase); + static_assert(HasBase); + static_assert(!HasBase); + static_assert(!HasBase); + std::same_as> auto it = std::move(begin).base(); + assert(base(it) == globalBuff); } - - static_assert(!BaseInvocable); - return true; } diff --git a/libcxx/test/std/ranges/range.adaptors/range.transform/types.h b/libcxx/test/std/ranges/range.adaptors/range.transform/types.h --- a/libcxx/test/std/ranges/range.adaptors/range.transform/types.h +++ b/libcxx/test/std/ranges/range.adaptors/range.transform/types.h @@ -85,12 +85,11 @@ struct InputView : std::ranges::view_base { int *ptr_; constexpr explicit InputView(int* ptr = globalBuff) : ptr_(ptr) {} - constexpr cpp20_input_iterator begin() const { return cpp20_input_iterator(ptr_); } - constexpr int *end() const { return ptr_ + 8; } + constexpr auto begin() const { return cpp20_input_iterator(ptr_); } + constexpr auto end() const { return sentinel_wrapper>(cpp20_input_iterator(ptr_ + 8)); } }; -// TODO: remove these bogus operators -constexpr bool operator==(const cpp20_input_iterator &lhs, int* rhs) { return lhs.base() == rhs; } -constexpr bool operator==(int* lhs, const cpp20_input_iterator &rhs) { return rhs.base() == lhs; } +static_assert( std::ranges::view); +static_assert(!std::ranges::sized_range); struct SizedSentinelView : std::ranges::view_base { int count_;