about summary refs log tree commit diff
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2019-12-28 06:02:45 +0000
committerbors <bors@rust-lang.org>2019-12-28 06:02:45 +0000
commit8b4d22cb25bd49ac29eaa2960b559b7eee06d197 (patch)
tree42860753218df60cbb0e0a50ed497d352f02cc2a
parent3a087ad3a924be12343bb035bf9b63ed81f650bf (diff)
parentdca0a339dce46db80ce45e2d24ab29c3ec93270a (diff)
downloadrust-8b4d22cb25bd49ac29eaa2960b559b7eee06d197.tar.gz
rust-8b4d22cb25bd49ac29eaa2960b559b7eee06d197.zip
Auto merge of #67598 - jumbatm:issue67557_simd_shuffle, r=oli-obk
Fix ICE / miscompilation when inlining simd shuffle intrinsic in MIR.

Closes #67557.

r? @oli-obk
-rw-r--r--src/librustc_codegen_ssa/mir/block.rs9
-rw-r--r--src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557-ice.rs25
-rw-r--r--src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557.rs40
3 files changed, 71 insertions, 3 deletions
diff --git a/src/librustc_codegen_ssa/mir/block.rs b/src/librustc_codegen_ssa/mir/block.rs
index e856be0eeb3..a89b170c649 100644
--- a/src/librustc_codegen_ssa/mir/block.rs
+++ b/src/librustc_codegen_ssa/mir/block.rs
@@ -618,14 +618,17 @@ impl<'a, 'tcx, Bx: BuilderMethods<'a, 'tcx>> FunctionCx<'a, 'tcx, Bx> {
                                 if let mir::PlaceRef {
                                     base:
                                         &PlaceBase::Static(box Static {
-                                            kind: StaticKind::Promoted(promoted, _),
+                                            kind: StaticKind::Promoted(promoted, substs),
                                             ty,
-                                            def_id: _,
+                                            def_id,
                                         }),
                                     projection: &[],
                                 } = place.as_ref()
                                 {
-                                    let c = bx.tcx().const_eval_promoted(self.instance, promoted);
+                                    let c = bx.tcx().const_eval_promoted(
+                                        Instance::new(def_id, self.monomorphize(&substs)),
+                                        promoted,
+                                    );
                                     let (llval, ty) = self.simd_shuffle_indices(
                                         &bx,
                                         terminator.source_info.span,
diff --git a/src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557-ice.rs b/src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557-ice.rs
new file mode 100644
index 00000000000..4c09ae25c5f
--- /dev/null
+++ b/src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557-ice.rs
@@ -0,0 +1,25 @@
+// This used to cause an ICE for an internal index out of range due to simd_shuffle_indices being
+// passed the wrong Instance, causing issues with inlining. See #67557.
+//
+// run-pass
+// compile-flags: -Zmir-opt-level=3
+#![feature(platform_intrinsics, repr_simd)]
+
+extern "platform-intrinsic" {
+    fn simd_shuffle2<T, U>(x: T, y: T, idx: [u32; 2]) -> U;
+}
+
+#[repr(simd)]
+#[derive(Debug, PartialEq)]
+struct Simd2(u8, u8);
+
+fn main() {
+    unsafe {
+        let _: Simd2 = inline_me();
+    }
+}
+
+#[inline(always)]
+unsafe fn inline_me() -> Simd2 {
+    simd_shuffle2(Simd2(10, 11), Simd2(12, 13), [0, 3])
+}
diff --git a/src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557.rs b/src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557.rs
new file mode 100644
index 00000000000..7a0d955686b
--- /dev/null
+++ b/src/test/ui/simd-intrinsic/simd-intrinsic-inlining-issue67557.rs
@@ -0,0 +1,40 @@
+// This used to cause assert_10_13 to unexpectingly fail, due to simd_shuffle_indices being passed
+// the wrong Instance, causing issues with inlining. See #67557.
+//
+// run-pass
+// compile-flags: -Zmir-opt-level=3
+#![feature(platform_intrinsics, repr_simd)]
+
+extern "platform-intrinsic" {
+    fn simd_shuffle2<T, U>(x: T, y: T, idx: [u32; 2]) -> U;
+}
+
+#[repr(simd)]
+#[derive(Debug, PartialEq)]
+struct Simd2(u8, u8);
+
+fn main() {
+    unsafe {
+        let p_res: Simd2 = simd_shuffle2(Simd2(10, 11), Simd2(12, 13), [0, 1]);
+        let a_res: Simd2 = inline_me();
+
+        assert_10_11(p_res);
+        assert_10_13(a_res);
+    }
+}
+
+#[inline(never)]
+fn assert_10_11(x: Simd2) {
+    assert_eq!(x, Simd2(10, 11));
+}
+
+#[inline(never)]
+fn assert_10_13(x: Simd2) {
+    assert_eq!(x, Simd2(10, 13));
+}
+
+
+#[inline(always)]
+unsafe fn inline_me() -> Simd2 {
+    simd_shuffle2(Simd2(10, 11), Simd2(12, 13), [0, 3])
+}