Skip to content

Commit bc6af97

Browse files
committed
core: disable ptr::swap_nonoverlapping_one's block optimization on SPIR-V.
1 parent 3c3d3dd commit bc6af97

File tree

1 file changed

+17
-6
lines changed

1 file changed

+17
-6
lines changed

library/core/src/ptr/mod.rs

+17-6
Original file line numberDiff line numberDiff line change
@@ -473,12 +473,23 @@ pub const unsafe fn swap_nonoverlapping<T>(x: *mut T, y: *mut T, count: usize) {
473473
#[inline]
474474
#[rustc_const_unstable(feature = "const_swap", issue = "83163")]
475475
pub(crate) const unsafe fn swap_nonoverlapping_one<T>(x: *mut T, y: *mut T) {
476-
// Only apply the block optimization in `swap_nonoverlapping_bytes` for types
477-
// at least as large as the block size, to avoid pessimizing codegen.
478-
if mem::size_of::<T>() >= 32 {
479-
// SAFETY: the caller must uphold the safety contract for `swap_nonoverlapping`.
480-
unsafe { swap_nonoverlapping(x, y, 1) };
481-
return;
476+
// NOTE(eddyb) SPIR-V's Logical addressing model doesn't allow for arbitrary
477+
// reinterpretation of values as (chunkable) byte arrays, and the loop in the
478+
// block optimization in `swap_nonoverlapping_bytes` is hard to rewrite back
479+
// into the (unoptimized) direct swapping implementation, so we disable it.
480+
// FIXME(eddyb) the block optimization also prevents MIR optimizations from
481+
// understanding `mem::replace`, `Option::take`, etc. - a better overall
482+
// solution might be to make `swap_nonoverlapping` into an intrinsic, which
483+
// a backend can choose to implement using the block optimization, or not.
484+
#[cfg(not(target_arch = "spirv"))]
485+
{
486+
// Only apply the block optimization in `swap_nonoverlapping_bytes` for types
487+
// at least as large as the block size, to avoid pessimizing codegen.
488+
if mem::size_of::<T>() >= 32 {
489+
// SAFETY: the caller must uphold the safety contract for `swap_nonoverlapping`.
490+
unsafe { swap_nonoverlapping(x, y, 1) };
491+
return;
492+
}
482493
}
483494

484495
// Direct swapping, for the cases not going through the block optimization.

0 commit comments

Comments
 (0)