Skip to content

Commit 4a19ce2

Browse files
committed
New issue from Casey: "contiguous_iterator should require to_address(I{})"
1 parent 7b78b80 commit 4a19ce2

File tree

1 file changed

+79
-0
lines changed

1 file changed

+79
-0
lines changed

xml/issue4170.xml

Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
<?xml version='1.0' encoding='utf-8' standalone='no'?>
2+
<!DOCTYPE issue SYSTEM "lwg-issue.dtd">
3+
4+
<issue num="4170" status="New">
5+
<title>`contiguous_iterator` should require `to_address(I{})`</title>
6+
<section><sref ref="[iterator.concept.contiguous]"/></section>
7+
<submitter>Casey Carter</submitter>
8+
<date>01 Nov 2024</date>
9+
<priority>99</priority>
10+
11+
<discussion>
12+
<p>
13+
The design intent of the `contiguous_iterator` concept is that iterators can be converted
14+
to pointers that denote the same sequence of elements. Practically, that means that a common range
15+
`[i, j)` or counted range `i + [0, n)` can be processed with extremely efficient
16+
low-level C or assembly code that operates on `[to_address(i), to_address(j))` (respectively
17+
`to_address(i) + [0, n)`). A value-initialized iterator `I{}` can be used to denote the empty
18+
ranges `[I{}, I{})` and `I{} + [0, 0)`. While the existing semantic requirements of
19+
`contiguous_iterator` enable us to convert both dereferenceable and past-the-end iterators with
20+
`to_address` converting such ranges to pointer ranges requires either (1) `to_address(I{})`
21+
is well-defined and equality preserving so e.g. `copy(i, j)` can directly dispatch to
22+
`__vectorized_copy(to_address(j), to_address(i), j - i)` when it detects contiguous iterators
23+
to types that can be trivially copied, or (2) we have to introduce a branch guarding such calls
24+
with `i != j` (or <tt>n &gt; 0</tt> for counted ranges).
25+
<p/>
26+
Since we already require `to_address` to be equality-preserving, we need only require
27+
`to_address(I{})` to be well-defined. It's then easily demonstrable that
28+
`to_address(I{}) == to_address(I{})` and `to_address(I{}) == to_address(I{)) + 0` hold.
29+
</p>
30+
</discussion>
31+
32+
<resolution>
33+
<p>
34+
This wording is relative to <paper num="N4993"/>.
35+
</p>
36+
37+
<ol>
38+
<li><p>Modify <sref ref="[iterator.concept.contiguous]"/> as indicated:</p>
39+
40+
<blockquote>
41+
<p>
42+
-1- The `contiguous_iterator` concept provides a guarantee that the denoted elements are stored contiguously
43+
in memory.
44+
</p>
45+
<blockquote>
46+
<pre>
47+
template&lt;class I&gt;
48+
concept contiguous_iterator =
49+
random_access_iterator&lt;I&gt; &amp;&amp;
50+
derived_from&lt;<i>ITER_CONCEPT</i>(I), contiguous_iterator_tag&gt; &amp;&amp;
51+
is_lvalue_reference_v&lt;iter_reference_t&lt;I&gt;&gt; &amp;&amp;
52+
same_as&lt;iter_value_t&lt;I&gt;, remove_cvref_t&lt;iter_reference_t&lt;I&gt;&gt;&gt; &amp;&amp;
53+
requires(const I&amp; i) {
54+
{ to_address(i) } -&gt; same_as&lt;add_pointer_t&lt;iter_reference_t&lt;I&gt;&gt;&gt;;
55+
};
56+
</pre>
57+
</blockquote>
58+
<p>
59+
-2- Let `a` and `b` be dereferenceable iterators and `c` be a non-dereferenceable iterator of type
60+
`I` such that `b` is reachable from `a` and `c` is reachable from `b`, and let `D` be
61+
<tt>iter_difference_t&lt;I&gt;</tt>. The type `I` models `contiguous_iterator` only if
62+
</p>
63+
64+
<ol style="list-style-type: none">
65+
<li><p>(2.1) &mdash; `to_address(a) == addressof(*a)`,</p></li>
66+
<li><p>(2.2) &mdash; `to_address(b) == to_address(a) + D(b - a)`,</p></li>
67+
<li><p>(2.3) &mdash; `to_address(c) == to_address(a) + D(c - a)`,</p></li>
68+
<li><p><ins>(2.?) &mdash; `to_address(I{})` is well-defined,</ins></p></li>
69+
<li><p>(2.4) &mdash; `ranges::iter_move(a)` has the same type, value category, and effects as
70+
`std::move(*a)`, and</p></li>
71+
<li><p>(2.5) &mdash; if `ranges::iter_swap(a, b)` is well-formed, it has effects equivalent to
72+
`ranges::swap(*a, *b)`.</p></li>
73+
</ol>
74+
</blockquote>
75+
76+
</li>
77+
</ol>
78+
</resolution>
79+
</issue>

0 commit comments

Comments
 (0)