diff options
| author | bjorn3 <bjorn3@users.noreply.github.com> | 2021-11-18 19:27:32 +0100 |
|---|---|---|
| committer | bjorn3 <bjorn3@users.noreply.github.com> | 2021-11-18 19:27:32 +0100 |
| commit | a8be7ea503211115d7e6339942544268de99bf17 (patch) | |
| tree | 1a199945be4e72d4587a988af6cf33129c7de33f | |
| parent | da83c84103e5f091ad1bee4823a6cc85bdf320a0 (diff) | |
| download | rust-a8be7ea503211115d7e6339942544268de99bf17.tar.gz rust-a8be7ea503211115d7e6339942544268de99bf17.zip | |
Implement new simd_shuffle signature
| -rw-r--r-- | src/intrinsics/simd.rs | 29 |
1 files changed, 28 insertions, 1 deletions
diff --git a/src/intrinsics/simd.rs b/src/intrinsics/simd.rs index 43e68b4afa9..73f5d367686 100644 --- a/src/intrinsics/simd.rs +++ b/src/intrinsics/simd.rs @@ -67,7 +67,34 @@ pub(super) fn codegen_simd_intrinsic_call<'tcx>( _ if intrinsic.as_str().starts_with("simd_shuffle"), (c x, c y, o idx) { validate_simd_type!(fx, intrinsic, span, x.layout().ty); - let n: u16 = intrinsic.as_str()["simd_shuffle".len()..].parse().unwrap(); + // If this intrinsic is the older "simd_shuffleN" form, simply parse the integer. + // If there is no suffix, use the index array length. + let n: u16 = if intrinsic == sym::simd_shuffle { + // Make sure this is actually an array, since typeck only checks the length-suffixed + // version of this intrinsic. + let idx_ty = fx.monomorphize(idx.ty(fx.mir, fx.tcx)); + match idx_ty.kind() { + ty::Array(ty, len) if matches!(ty.kind(), ty::Uint(ty::UintTy::U32)) => { + len.try_eval_usize(fx.tcx, ty::ParamEnv::reveal_all()).unwrap_or_else(|| { + span_bug!(span, "could not evaluate shuffle index array length") + }).try_into().unwrap() + } + _ => { + fx.tcx.sess.span_err( + span, + &format!( + "simd_shuffle index must be an array of `u32`, got `{}`", + idx_ty, + ), + ); + // Prevent verifier error + crate::trap::trap_unreachable(fx, "compilation should not have succeeded"); + return; + } + } + } else { + intrinsic.as_str()["simd_shuffle".len()..].parse().unwrap() + }; assert_eq!(x.layout(), y.layout()); let layout = x.layout(); |
