1+ #[ cfg( not( bootstrap) ) ]
2+ use crate :: intrinsics;
13use crate :: iter:: {
24 FusedIterator , Step , TrustedLen , TrustedRandomAccess , TrustedRandomAccessNoCoerce , TrustedStep ,
35} ;
6+ use crate :: mem;
47use crate :: num:: NonZero ;
58use crate :: range:: { Range , RangeFrom , RangeInclusive , legacy} ;
69
@@ -293,12 +296,27 @@ range_incl_exact_iter_impl! {
293296/// By-value [`RangeFrom`] iterator.
294297#[ unstable( feature = "new_range_api" , issue = "125687" ) ]
295298#[ derive( Debug , Clone ) ]
296- pub struct IterRangeFrom < A > ( legacy:: RangeFrom < A > ) ;
299+ pub struct IterRangeFrom < A > {
300+ start : A ,
301+ #[ allow( dead_code) ]
302+ /// Whether the first element of the iterator has yielded.
303+ /// Only used when overflow checks are enabled.
304+ first : bool ,
305+ }
297306
298- impl < A > IterRangeFrom < A > {
307+ impl < A : Step > IterRangeFrom < A > {
299308 /// Returns the remainder of the range being iterated over.
309+ #[ inline]
310+ #[ rustc_inherit_overflow_checks]
300311 pub fn remainder ( self ) -> RangeFrom < A > {
301- RangeFrom { start : self . 0 . start }
312+ #[ cfg( not( bootstrap) ) ]
313+ if intrinsics:: overflow_checks ( ) {
314+ if !self . first {
315+ return RangeFrom { start : Step :: forward ( self . start , 1 ) } ;
316+ }
317+ }
318+
319+ RangeFrom { start : self . start }
302320 }
303321}
304322
@@ -307,18 +325,49 @@ impl<A: Step> Iterator for IterRangeFrom<A> {
307325 type Item = A ;
308326
309327 #[ inline]
328+ #[ rustc_inherit_overflow_checks]
310329 fn next ( & mut self ) -> Option < A > {
311- self . 0 . next ( )
330+ #[ cfg( not( bootstrap) ) ]
331+ if intrinsics:: overflow_checks ( ) {
332+ if self . first {
333+ self . first = false ;
334+ return Some ( self . start . clone ( ) ) ;
335+ }
336+
337+ self . start = Step :: forward ( self . start . clone ( ) , 1 ) ;
338+ return Some ( self . start . clone ( ) ) ;
339+ }
340+
341+ let n = Step :: forward ( self . start . clone ( ) , 1 ) ;
342+ Some ( mem:: replace ( & mut self . start , n) )
312343 }
313344
314345 #[ inline]
315346 fn size_hint ( & self ) -> ( usize , Option < usize > ) {
316- self . 0 . size_hint ( )
347+ ( usize :: MAX , None )
317348 }
318349
319350 #[ inline]
351+ #[ rustc_inherit_overflow_checks]
320352 fn nth ( & mut self , n : usize ) -> Option < A > {
321- self . 0 . nth ( n)
353+ #[ cfg( not( bootstrap) ) ]
354+ if intrinsics:: overflow_checks ( ) {
355+ if self . first {
356+ self . first = false ;
357+
358+ let plus_n = Step :: forward ( self . start . clone ( ) , n) ;
359+ self . start = plus_n. clone ( ) ;
360+ return Some ( plus_n) ;
361+ }
362+
363+ let plus_n = Step :: forward ( self . start . clone ( ) , n) ;
364+ self . start = Step :: forward ( plus_n. clone ( ) , 1 ) ;
365+ return Some ( self . start . clone ( ) ) ;
366+ }
367+
368+ let plus_n = Step :: forward ( self . start . clone ( ) , n) ;
369+ self . start = Step :: forward ( plus_n. clone ( ) , 1 ) ;
370+ Some ( plus_n)
322371 }
323372}
324373
@@ -334,6 +383,6 @@ impl<A: Step> IntoIterator for RangeFrom<A> {
334383 type IntoIter = IterRangeFrom < A > ;
335384
336385 fn into_iter ( self ) -> Self :: IntoIter {
337- IterRangeFrom ( self . into ( ) )
386+ IterRangeFrom { start : self . start , first : true }
338387 }
339388}
0 commit comments