diff options
| author | bors <bors@rust-lang.org> | 2023-01-15 18:39:40 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2023-01-15 18:39:40 +0000 |
| commit | 9e75dddf609c0201d03f9792e850f95d6a283d11 (patch) | |
| tree | 30f268196652356e492213e82503c7af99414f6b | |
| parent | ae4d89dfb51535c1c43052ef848564bd2323c9ca (diff) | |
| parent | 9db013401879a39df86c33552c8c092cf95ea20c (diff) | |
| download | rust-9e75dddf609c0201d03f9792e850f95d6a283d11.tar.gz rust-9e75dddf609c0201d03f9792e850f95d6a283d11.zip | |
Auto merge of #106393 - the8472:use-ptr-sub, r=scottmcm
Simplify manual ptr arithmetic in slice::Iter with ptr_sub The old code was introduced in #61885, which predates the ptr_sub method and underlying intrinsic. The codegen test still passes. r? `@scottmcm`
| -rw-r--r-- | library/core/src/slice/iter.rs | 8 | ||||
| -rw-r--r-- | library/core/src/slice/iter/macros.rs | 22 | ||||
| -rw-r--r-- | tests/codegen/issue-45964-bounds-check-slice-pos.rs | 1 |
3 files changed, 8 insertions, 23 deletions
diff --git a/library/core/src/slice/iter.rs b/library/core/src/slice/iter.rs index c3e7f2eb302..90ab43d1289 100644 --- a/library/core/src/slice/iter.rs +++ b/library/core/src/slice/iter.rs @@ -6,7 +6,7 @@ mod macros; use crate::cmp; use crate::cmp::Ordering; use crate::fmt; -use crate::intrinsics::{assume, exact_div, unchecked_sub}; +use crate::intrinsics::assume; use crate::iter::{FusedIterator, TrustedLen, TrustedRandomAccess, TrustedRandomAccessNoCoerce}; use crate::marker::{PhantomData, Send, Sized, Sync}; use crate::mem::{self, SizedTypeProperties}; @@ -35,12 +35,6 @@ impl<'a, T> IntoIterator for &'a mut [T] { } } -// Macro helper functions -#[inline(always)] -fn size_from_ptr<T>(_: *const T) -> usize { - mem::size_of::<T>() -} - /// Immutable slice iterator /// /// This struct is created by the [`iter`] method on [slices]. diff --git a/library/core/src/slice/iter/macros.rs b/library/core/src/slice/iter/macros.rs index 55af4cb61dc..0fd57b197aa 100644 --- a/library/core/src/slice/iter/macros.rs +++ b/library/core/src/slice/iter/macros.rs @@ -9,30 +9,20 @@ macro_rules! is_empty { }; } -// To get rid of some bounds checks (see `position`), we compute the length in a somewhat -// unexpected way. (Tested by `codegen/slice-position-bounds-check`.) macro_rules! len { ($self: ident) => {{ #![allow(unused_unsafe)] // we're sometimes used within an unsafe block let start = $self.ptr; - let size = size_from_ptr(start.as_ptr()); - if size == 0 { - // This _cannot_ use `unchecked_sub` because we depend on wrapping + if T::IS_ZST { + // This _cannot_ use `ptr_sub` because we depend on wrapping // to represent the length of long ZST slice iterators. $self.end.addr().wrapping_sub(start.as_ptr().addr()) } else { - // We know that `start <= end`, so can do better than `offset_from`, - // which needs to deal in signed. By setting appropriate flags here - // we can tell LLVM this, which helps it remove bounds checks. - // SAFETY: By the type invariant, `start <= end` - let diff = unsafe { unchecked_sub($self.end.addr(), start.as_ptr().addr()) }; - // By also telling LLVM that the pointers are apart by an exact - // multiple of the type size, it can optimize `len() == 0` down to - // `start == end` instead of `(end - start) < size`. - // SAFETY: By the type invariant, the pointers are aligned so the - // distance between them must be a multiple of pointee size - unsafe { exact_div(diff, size) } + // To get rid of some bounds checks (see `position`), we use ptr_sub instead of + // offset_from (Tested by `codegen/slice-position-bounds-check`.) + // SAFETY: by the type invariant pointers are aligned and `start <= end` + unsafe { $self.end.sub_ptr(start.as_ptr()) } } }}; } diff --git a/tests/codegen/issue-45964-bounds-check-slice-pos.rs b/tests/codegen/issue-45964-bounds-check-slice-pos.rs index aa59c713b78..1daa213fc82 100644 --- a/tests/codegen/issue-45964-bounds-check-slice-pos.rs +++ b/tests/codegen/issue-45964-bounds-check-slice-pos.rs @@ -2,6 +2,7 @@ // prevent optimizing away bounds checks // compile-flags: -O +// ignore-debug: the debug assertions get in the way #![crate_type="rlib"] |
