diff --git a/libcxx/include/__ranges/to.h b/libcxx/include/__ranges/to.h index c937b0656de87d..360c33ee8f2083 100644 --- a/libcxx/include/__ranges/to.h +++ b/libcxx/include/__ranges/to.h @@ -109,8 +109,11 @@ template __result.reserve(static_cast>(ranges::size(__range))); } - for (auto&& __ref : __range) { - using _Ref = decltype(__ref); + auto __iter = ranges::begin(__range); + auto __sent = ranges::end(__range); + for (; __iter != __sent; ++__iter) { + auto&& __ref = *__iter; + using _Ref = decltype(__ref); if constexpr (requires { __result.emplace_back(std::declval<_Ref>()); }) { __result.emplace_back(std::forward<_Ref>(__ref)); } else if constexpr (requires { __result.push_back(std::declval<_Ref>()); }) { diff --git a/libcxx/test/std/ranges/range.utility/range.utility.conv/to.pass.cpp b/libcxx/test/std/ranges/range.utility/range.utility.conv/to.pass.cpp index a983745fd636e8..26c7af6d88479b 100644 --- a/libcxx/test/std/ranges/range.utility/range.utility.conv/to.pass.cpp +++ b/libcxx/test/std/ranges/range.utility/range.utility.conv/to.pass.cpp @@ -550,11 +550,30 @@ constexpr void test_recursive() { assert(std::ranges::to(in_owning_view) == result); } +struct adl_only_range { + static constexpr int numbers[2]{42, 1729}; + + void begin() const = delete; + void end() const = delete; + + friend constexpr const int* begin(const adl_only_range&) { return std::ranges::begin(numbers); } + friend constexpr const int* end(const adl_only_range&) { return std::ranges::end(numbers); } +}; + +constexpr void test_lwg4016_regression() { + using Cont = Container; + + std::ranges::contiguous_range auto r = adl_only_range{}; + auto v = r | std::ranges::to(); + assert(std::ranges::equal(v, adl_only_range::numbers)); +} + constexpr bool test() { test_constraints(); test_ctr_choice_order(); test_lwg_3785(); test_recursive(); + test_lwg4016_regression(); return true; }