From e9915738beed0d8b4b50dca8c0ed8c76e7d320db Mon Sep 17 00:00:00 2001 From: Jim Grosbach Date: Wed, 9 Apr 2014 23:28:11 +0000 Subject: [PATCH] SelectionDAG: Don't constant fold target-specific nodes. FoldConstantArithmetic() only knows how to deal with a few target independent ISD opcodes. Bail early if it sees a target-specific ISD node. These node do funny things with operand types which may break the assumptions of the code that follows, and there's no actual folding that can be done anyway. For example, non-constant 256 bit vector shifts on X86 have a shift-amount operand that's a 128-bit v4i32 vector regardless of what the first operand type is and that breaks the assumption that the operand types must match. rdar://16530923 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@205937 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/CodeGen/SelectionDAG/SelectionDAG.cpp | 6 ++++++ test/CodeGen/X86/avx2-vector-shifts.ll | 10 ++++++++++ 2 files changed, 16 insertions(+) diff --git a/lib/CodeGen/SelectionDAG/SelectionDAG.cpp b/lib/CodeGen/SelectionDAG/SelectionDAG.cpp index 8f624508398..e85739688cf 100644 --- a/lib/CodeGen/SelectionDAG/SelectionDAG.cpp +++ b/lib/CodeGen/SelectionDAG/SelectionDAG.cpp @@ -2811,6 +2811,12 @@ SDValue SelectionDAG::getNode(unsigned Opcode, SDLoc DL, SDValue SelectionDAG::FoldConstantArithmetic(unsigned Opcode, EVT VT, SDNode *Cst1, SDNode *Cst2) { + // If the opcode is a target-specific ISD node, there's nothing we can + // do here and the operand rules may not line up with the below, so + // bail early. + if (Opcode >= ISD::BUILTIN_OP_END) + return SDValue(); + SmallVector, 4> Inputs; SmallVector Outputs; EVT SVT = VT.getScalarType(); diff --git a/test/CodeGen/X86/avx2-vector-shifts.ll b/test/CodeGen/X86/avx2-vector-shifts.ll index 4ae2905ef22..e355301dd05 100644 --- a/test/CodeGen/X86/avx2-vector-shifts.ll +++ b/test/CodeGen/X86/avx2-vector-shifts.ll @@ -52,6 +52,16 @@ entry: ; CHECK: vpaddd %ymm0, %ymm0, %ymm0 ; CHECK: ret +define <8 x i32> @test_vpslld_var(i32 %shift) { + %amt = insertelement <8 x i32> undef, i32 %shift, i32 0 + %tmp = shl <8 x i32> , %amt + ret <8 x i32> %tmp +} + +; CHECK-LABEL: test_vpslld_var: +; CHECK: vpslld %xmm0, %ymm1, %ymm0 +; CHECK: ret + define <8 x i32> @test_slld_3(<8 x i32> %InVec) { entry: %shl = shl <8 x i32> %InVec,