diff --git a/library/core/src/iter/adapters/skip.rs b/library/core/src/iter/adapters/skip.rs index ea1da8ba434ed..2c283100f071f 100644 --- a/library/core/src/iter/adapters/skip.rs +++ b/library/core/src/iter/adapters/skip.rs @@ -33,7 +33,7 @@ where #[inline] fn next(&mut self) -> Option { if unlikely(self.n > 0) { - self.iter.nth(crate::mem::take(&mut self.n) - 1); + self.iter.nth(crate::mem::take(&mut self.n) - 1)?; } self.iter.next() } diff --git a/library/core/tests/iter/adapters/skip.rs b/library/core/tests/iter/adapters/skip.rs index 0c464bdd03a22..65f235e86aab9 100644 --- a/library/core/tests/iter/adapters/skip.rs +++ b/library/core/tests/iter/adapters/skip.rs @@ -1,5 +1,7 @@ use core::iter::*; +use super::Unfuse; + #[test] fn test_iterator_skip() { let xs = [0, 1, 2, 3, 5, 13, 15, 16, 17, 19, 20, 30]; @@ -190,3 +192,12 @@ fn test_skip_nth_back() { it.by_ref().skip(2).nth_back(10); assert_eq!(it.next_back(), Some(&1)); } + +#[test] +fn test_skip_non_fused() { + let non_fused = Unfuse::new(0..10); + + // `Skip` would previously exhaust the iterator in this `next` call and then erroneously try to + // advance it further. `Unfuse` tests that this doesn't happen by panicking in that scenario. + let _ = non_fused.skip(20).next(); +}