mirror of
https://github.com/rust-lang/rust.git
synced 2024-12-25 15:04:33 +00:00
Rollup merge of #44537 - oli-obk:memchr, r=alexcrichton
More `align_offset` things cc #44488
This commit is contained in:
commit
8dae2b0aef
@ -1381,38 +1381,7 @@ extern "rust-intrinsic" {
|
||||
}
|
||||
|
||||
#[cfg(stage0)]
|
||||
/// Computes the byte offset that needs to be applied to `ptr` in order to
|
||||
/// make it aligned to `align`.
|
||||
/// If it is not possible to align `ptr`, the implementation returns
|
||||
/// `usize::max_value()`.
|
||||
///
|
||||
/// There are no guarantees whatsover that offsetting the pointer will not
|
||||
/// overflow or go beyond the allocation that `ptr` points into.
|
||||
/// It is up to the caller to ensure that the returned offset is correct
|
||||
/// in all terms other than alignment.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// Accessing adjacent `u8` as `u16`
|
||||
///
|
||||
/// ```
|
||||
/// # #![feature(core_intrinsics)]
|
||||
/// # fn foo(n: usize) {
|
||||
/// # use std::intrinsics::align_offset;
|
||||
/// # use std::mem::align_of;
|
||||
/// # unsafe {
|
||||
/// let x = [5u8, 6u8, 7u8, 8u8, 9u8];
|
||||
/// let ptr = &x[n] as *const u8;
|
||||
/// let offset = align_offset(ptr as *const (), align_of::<u16>());
|
||||
/// if offset < x.len() - n - 1 {
|
||||
/// let u16_ptr = ptr.offset(offset as isize) as *const u16;
|
||||
/// assert_ne!(*u16_ptr, 500);
|
||||
/// } else {
|
||||
/// // while the pointer can be aligned via `offset`, it would point
|
||||
/// // outside the allocation
|
||||
/// }
|
||||
/// # } }
|
||||
/// ```
|
||||
/// remove me after the next release
|
||||
pub unsafe fn align_offset(ptr: *const (), align: usize) -> usize {
|
||||
let offset = ptr as usize % align;
|
||||
if offset == 0 {
|
||||
|
@ -1064,7 +1064,43 @@ impl<T: ?Sized> *const T {
|
||||
copy_nonoverlapping(self, dest, count)
|
||||
}
|
||||
|
||||
|
||||
/// Computes the byte offset that needs to be applied in order to
|
||||
/// make the pointer aligned to `align`.
|
||||
/// If it is not possible to align the pointer, the implementation returns
|
||||
/// `usize::max_value()`.
|
||||
///
|
||||
/// There are no guarantees whatsover that offsetting the pointer will not
|
||||
/// overflow or go beyond the allocation that the pointer points into.
|
||||
/// It is up to the caller to ensure that the returned offset is correct
|
||||
/// in all terms other than alignment.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// Accessing adjacent `u8` as `u16`
|
||||
///
|
||||
/// ```
|
||||
/// # #![feature(align_offset)]
|
||||
/// # fn foo(n: usize) {
|
||||
/// # use std::mem::align_of;
|
||||
/// # unsafe {
|
||||
/// let x = [5u8, 6u8, 7u8, 8u8, 9u8];
|
||||
/// let ptr = &x[n] as *const u8;
|
||||
/// let offset = ptr.align_offset(align_of::<u16>());
|
||||
/// if offset < x.len() - n - 1 {
|
||||
/// let u16_ptr = ptr.offset(offset as isize) as *const u16;
|
||||
/// assert_ne!(*u16_ptr, 500);
|
||||
/// } else {
|
||||
/// // while the pointer can be aligned via `offset`, it would point
|
||||
/// // outside the allocation
|
||||
/// }
|
||||
/// # } }
|
||||
/// ```
|
||||
#[unstable(feature = "align_offset", issue = "44488")]
|
||||
pub fn align_offset(self, align: usize) -> usize {
|
||||
unsafe {
|
||||
intrinsics::align_offset(self as *const _, align)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[lang = "mut_ptr"]
|
||||
@ -1284,6 +1320,43 @@ impl<T: ?Sized> *mut T {
|
||||
}
|
||||
}
|
||||
|
||||
/// Computes the byte offset that needs to be applied in order to
|
||||
/// make the pointer aligned to `align`.
|
||||
/// If it is not possible to align the pointer, the implementation returns
|
||||
/// `usize::max_value()`.
|
||||
///
|
||||
/// There are no guarantees whatsover that offsetting the pointer will not
|
||||
/// overflow or go beyond the allocation that the pointer points into.
|
||||
/// It is up to the caller to ensure that the returned offset is correct
|
||||
/// in all terms other than alignment.
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// Accessing adjacent `u8` as `u16`
|
||||
///
|
||||
/// ```
|
||||
/// # #![feature(align_offset)]
|
||||
/// # fn foo(n: usize) {
|
||||
/// # use std::mem::align_of;
|
||||
/// # unsafe {
|
||||
/// let x = [5u8, 6u8, 7u8, 8u8, 9u8];
|
||||
/// let ptr = &x[n] as *const u8;
|
||||
/// let offset = ptr.align_offset(align_of::<u16>());
|
||||
/// if offset < x.len() - n - 1 {
|
||||
/// let u16_ptr = ptr.offset(offset as isize) as *const u16;
|
||||
/// assert_ne!(*u16_ptr, 500);
|
||||
/// } else {
|
||||
/// // while the pointer can be aligned via `offset`, it would point
|
||||
/// // outside the allocation
|
||||
/// }
|
||||
/// # } }
|
||||
/// ```
|
||||
#[unstable(feature = "align_offset", issue = "44488")]
|
||||
pub fn align_offset(self, align: usize) -> usize {
|
||||
unsafe {
|
||||
intrinsics::align_offset(self as *const _, align)
|
||||
}
|
||||
}
|
||||
|
||||
/// Calculates the offset from a pointer (convenience for `.offset(count as isize)`).
|
||||
///
|
||||
|
@ -23,7 +23,6 @@ use fmt;
|
||||
use iter::{Map, Cloned, FusedIterator};
|
||||
use slice::{self, SliceIndex};
|
||||
use mem;
|
||||
use intrinsics::align_offset;
|
||||
|
||||
pub mod pattern;
|
||||
|
||||
@ -1515,7 +1514,7 @@ fn run_utf8_validation(v: &[u8]) -> Result<(), Utf8Error> {
|
||||
let ptr = v.as_ptr();
|
||||
let align = unsafe {
|
||||
// the offset is safe, because `index` is guaranteed inbounds
|
||||
align_offset(ptr.offset(index as isize) as *const (), usize_bytes)
|
||||
ptr.offset(index as isize).align_offset(usize_bytes)
|
||||
};
|
||||
if align == 0 {
|
||||
while index < blocks_end {
|
||||
|
@ -242,6 +242,7 @@
|
||||
#![feature(allocator_internals)]
|
||||
#![feature(allow_internal_unsafe)]
|
||||
#![feature(allow_internal_unstable)]
|
||||
#![feature(align_offset)]
|
||||
#![feature(asm)]
|
||||
#![feature(box_syntax)]
|
||||
#![feature(cfg_target_has_atomic)]
|
||||
|
@ -65,15 +65,12 @@ pub mod fallback {
|
||||
let usize_bytes = mem::size_of::<usize>();
|
||||
|
||||
// search up to an aligned boundary
|
||||
let align = (ptr as usize) & (usize_bytes- 1);
|
||||
let mut offset;
|
||||
if align > 0 {
|
||||
offset = cmp::min(usize_bytes - align, len);
|
||||
let mut offset = ptr.align_offset(usize_bytes);
|
||||
if offset > 0 {
|
||||
offset = cmp::min(offset, len);
|
||||
if let Some(index) = text[..offset].iter().position(|elt| *elt == x) {
|
||||
return Some(index);
|
||||
}
|
||||
} else {
|
||||
offset = 0;
|
||||
}
|
||||
|
||||
// search the body of the text
|
||||
|
Loading…
Reference in New Issue
Block a user