Skip to content

Commit 9686822

Browse files
committed
move TrustedRandomAccess into its own module
1 parent aec6846 commit 9686822

File tree

10 files changed

+117
-111
lines changed

10 files changed

+117
-111
lines changed

library/core/src/iter/adapters/cloned.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
1-
use crate::iter::adapters::{zip::try_get_unchecked, TrustedRandomAccess};
1+
use crate::iter::traits::trusted_random_access::try_get_unchecked;
2+
use crate::iter::traits::TrustedRandomAccess;
23
use crate::iter::{FusedIterator, TrustedLen};
34
use crate::ops::Try;
45

library/core/src/iter/adapters/copied.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
1-
use crate::iter::adapters::{zip::try_get_unchecked, TrustedRandomAccess};
1+
use crate::iter::traits::trusted_random_access::try_get_unchecked;
2+
use crate::iter::traits::TrustedRandomAccess;
23
use crate::iter::{FusedIterator, TrustedLen};
34
use crate::ops::Try;
45

library/core/src/iter/adapters/enumerate.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1-
use crate::iter::adapters::{zip::try_get_unchecked, SourceIter, TrustedRandomAccess};
1+
use crate::iter::adapters::SourceIter;
2+
use crate::iter::traits::trusted_random_access::try_get_unchecked;
3+
use crate::iter::traits::TrustedRandomAccess;
24
use crate::iter::{FusedIterator, InPlaceIterable, TrustedLen};
35
use crate::ops::Try;
46

library/core/src/iter/adapters/fuse.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use crate::intrinsics;
2-
use crate::iter::adapters::zip::try_get_unchecked;
2+
use crate::iter::traits::trusted_random_access::try_get_unchecked;
33
use crate::iter::{
44
DoubleEndedIterator, ExactSizeIterator, FusedIterator, TrustedLen, TrustedRandomAccess,
55
};

library/core/src/iter/adapters/map.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
use crate::fmt;
2-
use crate::iter::adapters::{zip::try_get_unchecked, SourceIter, TrustedRandomAccess};
2+
use crate::iter::adapters::SourceIter;
3+
use crate::iter::traits::trusted_random_access::try_get_unchecked;
4+
use crate::iter::traits::TrustedRandomAccess;
35
use crate::iter::{FusedIterator, InPlaceIterable, TrustedLen};
46
use crate::ops::Try;
57

library/core/src/iter/adapters/mod.rs

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -52,9 +52,6 @@ pub use self::intersperse::{Intersperse, IntersperseWith};
5252
#[stable(feature = "iter_map_while", since = "1.57.0")]
5353
pub use self::map_while::MapWhile;
5454

55-
#[unstable(feature = "trusted_random_access", issue = "none")]
56-
pub use self::zip::TrustedRandomAccess;
57-
5855
#[stable(feature = "iter_zip", since = "1.59.0")]
5956
pub use self::zip::zip;
6057

library/core/src/iter/adapters/zip.rs

Lines changed: 2 additions & 101 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
use crate::cmp;
22
use crate::fmt::{self, Debug};
3+
use crate::iter::traits::trusted_random_access::try_get_unchecked;
34
use crate::iter::{DoubleEndedIterator, ExactSizeIterator, FusedIterator, Iterator};
4-
use crate::iter::{InPlaceIterable, SourceIter, TrustedLen};
5+
use crate::iter::{InPlaceIterable, SourceIter, TrustedLen, TrustedRandomAccess};
56
use crate::ops::Try;
67

78
/// An iterator that iterates two other iterators simultaneously.
@@ -326,103 +327,3 @@ impl<A: Debug + TrustedRandomAccess, B: Debug + TrustedRandomAccess> ZipFmt<A, B
326327
f.debug_struct("Zip").finish()
327328
}
328329
}
329-
330-
/// An iterator whose items are random-accessible efficiently
331-
///
332-
/// # Safety
333-
///
334-
/// The iterator's `size_hint` must be exact and cheap to call.
335-
///
336-
/// `TrustedRandomAccess::size` may not be overridden.
337-
///
338-
/// All subtypes and all supertypes of `Self` must also implement `TrustedRandomAccess`.
339-
/// In particular, this means that types with non-invariant parameters usually can not have
340-
/// an impl for `TrustedRandomAccess` that depends on any trait bounds on such parameters, except
341-
/// for bounds that come from the respective struct/enum definition itself, or bounds involving
342-
/// traits that themselves come with a guarantee similar to this one.
343-
///
344-
/// If `Self: ExactSizeIterator` then `self.len()` must always produce results consistent
345-
/// with `self.size()`.
346-
///
347-
/// If `Self: Iterator`, then `<Self as Iterator>::__iterator_get_unchecked(&mut self, idx)`
348-
/// must be safe to call provided the following conditions are met.
349-
///
350-
/// 1. `0 <= idx` and `idx < self.size()`.
351-
/// 2. If `Self: !Clone`, then `self.__iterator_get_unchecked(idx)` is never called with the same
352-
/// index on `self` more than once.
353-
/// 3. After `self.__iterator_get_unchecked(idx)` has been called, then `self.next_back()` will
354-
/// only be called at most `self.size() - idx - 1` times. If `Self: Clone` and `self` is cloned,
355-
/// then this number is calculated for `self` and its clone individually,
356-
/// but `self.next_back()` calls that happened before the cloning count for both `self` and the clone.
357-
/// 4. After `self.__iterator_get_unchecked(idx)` has been called, then only the following methods
358-
/// will be called on `self` or on any new clones of `self`:
359-
/// * `std::clone::Clone::clone`
360-
/// * `std::iter::Iterator::size_hint`
361-
/// * `std::iter::DoubleEndedIterator::next_back`
362-
/// * `std::iter::ExactSizeIterator::len`
363-
/// * `std::iter::Iterator::__iterator_get_unchecked`
364-
/// * `std::iter::TrustedRandomAccess::size`
365-
///
366-
/// Further, given that these conditions are met, it must guarantee that:
367-
///
368-
/// * It does not change the value returned from `size_hint`
369-
/// * It must be safe to call the methods listed above on `self` after calling
370-
/// `self.__iterator_get_unchecked(idx)`, assuming that the required traits are implemented.
371-
/// * It must also be safe to drop `self` after calling `self.__iterator_get_unchecked(idx)`.
372-
//
373-
// FIXME: Clarify interaction with SourceIter/InPlaceIterable. Calling `SourceIter::as_inner`
374-
// after `__iterator_get_unchecked` is supposed to be allowed.
375-
#[doc(hidden)]
376-
#[unstable(feature = "trusted_random_access", issue = "none")]
377-
#[rustc_specialization_trait]
378-
pub unsafe trait TrustedRandomAccess: Sized {
379-
// Convenience method.
380-
fn size(&self) -> usize
381-
where
382-
Self: Iterator,
383-
{
384-
self.size_hint().0
385-
}
386-
387-
const NEEDS_CLEANUP: bool;
388-
389-
fn cleanup(&mut self, num: usize, forward: bool);
390-
}
391-
392-
/// Like `Iterator::__iterator_get_unchecked`, but doesn't require the compiler to
393-
/// know that `U: TrustedRandomAccess`.
394-
///
395-
/// ## Safety
396-
///
397-
/// Same requirements calling `get_unchecked` directly.
398-
#[doc(hidden)]
399-
#[inline]
400-
pub(in crate::iter::adapters) unsafe fn try_get_unchecked<I>(it: &mut I, idx: usize) -> I::Item
401-
where
402-
I: Iterator,
403-
{
404-
// SAFETY: the caller must uphold the contract for
405-
// `Iterator::__iterator_get_unchecked`.
406-
unsafe { it.try_get_unchecked(idx) }
407-
}
408-
409-
unsafe trait SpecTrustedRandomAccess: Iterator {
410-
/// If `Self: TrustedRandomAccess`, it must be safe to call
411-
/// `Iterator::__iterator_get_unchecked(self, index)`.
412-
unsafe fn try_get_unchecked(&mut self, index: usize) -> Self::Item;
413-
}
414-
415-
unsafe impl<I: Iterator> SpecTrustedRandomAccess for I {
416-
default unsafe fn try_get_unchecked(&mut self, _: usize) -> Self::Item {
417-
panic!("Should only be called on TrustedRandomAccess iterators");
418-
}
419-
}
420-
421-
unsafe impl<I: Iterator + TrustedRandomAccess> SpecTrustedRandomAccess for I {
422-
#[inline]
423-
unsafe fn try_get_unchecked(&mut self, index: usize) -> Self::Item {
424-
// SAFETY: the caller must uphold the contract for
425-
// `Iterator::__iterator_get_unchecked`.
426-
unsafe { self.__iterator_get_unchecked(index) }
427-
}
428-
}

library/core/src/iter/mod.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -383,6 +383,8 @@ pub use self::traits::FusedIterator;
383383
pub use self::traits::InPlaceIterable;
384384
#[unstable(feature = "trusted_len", issue = "37572")]
385385
pub use self::traits::TrustedLen;
386+
#[unstable(feature = "trusted_random_access", issue = "none")]
387+
pub use self::traits::TrustedRandomAccess;
386388
#[unstable(feature = "trusted_step", issue = "85731")]
387389
pub use self::traits::TrustedStep;
388390
#[stable(feature = "rust1", since = "1.0.0")]
@@ -404,8 +406,6 @@ pub use self::adapters::MapWhile;
404406
pub use self::adapters::SourceIter;
405407
#[stable(feature = "iterator_step_by", since = "1.28.0")]
406408
pub use self::adapters::StepBy;
407-
#[unstable(feature = "trusted_random_access", issue = "none")]
408-
pub use self::adapters::TrustedRandomAccess;
409409
#[stable(feature = "rust1", since = "1.0.0")]
410410
pub use self::adapters::{
411411
Chain, Cycle, Enumerate, Filter, FilterMap, FlatMap, Fuse, Inspect, Map, Peekable, Rev, Scan,

library/core/src/iter/traits/mod.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ mod double_ended;
44
mod exact_size;
55
mod iterator;
66
mod marker;
7+
pub(crate) mod trusted_random_access;
78

89
#[stable(feature = "rust1", since = "1.0.0")]
910
pub use self::{
@@ -19,3 +20,5 @@ pub use self::{
1920
pub use self::marker::InPlaceIterable;
2021
#[unstable(feature = "trusted_step", issue = "85731")]
2122
pub use self::marker::TrustedStep;
23+
#[unstable(feature = "trusted_random_access", issue = "none")]
24+
pub use self::trusted_random_access::TrustedRandomAccess;
Lines changed: 99 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,99 @@
1+
/// An iterator whose items are random-accessible efficiently
2+
///
3+
/// # Safety
4+
///
5+
/// The iterator's `size_hint` must be exact and cheap to call.
6+
///
7+
/// `TrustedRandomAccess::size` may not be overridden.
8+
///
9+
/// All subtypes and all supertypes of `Self` must also implement `TrustedRandomAccess`.
10+
/// In particular, this means that types with non-invariant parameters usually can not have
11+
/// an impl for `TrustedRandomAccess` that depends on any trait bounds on such parameters, except
12+
/// for bounds that come from the respective struct/enum definition itself, or bounds involving
13+
/// traits that themselves come with a guarantee similar to this one.
14+
///
15+
/// If `Self: ExactSizeIterator` then `self.len()` must always produce results consistent
16+
/// with `self.size()`.
17+
///
18+
/// If `Self: Iterator`, then `<Self as Iterator>::__iterator_get_unchecked(&mut self, idx)`
19+
/// must be safe to call provided the following conditions are met.
20+
///
21+
/// 1. `0 <= idx` and `idx < self.size()`.
22+
/// 2. If `Self: !Clone`, then `self.__iterator_get_unchecked(idx)` is never called with the same
23+
/// index on `self` more than once.
24+
/// 3. After `self.__iterator_get_unchecked(idx)` has been called, then `self.next_back()` will
25+
/// only be called at most `self.size() - idx - 1` times. If `Self: Clone` and `self` is cloned,
26+
/// then this number is calculated for `self` and its clone individually,
27+
/// but `self.next_back()` calls that happened before the cloning count for both `self` and the clone.
28+
/// 4. After `self.__iterator_get_unchecked(idx)` has been called, then only the following methods
29+
/// will be called on `self` or on any new clones of `self`:
30+
/// * `std::clone::Clone::clone`
31+
/// * `std::iter::Iterator::size_hint`
32+
/// * `std::iter::DoubleEndedIterator::next_back`
33+
/// * `std::iter::ExactSizeIterator::len`
34+
/// * `std::iter::Iterator::__iterator_get_unchecked`
35+
/// * `std::iter::TrustedRandomAccess::size`
36+
///
37+
/// Further, given that these conditions are met, it must guarantee that:
38+
///
39+
/// * It does not change the value returned from `size_hint`
40+
/// * It must be safe to call the methods listed above on `self` after calling
41+
/// `self.__iterator_get_unchecked(idx)`, assuming that the required traits are implemented.
42+
/// * It must also be safe to drop `self` after calling `self.__iterator_get_unchecked(idx)`.
43+
//
44+
// FIXME: Clarify interaction with SourceIter/InPlaceIterable. Calling `SourceIter::as_inner`
45+
// after `__iterator_get_unchecked` is supposed to be allowed.
46+
#[doc(hidden)]
47+
#[unstable(feature = "trusted_random_access", issue = "none")]
48+
#[rustc_specialization_trait]
49+
pub unsafe trait TrustedRandomAccess: Sized {
50+
// Convenience method.
51+
fn size(&self) -> usize
52+
where
53+
Self: Iterator,
54+
{
55+
self.size_hint().0
56+
}
57+
58+
const NEEDS_CLEANUP: bool;
59+
60+
fn cleanup(&mut self, num: usize, forward: bool);
61+
}
62+
63+
/// Like `Iterator::__iterator_get_unchecked`, but doesn't require the compiler to
64+
/// know that `U: TrustedRandomAccess`.
65+
///
66+
/// ## Safety
67+
///
68+
/// Same requirements calling `get_unchecked` directly.
69+
#[doc(hidden)]
70+
#[inline]
71+
pub(in crate::iter) unsafe fn try_get_unchecked<I>(it: &mut I, idx: usize) -> I::Item
72+
where
73+
I: Iterator,
74+
{
75+
// SAFETY: the caller must uphold the contract for
76+
// `Iterator::__iterator_get_unchecked`.
77+
unsafe { it.try_get_unchecked(idx) }
78+
}
79+
80+
unsafe trait SpecTrustedRandomAccess: Iterator {
81+
/// If `Self: TrustedRandomAccess`, it must be safe to call
82+
/// `Iterator::__iterator_get_unchecked(self, index)`.
83+
unsafe fn try_get_unchecked(&mut self, index: usize) -> Self::Item;
84+
}
85+
86+
unsafe impl<I: Iterator> SpecTrustedRandomAccess for I {
87+
default unsafe fn try_get_unchecked(&mut self, _: usize) -> Self::Item {
88+
panic!("Should only be called on TrustedRandomAccess iterators");
89+
}
90+
}
91+
92+
unsafe impl<I: Iterator + TrustedRandomAccess> SpecTrustedRandomAccess for I {
93+
#[inline]
94+
unsafe fn try_get_unchecked(&mut self, index: usize) -> Self::Item {
95+
// SAFETY: the caller must uphold the contract for
96+
// `Iterator::__iterator_get_unchecked`.
97+
unsafe { self.__iterator_get_unchecked(index) }
98+
}
99+
}

0 commit comments

Comments
 (0)