You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
[libc++] Fix uninitialized algorithms when using unconstrained comparison operators (#69373)
If an iterator passed to std::uninitialized_copy & friends provided an
unconstrained comparison operator, we would trigger an ambiguous
overload resolution because we used to compare against
__unreachable_sentinel in our implementation.
This patch fixes that by only comparing the output iterator when it is
actually required, i.e. in the <ranges> versions of the algorithms.
Fixes#69334
Copy file name to clipboardExpand all lines: libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/ranges_uninitialized_copy.pass.cpp
+32Lines changed: 32 additions & 0 deletions
Original file line number
Diff line number
Diff line change
@@ -27,6 +27,7 @@
27
27
28
28
#include"../buffer.h"
29
29
#include"../counted.h"
30
+
#include"../overload_compare_iterator.h"
30
31
#include"test_macros.h"
31
32
#include"test_iterators.h"
32
33
@@ -396,5 +397,36 @@ int main(int, char**) {
396
397
}
397
398
}
398
399
400
+
// Test with an iterator that overloads operator== and operator!= as the input and output iterators
Copy file name to clipboardExpand all lines: libcxx/test/std/utilities/memory/specialized.algorithms/uninitialized.copy/ranges_uninitialized_copy_n.pass.cpp
+32Lines changed: 32 additions & 0 deletions
Original file line number
Diff line number
Diff line change
@@ -24,6 +24,7 @@
24
24
25
25
#include"../buffer.h"
26
26
#include"../counted.h"
27
+
#include"../overload_compare_iterator.h"
27
28
#include"test_macros.h"
28
29
#include"test_iterators.h"
29
30
@@ -161,5 +162,36 @@ int main(int, char**) {
161
162
std::ranges::uninitialized_copy_n(std::move(in), N, out.begin(), out.end());
162
163
}
163
164
165
+
// Test with an iterator that overloads operator== and operator!= as the input and output iterators
166
+
{
167
+
using T = int;
168
+
using Iterator = overload_compare_iterator<T*>;
169
+
constint N = 5;
170
+
171
+
// input
172
+
{
173
+
char pool[sizeof(T) * N] = {0};
174
+
T* p = reinterpret_cast<T*>(pool);
175
+
T* p_end = reinterpret_cast<T*>(pool) + N;
176
+
T array[N] = {1, 2, 3, 4, 5};
177
+
std::ranges::uninitialized_copy_n(Iterator(array), N, p, p_end);
178
+
for (int i = 0; i != N; ++i) {
179
+
assert(array[i] == p[i]);
180
+
}
181
+
}
182
+
183
+
// output
184
+
{
185
+
char pool[sizeof(T) * N] = {0};
186
+
T* p = reinterpret_cast<T*>(pool);
187
+
T* p_end = reinterpret_cast<T*>(pool) + N;
188
+
T array[N] = {1, 2, 3, 4, 5};
189
+
std::ranges::uninitialized_copy_n(array, N, Iterator(p), Iterator(p_end));
0 commit comments