Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rollup of 16 pull requests #73939

Closed
wants to merge 47 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
47 commits
Select commit Hold shift + click to select a range
144206e
Don't implement Fn* traits for #[target_feature] functions
calebzulawski Jun 13, 2020
c98b4c8
Add error note when trying fn as Fn trait
calebzulawski Jun 13, 2020
0d0865f
Make `rustc_peek` a safe intrinsic
oli-obk Jun 27, 2020
765bd47
Recover extra trailing angle brackets in struct definition
Aaron1011 Jun 27, 2020
8e899b1
Don't implement Fn* for unsafe #[target_feature] functions
calebzulawski Jun 27, 2020
7055c23
ast_pretty: Pass some token streams and trees by reference
petrochenkov Jun 24, 2020
14d0370
Remove defunct `-Z print-region-graph`
tmiasko Jun 28, 2020
e8f5785
Split and expand nonstandard-style lints unicode unit test.
crlf0710 Jun 28, 2020
824b2bb
Match on `Symbol` instead of `&str` for type-checking intrinsics.
oli-obk Jun 28, 2020
49c1018
Fix markdown rendering in librustc_lexer docs
pierwill Jun 28, 2020
4966272
Add newline to rustc MultiSpan docs
pierwill Jun 28, 2020
844dc31
ci: fix wasm32 broken due to a NodeJS version bump
pietroalbini Jun 30, 2020
f74a7d3
Clean up E0712 explanation
GuillaumeGomez Jun 30, 2020
8ee1dec
Deny unsafe ops in unsafe fns, part 1
LeSeulArtichaut Jun 21, 2020
8a515e9
Deny unsafe ops in unsafe fns, part 2
LeSeulArtichaut Jun 22, 2020
ac7539c
Deny unsafe ops in unsafe fns, part 3
LeSeulArtichaut Jun 24, 2020
c68f478
Deny unsafe ops in unsafe fns, part 4
LeSeulArtichaut Jun 25, 2020
c225e5c
Provide more information on duplicate lang item error.
ehuss Jun 17, 2020
b365233
Deny unsafe ops in unsafe fns, part 5
LeSeulArtichaut Jun 30, 2020
1b3ef66
Switch crate_extern_paths to a query, and tweak wording.
ehuss Jun 27, 2020
a1623ff
Deny unsafe ops in unsafe fns, part 6
LeSeulArtichaut Jun 30, 2020
0889d79
remove duplicate tests
lcnr Jun 30, 2020
6a7a652
Bless failing tests
LeSeulArtichaut Jun 30, 2020
e3cbb62
Rename TypeckTables to TypeckResults.
Lezzz Jun 4, 2020
51858da
Make #[target_feature] Fn trait error message less confusing
calebzulawski Jun 30, 2020
a5764de
expand: Stop using nonterminals for passing tokens to attribute and d…
petrochenkov Jun 14, 2020
b37434e
Remove `token::FlattenGroup`
petrochenkov Jul 1, 2020
5da0576
Insert NoDelim groups around nonterminals when lowering macro_rules
Aaron1011 Jun 21, 2020
c844028
Don't print additional spaces when pretty-printing NoDelim groups
Aaron1011 Jun 21, 2020
1ded7a5
Handle `None`-delimited groups when parsing `macro_rules!` macro
Aaron1011 Jun 29, 2020
eb4ba55
Add an issue number for the pretty_printing_compatibility_hack FIXME
petrochenkov Jul 1, 2020
6b34642
Rollup merge of #72983 - Lezzz:rename-typeck, r=nikomatsakis
Manishearth Jul 1, 2020
88e068b
Rollup merge of #73306 - calebzulawski:target-feature-11-fn-trait-sou…
Manishearth Jul 1, 2020
2071773
Rollup merge of #73345 - petrochenkov:nointerp, r=Aaron1011
Manishearth Jul 1, 2020
3cbcdc4
Rollup merge of #73449 - ehuss:duplicate-lang-item, r=matthewjasper
Manishearth Jul 1, 2020
6e57524
Rollup merge of #73569 - Aaron1011:fix/macro-rules-group, r=petrochenkov
Manishearth Jul 1, 2020
be11c3d
Rollup merge of #73622 - LeSeulArtichaut:unsafe-libcore, r=nikomatsakis
Manishearth Jul 1, 2020
f436a3a
Rollup merge of #73803 - Aaron1011:feature/angle-field-recovery, r=ma…
Manishearth Jul 1, 2020
127b3ba
Rollup merge of #73812 - petrochenkov:prettyref, r=varkor
Manishearth Jul 1, 2020
1b5696f
Rollup merge of #73834 - oli-obk:safe_intrinsics, r=ecstatic-morse
Manishearth Jul 1, 2020
d812bd9
Rollup merge of #73839 - crlf0710:snapshot_the_reality, r=Manishearth
Manishearth Jul 1, 2020
f01c218
Rollup merge of #73841 - tmiasko:print-region-graph, r=Mark-Simulacrum
Manishearth Jul 1, 2020
ee455a6
Rollup merge of #73848 - pierwill:pierwill-lexer-block-doc, r=jonas-s…
Manishearth Jul 1, 2020
f422af7
Rollup merge of #73853 - pierwill:pierwill-multispan-doc, r=jonas-sch…
Manishearth Jul 1, 2020
e663791
Rollup merge of #73885 - pietroalbini:ci-fix-wasm32, r=kennytm
Manishearth Jul 1, 2020
fe1f05c
Rollup merge of #73892 - GuillaumeGomez:cleanup-e0712, r=Dylan-DPC
Manishearth Jul 1, 2020
555397d
Rollup merge of #73898 - lcnr:issue61383, r=jonas-schievink
Manishearth Jul 1, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
13 changes: 12 additions & 1 deletion src/ci/docker/wasm32/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,18 @@ RUN ln `which python3` /usr/bin/python

ENV PATH=$PATH:/emsdk-portable
ENV PATH=$PATH:/emsdk-portable/upstream/emscripten/
ENV PATH=$PATH:/emsdk-portable/node/12.9.1_64bit/bin/

# Rust's build system requires NodeJS to be in the path, but the directory in
# which emsdk stores it contains the version number. This caused breakages in
# the past when emsdk bumped the node version causing the path to point to a
# missing directory.
#
# To avoid the problem this symlinks the latest NodeJs version available to
# "latest", and adds that to the path.
RUN ln -s /emsdk-portable/node/$(ls /emsdk-portable/node | sort -V | tail -n 1) \
/emsdk-portable/node/latest
ENV PATH=$PATH:/emsdk-portable/node/latest/bin/

ENV BINARYEN_ROOT=/emsdk-portable/upstream/
ENV EMSDK=/emsdk-portable
ENV EM_CONFIG=/emsdk-portable/.emscripten
Expand Down
22 changes: 16 additions & 6 deletions src/libcore/alloc/global.rs
Original file line number Diff line number Diff line change
Expand Up @@ -127,9 +127,12 @@ pub unsafe trait GlobalAlloc {
#[stable(feature = "global_alloc", since = "1.28.0")]
unsafe fn alloc_zeroed(&self, layout: Layout) -> *mut u8 {
let size = layout.size();
let ptr = self.alloc(layout);
// SAFETY: the safety contract for `alloc` must be upheld by the caller.
let ptr = unsafe { self.alloc(layout) };
if !ptr.is_null() {
ptr::write_bytes(ptr, 0, size);
// SAFETY: as allocation succeeded, the region from `ptr`
// of size `size` is guaranteed to be valid for writes.
unsafe { ptr::write_bytes(ptr, 0, size) };
}
ptr
}
Expand Down Expand Up @@ -187,11 +190,18 @@ pub unsafe trait GlobalAlloc {
/// [`handle_alloc_error`]: ../../alloc/alloc/fn.handle_alloc_error.html
#[stable(feature = "global_alloc", since = "1.28.0")]
unsafe fn realloc(&self, ptr: *mut u8, layout: Layout, new_size: usize) -> *mut u8 {
let new_layout = Layout::from_size_align_unchecked(new_size, layout.align());
let new_ptr = self.alloc(new_layout);
// SAFETY: the caller must ensure that the `new_size` does not overflow.
// `layout.align()` comes from a `Layout` and is thus guaranteed to be valid.
let new_layout = unsafe { Layout::from_size_align_unchecked(new_size, layout.align()) };
// SAFETY: the caller must ensure that `new_layout` is greater than zero.
let new_ptr = unsafe { self.alloc(new_layout) };
if !new_ptr.is_null() {
ptr::copy_nonoverlapping(ptr, new_ptr, cmp::min(layout.size(), new_size));
self.dealloc(ptr, layout);
// SAFETY: the previously allocated block cannot overlap the newly allocated block.
// The safety contract for `dealloc` must be upheld by the caller.
unsafe {
ptr::copy_nonoverlapping(ptr, new_ptr, cmp::min(layout.size(), new_size));
self.dealloc(ptr, layout);
}
}
new_ptr
}
Expand Down
3 changes: 2 additions & 1 deletion src/libcore/alloc/layout.rs
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,8 @@ impl Layout {
#[rustc_const_stable(feature = "alloc_layout", since = "1.28.0")]
#[inline]
pub const unsafe fn from_size_align_unchecked(size: usize, align: usize) -> Self {
Layout { size_: size, align_: NonZeroUsize::new_unchecked(align) }
// SAFETY: the caller must ensure that `align` is greater than zero.
Layout { size_: size, align_: unsafe { NonZeroUsize::new_unchecked(align) } }
}

/// The minimum size in bytes for a memory block of this layout.
Expand Down
58 changes: 45 additions & 13 deletions src/libcore/alloc/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,9 @@ impl AllocInit {
#[inline]
#[unstable(feature = "allocator_api", issue = "32838")]
pub unsafe fn init(self, memory: MemoryBlock) {
self.init_offset(memory, 0)
// SAFETY: the safety contract for `init_offset` must be
// upheld by the caller.
unsafe { self.init_offset(memory, 0) }
}

/// Initialize the memory block like specified by `init` at the specified `offset`.
Expand All @@ -78,7 +80,10 @@ impl AllocInit {
match self {
AllocInit::Uninitialized => (),
AllocInit::Zeroed => {
memory.ptr.as_ptr().add(offset).write_bytes(0, memory.size - offset)
// SAFETY: the caller must guarantee that `offset` is smaller than or equal to `memory.size`,
// so the memory from `memory.ptr + offset` of length `memory.size - offset`
// is guaranteed to be contaned in `memory` and thus valid for writes.
unsafe { memory.ptr.as_ptr().add(offset).write_bytes(0, memory.size - offset) }
}
}
}
Expand Down Expand Up @@ -281,11 +286,23 @@ pub unsafe trait AllocRef {
return Ok(MemoryBlock { ptr, size });
}

let new_layout = Layout::from_size_align_unchecked(new_size, layout.align());
let new_layout =
// SAFETY: the caller must ensure that the `new_size` does not overflow.
// `layout.align()` comes from a `Layout` and is thus guaranteed to be valid for a Layout.
// The caller must ensure that `new_size` is greater than zero.
unsafe { Layout::from_size_align_unchecked(new_size, layout.align()) };
let new_memory = self.alloc(new_layout, init)?;
ptr::copy_nonoverlapping(ptr.as_ptr(), new_memory.ptr.as_ptr(), size);
self.dealloc(ptr, layout);
Ok(new_memory)

// SAFETY: because `new_size` must be greater than or equal to `size`, both the old and new
// memory allocation are valid for reads and writes for `size` bytes. Also, because the old
// allocation wasn't yet deallocated, it cannot overlap `new_memory`. Thus, the call to
// `copy_nonoverlapping` is safe.
// The safety contract for `dealloc` must be upheld by the caller.
unsafe {
ptr::copy_nonoverlapping(ptr.as_ptr(), new_memory.ptr.as_ptr(), size);
self.dealloc(ptr, layout);
Ok(new_memory)
}
}
}
}
Expand Down Expand Up @@ -356,11 +373,23 @@ pub unsafe trait AllocRef {
return Ok(MemoryBlock { ptr, size });
}

let new_layout = Layout::from_size_align_unchecked(new_size, layout.align());
let new_layout =
// SAFETY: the caller must ensure that the `new_size` does not overflow.
// `layout.align()` comes from a `Layout` and is thus guaranteed to be valid for a Layout.
// The caller must ensure that `new_size` is greater than zero.
unsafe { Layout::from_size_align_unchecked(new_size, layout.align()) };
let new_memory = self.alloc(new_layout, AllocInit::Uninitialized)?;
ptr::copy_nonoverlapping(ptr.as_ptr(), new_memory.ptr.as_ptr(), new_size);
self.dealloc(ptr, layout);
Ok(new_memory)

// SAFETY: because `new_size` must be lower than or equal to `size`, both the old and new
// memory allocation are valid for reads and writes for `new_size` bytes. Also, because the
// old allocation wasn't yet deallocated, it cannot overlap `new_memory`. Thus, the call to
// `copy_nonoverlapping` is safe.
// The safety contract for `dealloc` must be upheld by the caller.
unsafe {
ptr::copy_nonoverlapping(ptr.as_ptr(), new_memory.ptr.as_ptr(), new_size);
self.dealloc(ptr, layout);
Ok(new_memory)
}
}
}
}
Expand All @@ -386,7 +415,8 @@ where

#[inline]
unsafe fn dealloc(&mut self, ptr: NonNull<u8>, layout: Layout) {
(**self).dealloc(ptr, layout)
// SAFETY: the safety contract must be upheld by the caller
unsafe { (**self).dealloc(ptr, layout) }
}

#[inline]
Expand All @@ -398,7 +428,8 @@ where
placement: ReallocPlacement,
init: AllocInit,
) -> Result<MemoryBlock, AllocErr> {
(**self).grow(ptr, layout, new_size, placement, init)
// SAFETY: the safety contract must be upheld by the caller
unsafe { (**self).grow(ptr, layout, new_size, placement, init) }
}

#[inline]
Expand All @@ -409,6 +440,7 @@ where
new_size: usize,
placement: ReallocPlacement,
) -> Result<MemoryBlock, AllocErr> {
(**self).shrink(ptr, layout, new_size, placement)
// SAFETY: the safety contract must be upheld by the caller
unsafe { (**self).shrink(ptr, layout, new_size, placement) }
}
}
7 changes: 6 additions & 1 deletion src/libcore/cell.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1005,7 +1005,12 @@ impl<T: ?Sized> RefCell<T> {
#[inline]
pub unsafe fn try_borrow_unguarded(&self) -> Result<&T, BorrowError> {
if !is_writing(self.borrow.get()) {
Ok(&*self.value.get())
// SAFETY: We check that nobody is actively writing now, but it is
// the caller's responsibility to ensure that nobody writes until
// the returned reference is no longer in use.
// Also, `self.value.get()` refers to the value owned by `self`
// and is thus guaranteed to be valid for the lifetime of `self`.
Ok(unsafe { &*self.value.get() })
} else {
Err(BorrowError { _private: () })
}
Expand Down
3 changes: 2 additions & 1 deletion src/libcore/char/convert.rs
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,8 @@ pub fn from_u32(i: u32) -> Option<char> {
#[inline]
#[stable(feature = "char_from_unchecked", since = "1.5.0")]
pub unsafe fn from_u32_unchecked(i: u32) -> char {
if cfg!(debug_assertions) { char::from_u32(i).unwrap() } else { transmute(i) }
// SAFETY: the caller must guarantee that `i` is a valid char value.
if cfg!(debug_assertions) { char::from_u32(i).unwrap() } else { unsafe { transmute(i) } }
}

#[stable(feature = "char_convert", since = "1.13.0")]
Expand Down
3 changes: 2 additions & 1 deletion src/libcore/char/methods.rs
Original file line number Diff line number Diff line change
Expand Up @@ -183,7 +183,8 @@ impl char {
#[unstable(feature = "assoc_char_funcs", reason = "recently added", issue = "71763")]
#[inline]
pub unsafe fn from_u32_unchecked(i: u32) -> char {
super::convert::from_u32_unchecked(i)
// SAFETY: the safety contract must be upheld by the caller.
unsafe { super::convert::from_u32_unchecked(i) }
}

/// Converts a digit in the given radix to a `char`.
Expand Down
3 changes: 2 additions & 1 deletion src/libcore/convert/num.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,8 @@ macro_rules! impl_float_to_int {
#[doc(hidden)]
#[inline]
unsafe fn to_int_unchecked(self) -> $Int {
crate::intrinsics::float_to_int_unchecked(self)
// SAFETY: the safety contract must be upheld by the caller.
unsafe { crate::intrinsics::float_to_int_unchecked(self) }
}
}
)+
Expand Down
8 changes: 6 additions & 2 deletions src/libcore/ffi.rs
Original file line number Diff line number Diff line change
Expand Up @@ -333,7 +333,8 @@ impl<'f> VaListImpl<'f> {
/// Advance to the next arg.
#[inline]
pub unsafe fn arg<T: sealed_trait::VaArgSafe>(&mut self) -> T {
va_arg(self)
// SAFETY: the caller must uphold the safety contract for `va_arg`.
unsafe { va_arg(self) }
}

/// Copies the `va_list` at the current location.
Expand All @@ -343,7 +344,10 @@ impl<'f> VaListImpl<'f> {
{
let mut ap = self.clone();
let ret = f(ap.as_va_list());
va_end(&mut ap);
// SAFETY: the caller must uphold the safety contract for `va_end`.
unsafe {
va_end(&mut ap);
}
ret
}
}
Expand Down
4 changes: 3 additions & 1 deletion src/libcore/future/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -85,5 +85,7 @@ where
#[unstable(feature = "gen_future", issue = "50547")]
#[inline]
pub unsafe fn get_context<'a, 'b>(cx: ResumeTy) -> &'a mut Context<'b> {
&mut *cx.0.as_ptr().cast()
// SAFETY: the caller must guarantee that `cx.0` is a valid pointer
// that fulfills all the requirements for a mutable reference.
unsafe { &mut *cx.0.as_ptr().cast() }
}
10 changes: 7 additions & 3 deletions src/libcore/hash/sip.rs
Original file line number Diff line number Diff line change
Expand Up @@ -130,15 +130,19 @@ unsafe fn u8to64_le(buf: &[u8], start: usize, len: usize) -> u64 {
let mut i = 0; // current byte index (from LSB) in the output u64
let mut out = 0;
if i + 3 < len {
out = load_int_le!(buf, start + i, u32) as u64;
// SAFETY: `i` cannot be greater than `len`, and the caller must guarantee
// that the index start..start+len is in bounds.
out = unsafe { load_int_le!(buf, start + i, u32) } as u64;
i += 4;
}
if i + 1 < len {
out |= (load_int_le!(buf, start + i, u16) as u64) << (i * 8);
// SAFETY: same as above.
out |= (unsafe { load_int_le!(buf, start + i, u16) } as u64) << (i * 8);
i += 2
}
if i < len {
out |= (*buf.get_unchecked(start + i) as u64) << (i * 8);
// SAFETY: same as above.
out |= (unsafe { *buf.get_unchecked(start + i) } as u64) << (i * 8);
i += 1;
}
debug_assert_eq!(i, len);
Expand Down
4 changes: 3 additions & 1 deletion src/libcore/hint.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,9 @@ use crate::intrinsics;
#[inline]
#[stable(feature = "unreachable", since = "1.27.0")]
pub unsafe fn unreachable_unchecked() -> ! {
intrinsics::unreachable()
// SAFETY: the safety contract for `intrinsics::unreachable` must
// be upheld by the caller.
unsafe { intrinsics::unreachable() }
}

/// Emits a machine instruction hinting to the processor that it is running in busy-wait
Expand Down
13 changes: 10 additions & 3 deletions src/libcore/intrinsics.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2099,7 +2099,10 @@ pub unsafe fn copy_nonoverlapping<T>(src: *const T, dst: *mut T, count: usize) {
// Not panicking to keep codegen impact smaller.
abort();
}
copy_nonoverlapping(src, dst, count)

// SAFETY: the safety contract for `copy_nonoverlapping` must be
// upheld by the caller.
unsafe { copy_nonoverlapping(src, dst, count) }
}

/// Copies `count * size_of::<T>()` bytes from `src` to `dst`. The source
Expand Down Expand Up @@ -2165,7 +2168,9 @@ pub unsafe fn copy<T>(src: *const T, dst: *mut T, count: usize) {
// Not panicking to keep codegen impact smaller.
abort();
}
copy(src, dst, count)

// SAFETY: the safety contract for `copy` must be upheld by the caller.
unsafe { copy(src, dst, count) }
}

/// Sets `count * size_of::<T>()` bytes of memory starting at `dst` to
Expand Down Expand Up @@ -2248,5 +2253,7 @@ pub unsafe fn write_bytes<T>(dst: *mut T, val: u8, count: usize) {
}

debug_assert!(is_aligned_and_not_null(dst), "attempt to write to unaligned or null pointer");
write_bytes(dst, val, count)

// SAFETY: the safety contract for `write_bytes` must be upheld by the caller.
unsafe { write_bytes(dst, val, count) }
}
5 changes: 3 additions & 2 deletions src/libcore/iter/adapters/fuse.rs
Original file line number Diff line number Diff line change
Expand Up @@ -178,9 +178,10 @@ where
{
unsafe fn get_unchecked(&mut self, i: usize) -> I::Item {
match self.iter {
Some(ref mut iter) => iter.get_unchecked(i),
// SAFETY: the caller must uphold the contract for `TrustedRandomAccess::get_unchecked`.
Some(ref mut iter) => unsafe { iter.get_unchecked(i) },
// SAFETY: the caller asserts there is an item at `i`, so we're not exhausted.
None => intrinsics::unreachable(),
None => unsafe { intrinsics::unreachable() },
}
}

Expand Down
15 changes: 10 additions & 5 deletions src/libcore/iter/adapters/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -272,7 +272,8 @@ where
T: Copy,
{
unsafe fn get_unchecked(&mut self, i: usize) -> Self::Item {
*self.it.get_unchecked(i)
// SAFETY: the caller must uphold the contract for `TrustedRandomAccess::get_unchecked`.
unsafe { *self.it.get_unchecked(i) }
}

#[inline]
Expand Down Expand Up @@ -402,7 +403,8 @@ where
T: Clone,
{
default unsafe fn get_unchecked(&mut self, i: usize) -> Self::Item {
self.it.get_unchecked(i).clone()
// SAFETY: the caller must uphold the contract for `TrustedRandomAccess::get_unchecked`.
unsafe { self.it.get_unchecked(i) }.clone()
}

#[inline]
Expand All @@ -418,7 +420,8 @@ where
T: Copy,
{
unsafe fn get_unchecked(&mut self, i: usize) -> Self::Item {
*self.it.get_unchecked(i)
// SAFETY: the caller must uphold the contract for `TrustedRandomAccess::get_unchecked`.
unsafe { *self.it.get_unchecked(i) }
}

#[inline]
Expand Down Expand Up @@ -930,7 +933,8 @@ where
F: FnMut(I::Item) -> B,
{
unsafe fn get_unchecked(&mut self, i: usize) -> Self::Item {
(self.f)(self.iter.get_unchecked(i))
// SAFETY: the caller must uphold the contract for `TrustedRandomAccess::get_unchecked`.
(self.f)(unsafe { self.iter.get_unchecked(i) })
}
#[inline]
fn may_have_side_effect() -> bool {
Expand Down Expand Up @@ -1392,7 +1396,8 @@ where
I: TrustedRandomAccess,
{
unsafe fn get_unchecked(&mut self, i: usize) -> (usize, I::Item) {
(self.count + i, self.iter.get_unchecked(i))
// SAFETY: the caller must uphold the contract for `TrustedRandomAccess::get_unchecked`.
(self.count + i, unsafe { self.iter.get_unchecked(i) })
}

fn may_have_side_effect() -> bool {
Expand Down
3 changes: 2 additions & 1 deletion src/libcore/iter/adapters/zip.rs
Original file line number Diff line number Diff line change
Expand Up @@ -271,7 +271,8 @@ where
B: TrustedRandomAccess,
{
unsafe fn get_unchecked(&mut self, i: usize) -> (A::Item, B::Item) {
(self.a.get_unchecked(i), self.b.get_unchecked(i))
// SAFETY: the caller must uphold the contract for `TrustedRandomAccess::get_unchecked`.
unsafe { (self.a.get_unchecked(i), self.b.get_unchecked(i)) }
}

fn may_have_side_effect() -> bool {
Expand Down
Loading