Skip to content

Commit

Permalink
rebased
Browse files Browse the repository at this point in the history
  • Loading branch information
fee1-dead committed Nov 20, 2022
1 parent 7d2c911 commit 8249c6c
Show file tree
Hide file tree
Showing 17 changed files with 125 additions and 63 deletions.
30 changes: 24 additions & 6 deletions library/core/src/array/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -916,7 +916,7 @@ where
///
/// To minimize indirection fields are still pub but callers should at least use
/// `push_unchecked` to signal that something unsafe is going on.
pub(crate) struct Guard<'a, T, const N: usize> {
pub(crate) struct Guard<'a, T: ~const Destruct, const N: usize> {
/// The array to be initialized.
pub array_mut: &'a mut [MaybeUninit<T>; N],
/// The number of items that have been initialized so far.
Expand All @@ -930,7 +930,7 @@ impl<T, const N: usize> Guard<'_, T, N> {
///
/// No more than N elements must be initialized.
#[inline]
pub unsafe fn push_unchecked(&mut self, item: T) {
pub const unsafe fn push_unchecked(&mut self, item: T) {
// SAFETY: If `initialized` was correct before and the caller does not
// invoke this method more than N times then writes will be in-bounds
// and slots will not be initialized more than once.
Expand All @@ -941,15 +941,33 @@ impl<T, const N: usize> Guard<'_, T, N> {
}
}

impl<T, const N: usize> Drop for Guard<'_, T, N> {
impl<T: ~const Destruct, const N: usize> const Drop for Guard<'_, T, N> {
fn drop(&mut self) {
debug_assert!(self.initialized <= N);

#[inline]
const fn drop_ct<T: ~const Destruct>(x: &mut [T]) {
let mut i = 0;
while i < x.len() {
// SAFETY: dropping the value, contains initialized objects
unsafe {
crate::ptr::read(&mut x[i]);
}
i += 1;
}
}
#[inline]
fn drop_rt<T>(x: &mut [T]) {
// SAFETY: slice contains initialized objects
unsafe { crate::ptr::drop_in_place(x) }
}

// SAFETY: this slice will contain only initialized objects.
unsafe {
crate::ptr::drop_in_place(MaybeUninit::slice_assume_init_mut(
&mut self.array_mut.get_unchecked_mut(..self.initialized),
));
let to_drop = MaybeUninit::slice_assume_init_mut(
self.array_mut.get_unchecked_mut(..self.initialized),
);
crate::intrinsics::const_eval_select((to_drop,), drop_ct, drop_rt);
}
}
}
Expand Down
3 changes: 2 additions & 1 deletion library/core/src/cmp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1223,7 +1223,7 @@ pub const fn min<T: ~const Ord + ~const Destruct>(v1: T, v2: T) -> T {
#[stable(feature = "cmp_min_max_by", since = "1.53.0")]
#[rustc_const_unstable(feature = "const_cmp", issue = "92391")]
pub const fn min_by<T, F: ~const FnOnce(&T, &T) -> Ordering>(v1: T, v2: T, compare: F) -> T
where
where
T: ~const Destruct,
{
match compare(&v1, &v2) {
Expand Down Expand Up @@ -1309,6 +1309,7 @@ pub const fn max<T: ~const Ord + ~const Destruct>(v1: T, v2: T) -> T {
pub const fn max_by<T, F: ~const FnOnce(&T, &T) -> Ordering>(v1: T, v2: T, compare: F) -> T
where
T: ~const Destruct,
{
match compare(&v1, &v2) {
Ordering::Less | Ordering::Equal => v2,
Ordering::Greater => v1,
Expand Down
1 change: 1 addition & 0 deletions library/core/src/const_closure.rs
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ pub(crate) struct ConstFnMutClosure<CapturedData, Function> {
/// The Function of the Closure, must be: Fn(CapturedData, ClosureArgs) -> ClosureReturn
pub func: Function,
}

impl<'a, CapturedData: ?Sized, Function> ConstFnMutClosure<&'a mut CapturedData, Function> {
/// Function for creating a new closure.
///
Expand Down
1 change: 1 addition & 0 deletions library/core/src/iter/adapters/map.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
use crate::const_closure::ConstFnMutClosure;
use crate::fmt;
use crate::iter::adapters::{
zip::try_get_unchecked, SourceIter, TrustedRandomAccess, TrustedRandomAccessNoCoerce,
Expand Down
1 change: 1 addition & 0 deletions library/core/src/iter/adapters/mod.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
use crate::const_closure::ConstFnMutClosure;
use crate::iter::{InPlaceIterable, Iterator};
use crate::marker::Destruct;
use crate::ops::{ChangeOutputType, ControlFlow, FromResidual, Residual, Try};
Expand Down
8 changes: 5 additions & 3 deletions library/core/src/iter/adapters/zip.rs
Original file line number Diff line number Diff line change
Expand Up @@ -171,8 +171,9 @@ macro_rules! zip_impl_general_defaults {
#[inline]
#[cfg_attr(not(bootstrap), rustc_allow_const_fn_unstable(const_try, const_for))]
default fn next(&mut self) -> Option<(A::Item, B::Item)> {
let x = self.a.next()?;
let y = self.b.next()?;
// FIXME(const_trait_impl): revert to `?` when we can
let Some(x) = self.a.next() else { return None };
let Some(y) = self.b.next() else { return None };
Some((x, y))
}

Expand Down Expand Up @@ -586,11 +587,12 @@ pub unsafe trait TrustedRandomAccess: ~const TrustedRandomAccessNoCoerce {}
#[doc(hidden)]
#[unstable(feature = "trusted_random_access", issue = "none")]
#[rustc_specialization_trait]
#[const_trait]
pub unsafe trait TrustedRandomAccessNoCoerce: Sized {
// Convenience method.
fn size(&self) -> usize
where
Self: Iterator,
Self: ~const Iterator,
{
self.size_hint().0
}
Expand Down
3 changes: 2 additions & 1 deletion library/core/src/iter/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -364,7 +364,8 @@ macro_rules! impl_fold_via_try_fold {
#[inline]
fn $fold<AAA, FFF>(mut self, init: AAA, mut fold: FFF) -> AAA
where
FFF: FnMut(AAA, Self::Item) -> AAA,
FFF: ~const FnMut(AAA, Self::Item) -> AAA + ~const crate::marker::Destruct,
Self: ~const crate::marker::Destruct,
{
use crate::const_closure::ConstFnMutClosure;
use crate::ops::NeverShortCircuit;
Expand Down
1 change: 1 addition & 0 deletions library/core/src/iter/range.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ unsafe_impl_trusted_step![char i8 i16 i32 i64 i128 isize u8 u16 u32 u64 u128 usi
/// The *successor* operation moves towards values that compare greater.
/// The *predecessor* operation moves towards values that compare lesser.
#[unstable(feature = "step_trait", reason = "recently redesigned", issue = "42168")]
#[const_trait]
pub trait Step: Clone + PartialOrd + Sized {
/// Returns the number of *successor* steps required to get from `start` to `end`.
///
Expand Down
2 changes: 2 additions & 0 deletions library/core/src/iter/traits/accum.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ use crate::num::Wrapping;
/// [`sum()`]: Iterator::sum
/// [`FromIterator`]: iter::FromIterator
#[stable(feature = "iter_arith_traits", since = "1.12.0")]
#[const_trait]
pub trait Sum<A = Self>: Sized {
/// Method which takes an iterator and generates `Self` from the elements by
/// "summing up" the items.
Expand All @@ -27,6 +28,7 @@ pub trait Sum<A = Self>: Sized {
/// [`product()`]: Iterator::product
/// [`FromIterator`]: iter::FromIterator
#[stable(feature = "iter_arith_traits", since = "1.12.0")]
#[const_trait]
pub trait Product<A = Self>: Sized {
/// Method which takes an iterator and generates `Self` from the elements by
/// multiplying the items.
Expand Down
3 changes: 2 additions & 1 deletion library/core/src/iter/traits/collect.rs
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,7 @@ use crate::marker::Destruct;
label = "value of type `{Self}` cannot be built from `std::iter::Iterator<Item={A}>`"
)]
#[rustc_diagnostic_item = "FromIterator"]
#[const_trait]
pub trait FromIterator<A>: Sized {
/// Creates a value from an iterator.
///
Expand Down Expand Up @@ -267,7 +268,7 @@ pub trait IntoIterator {

#[rustc_const_unstable(feature = "const_intoiterator_identity", issue = "90603")]
#[stable(feature = "rust1", since = "1.0.0")]
impl<I: Iterator> const IntoIterator for I {
impl<I: ~const Iterator> const IntoIterator for I {
type Item = I::Item;
type IntoIter = I;

Expand Down
44 changes: 30 additions & 14 deletions library/core/src/iter/traits/double_ended.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use crate::const_closure::ConstFnMutClosure;
use crate::marker::Destruct;
use crate::ops::{ControlFlow, Try};

/// An iterator able to yield elements from both ends.
Expand Down Expand Up @@ -37,6 +39,7 @@ use crate::ops::{ControlFlow, Try};
/// ```
#[stable(feature = "rust1", since = "1.0.0")]
#[cfg_attr(not(test), rustc_diagnostic_item = "DoubleEndedIterator")]
#[const_trait]
pub trait DoubleEndedIterator: Iterator {
/// Removes and returns an element from the end of the iterator.
///
Expand Down Expand Up @@ -131,9 +134,15 @@ pub trait DoubleEndedIterator: Iterator {
/// [`Err(k)`]: Err
#[inline]
#[unstable(feature = "iter_advance_by", reason = "recently added", issue = "77404")]
fn advance_back_by(&mut self, n: usize) -> Result<(), usize> {
for i in 0..n {
fn advance_back_by(&mut self, n: usize) -> Result<(), usize>
where
Self::Item: ~const Destruct,
{
// FIXME(const_trait_impl): revert back to for loop
let mut i = 0;
while i < n {
self.next_back().ok_or(i)?;
i += 1;
}
Ok(())
}
Expand Down Expand Up @@ -181,7 +190,10 @@ pub trait DoubleEndedIterator: Iterator {
/// ```
#[inline]
#[stable(feature = "iter_nth_back", since = "1.37.0")]
fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
fn nth_back(&mut self, n: usize) -> Option<Self::Item>
where
Self::Item: ~const Destruct,
{
self.advance_back_by(n).ok()?;
self.next_back()
}
Expand Down Expand Up @@ -221,8 +233,9 @@ pub trait DoubleEndedIterator: Iterator {
fn try_rfold<B, F, R>(&mut self, init: B, mut f: F) -> R
where
Self: Sized,
F: FnMut(B, Self::Item) -> R,
R: Try<Output = B>,
F: ~const FnMut(B, Self::Item) -> R + ~const Destruct,
R: ~const Try<Output = B>,
Self::Item: ~const Destruct,
{
let mut accum = init;
while let Some(x) = self.next_back() {
Expand Down Expand Up @@ -291,8 +304,9 @@ pub trait DoubleEndedIterator: Iterator {
#[stable(feature = "iter_rfold", since = "1.27.0")]
fn rfold<B, F>(mut self, init: B, mut f: F) -> B
where
Self: Sized,
F: FnMut(B, Self::Item) -> B,
Self: Sized + ~const Destruct,
F: ~const FnMut(B, Self::Item) -> B + ~const Destruct,
Self::Item: ~const Destruct,
{
let mut accum = init;
while let Some(x) = self.next_back() {
Expand Down Expand Up @@ -344,19 +358,21 @@ pub trait DoubleEndedIterator: Iterator {
/// ```
#[inline]
#[stable(feature = "iter_rfind", since = "1.27.0")]
fn rfind<P>(&mut self, predicate: P) -> Option<Self::Item>
fn rfind<P>(&mut self, mut predicate: P) -> Option<Self::Item>
where
Self: Sized,
P: FnMut(&Self::Item) -> bool,
P: ~const FnMut(&Self::Item) -> bool + ~const Destruct,
Self::Item: ~const Destruct,
{
#[inline]
fn check<T>(mut predicate: impl FnMut(&T) -> bool) -> impl FnMut((), T) -> ControlFlow<T> {
move |(), x| {
if predicate(&x) { ControlFlow::Break(x) } else { ControlFlow::CONTINUE }
}
const fn check<T: ~const Destruct, F: ~const FnMut(&T) -> bool>(
predicate: &mut F,
((), x): ((), T),
) -> ControlFlow<T> {
if predicate(&x) { ControlFlow::Break(x) } else { ControlFlow::CONTINUE }
}

self.try_rfold((), check(predicate)).break_value()
self.try_rfold((), ConstFnMutClosure::new(&mut predicate, check)).break_value()
}
}

Expand Down
Loading

0 comments on commit 8249c6c

Please sign in to comment.