From d4b67a3fb6c2369f8cd6963e543b8e212e0022d8 Mon Sep 17 00:00:00 2001 From: Sanjay Patel Date: Mon, 9 Oct 2017 15:22:20 +0000 Subject: [PATCH] [DAG] combine assertsexts around a trunc This was a suggested follow-up to: D37017 / https://reviews.llvm.org/rL313577 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@315206 91177308-0d34-0410-b5e6-96231b3b80d8 --- lib/CodeGen/SelectionDAG/DAGCombiner.cpp | 20 ++++++++++---------- test/CodeGen/Mips/llvm-ir/and.ll | 24 +++++++++++++++--------- test/CodeGen/Mips/llvm-ir/not.ll | 15 ++++++++++++--- test/CodeGen/Mips/llvm-ir/or.ll | 24 +++++++++++++++--------- test/CodeGen/Mips/llvm-ir/xor.ll | 24 +++++++++++++++--------- test/CodeGen/X86/select_const.ll | 21 +++++++++------------ test/CodeGen/X86/sext-i1.ll | 5 ++--- test/CodeGen/X86/split-store.ll | 12 +++++------- 8 files changed, 83 insertions(+), 62 deletions(-) diff --git a/lib/CodeGen/SelectionDAG/DAGCombiner.cpp b/lib/CodeGen/SelectionDAG/DAGCombiner.cpp index f413ba29463..526c3b8d878 100644 --- a/lib/CodeGen/SelectionDAG/DAGCombiner.cpp +++ b/lib/CodeGen/SelectionDAG/DAGCombiner.cpp @@ -328,7 +328,7 @@ namespace { SDValue visitSIGN_EXTEND(SDNode *N); SDValue visitZERO_EXTEND(SDNode *N); SDValue visitANY_EXTEND(SDNode *N); - SDValue visitAssertZext(SDNode *N); + SDValue visitAssertExt(SDNode *N); SDValue visitSIGN_EXTEND_INREG(SDNode *N); SDValue visitSIGN_EXTEND_VECTOR_INREG(SDNode *N); SDValue visitZERO_EXTEND_VECTOR_INREG(SDNode *N); @@ -1553,7 +1553,8 @@ SDValue DAGCombiner::visit(SDNode *N) { case ISD::SIGN_EXTEND: return visitSIGN_EXTEND(N); case ISD::ZERO_EXTEND: return visitZERO_EXTEND(N); case ISD::ANY_EXTEND: return visitANY_EXTEND(N); - case ISD::AssertZext: return visitAssertZext(N); + case ISD::AssertSext: + case ISD::AssertZext: return visitAssertExt(N); case ISD::SIGN_EXTEND_INREG: return visitSIGN_EXTEND_INREG(N); case ISD::SIGN_EXTEND_VECTOR_INREG: return visitSIGN_EXTEND_VECTOR_INREG(N); case ISD::ZERO_EXTEND_VECTOR_INREG: return visitZERO_EXTEND_VECTOR_INREG(N); @@ -7978,20 +7979,19 @@ SDValue DAGCombiner::visitANY_EXTEND(SDNode *N) { return SDValue(); } -// TODO: These transforms should work with AssertSext too. -// Change the function name, comments, opcode references, and caller. -SDValue DAGCombiner::visitAssertZext(SDNode *N) { +SDValue DAGCombiner::visitAssertExt(SDNode *N) { + unsigned Opcode = N->getOpcode(); SDValue N0 = N->getOperand(0); SDValue N1 = N->getOperand(1); EVT AssertVT = cast(N1)->getVT(); - // fold (assertzext (assertzext x, vt), vt) -> (assertzext x, vt) - if (N0.getOpcode() == ISD::AssertZext && + // fold (assert?ext (assert?ext x, vt), vt) -> (assert?ext x, vt) + if (N0.getOpcode() == Opcode && AssertVT == cast(N0.getOperand(1))->getVT()) return N0; if (N0.getOpcode() == ISD::TRUNCATE && N0.hasOneUse() && - N0.getOperand(0).getOpcode() == ISD::AssertZext) { + N0.getOperand(0).getOpcode() == Opcode) { // We have an assert, truncate, assert sandwich. Make one stronger assert // by asserting on the smallest asserted type to the larger source type. // This eliminates the later assert: @@ -8000,13 +8000,13 @@ SDValue DAGCombiner::visitAssertZext(SDNode *N) { SDValue BigA = N0.getOperand(0); EVT BigA_AssertVT = cast(BigA.getOperand(1))->getVT(); assert(BigA_AssertVT.bitsLE(N0.getValueType()) && - "Asserting zero/sign-extended bits from a type larger than the " + "Asserting zero/sign-extended bits to a type larger than the " "truncated destination does not provide information"); SDLoc DL(N); EVT MinAssertVT = AssertVT.bitsLT(BigA_AssertVT) ? AssertVT : BigA_AssertVT; SDValue MinAssertVTVal = DAG.getValueType(MinAssertVT); - SDValue NewAssert = DAG.getNode(ISD::AssertZext, DL, BigA.getValueType(), + SDValue NewAssert = DAG.getNode(Opcode, DL, BigA.getValueType(), BigA.getOperand(0), MinAssertVTVal); return DAG.getNode(ISD::TRUNCATE, DL, N->getValueType(0), NewAssert); } diff --git a/test/CodeGen/Mips/llvm-ir/and.ll b/test/CodeGen/Mips/llvm-ir/and.ll index c26b60d0ff9..18d7a439f62 100644 --- a/test/CodeGen/Mips/llvm-ir/and.ll +++ b/test/CodeGen/Mips/llvm-ir/and.ll @@ -37,10 +37,12 @@ entry: ; GP32: and $2, $4, $5 - ; GP64: and $2, $4, $5 + ; GP64: and $1, $4, $5 + + ; MM32: and16 $[[T0:[0-9]+]], $5 + ; MM32: move $2, $[[T0]] - ; MM: and16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM64: and $1, $4, $5 %r = and i1 %a, %b ret i1 %r @@ -52,10 +54,12 @@ entry: ; GP32: and $2, $4, $5 - ; GP64: and $2, $4, $5 + ; GP64: and $1, $4, $5 - ; MM: and16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM32: and16 $[[T0:[0-9]+]], $5 + ; MM32: move $2, $[[T0]] + + ; MM64: and $1, $4, $5 %r = and i8 %a, %b ret i8 %r @@ -67,10 +71,12 @@ entry: ; GP32: and $2, $4, $5 - ; GP64: and $2, $4, $5 + ; GP64: and $1, $4, $5 + + ; MM32: and16 $[[T0:[0-9]+]], $5 + ; MM32 move $2, $[[T0]] - ; MM: and16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM64: and $1, $4, $5 %r = and i16 %a, %b ret i16 %r diff --git a/test/CodeGen/Mips/llvm-ir/not.ll b/test/CodeGen/Mips/llvm-ir/not.ll index 914b6164ad0..ab7a3c4613a 100644 --- a/test/CodeGen/Mips/llvm-ir/not.ll +++ b/test/CodeGen/Mips/llvm-ir/not.ll @@ -135,7 +135,10 @@ define signext i1 @nor_i1(i1 signext %a, i1 signext %b) { entry: ; ALL-LABEL: nor_i1: - ; ALL: nor $2, $5, $4 + ; GP32: nor $2, $5, $4 + ; GP64: or $1, $5, $4 + ; MM32: nor $2, $5, $4 + ; MM64: or $1, $5, $4 %or = or i1 %b, %a %r = xor i1 %or, -1 @@ -146,7 +149,10 @@ define signext i8 @nor_i8(i8 signext %a, i8 signext %b) { entry: ; ALL-LABEL: nor_i8: - ; ALL: nor $2, $5, $4 + ; GP32: nor $2, $5, $4 + ; GP64: or $1, $5, $4 + ; MM32: nor $2, $5, $4 + ; MM64: or $1, $5, $4 %or = or i8 %b, %a %r = xor i8 %or, -1 @@ -157,7 +163,10 @@ define signext i16 @nor_i16(i16 signext %a, i16 signext %b) { entry: ; ALL-LABEL: nor_i16: - ; ALL: nor $2, $5, $4 + ; GP32: nor $2, $5, $4 + ; GP64: or $1, $5, $4 + ; MM32: nor $2, $5, $4 + ; MM64: or $1, $5, $4 %or = or i16 %b, %a %r = xor i16 %or, -1 diff --git a/test/CodeGen/Mips/llvm-ir/or.ll b/test/CodeGen/Mips/llvm-ir/or.ll index c7f89ef5d22..609cf0210c3 100644 --- a/test/CodeGen/Mips/llvm-ir/or.ll +++ b/test/CodeGen/Mips/llvm-ir/or.ll @@ -24,10 +24,12 @@ entry: ; GP32: or $2, $4, $5 - ; GP64: or $2, $4, $5 + ; GP64: or $1, $4, $5 + + ; MM32: or16 $[[T0:[0-9]+]], $5 + ; MM32 move $2, $[[T0]] - ; MM: or16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM64: or $1, $4, $5 %r = or i1 %a, %b ret i1 %r @@ -39,10 +41,12 @@ entry: ; GP32: or $2, $4, $5 - ; GP64: or $2, $4, $5 + ; GP64: or $1, $4, $5 - ; MM: or16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM32: or16 $[[T0:[0-9]+]], $5 + ; MM32 move $2, $[[T0]] + + ; MM64: or $1, $4, $5 %r = or i8 %a, %b ret i8 %r @@ -54,10 +58,12 @@ entry: ; GP32: or $2, $4, $5 - ; GP64: or $2, $4, $5 + ; GP64: or $1, $4, $5 + + ; MM32: or16 $[[T0:[0-9]+]], $5 + ; MM32 move $2, $[[T0]] - ; MM: or16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM64: or $1, $4, $5 %r = or i16 %a, %b ret i16 %r diff --git a/test/CodeGen/Mips/llvm-ir/xor.ll b/test/CodeGen/Mips/llvm-ir/xor.ll index 1d45e200a2e..068d390839d 100644 --- a/test/CodeGen/Mips/llvm-ir/xor.ll +++ b/test/CodeGen/Mips/llvm-ir/xor.ll @@ -35,10 +35,12 @@ entry: ; GP32: xor $2, $4, $5 - ; GP64: xor $2, $4, $5 + ; GP64: xor $1, $4, $5 + + ; MM32: xor16 $[[T0:[0-9]+]], $5 + ; MM32: move $2, $[[T0]] - ; MM: xor16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM64: xor $1, $4, $5 %r = xor i1 %a, %b ret i1 %r @@ -50,10 +52,12 @@ entry: ; GP32: xor $2, $4, $5 - ; GP64: xor $2, $4, $5 + ; GP64: xor $1, $4, $5 + + ; MM32: xor16 $[[T0:[0-9]+]], $5 + ; MM32: move $2, $[[T0]] - ; MM: xor16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM64: xor $1, $4, $5 %r = xor i8 %a, %b ret i8 %r @@ -65,10 +69,12 @@ entry: ; GP32: xor $2, $4, $5 - ; GP64: xor $2, $4, $5 + ; GP64: xor $1, $4, $5 + + ; MM32: xor16 $[[T0:[0-9]+]], $5 + ; MM32: move $2, $[[T0]] - ; MM: xor16 $[[T0:[0-9]+]], $5 - ; MM: move $2, $[[T0]] + ; MM64: xor $1, $4, $5 %r = xor i16 %a, %b ret i16 %r diff --git a/test/CodeGen/X86/select_const.ll b/test/CodeGen/X86/select_const.ll index 07aa909d9a9..6454c284ae8 100644 --- a/test/CodeGen/X86/select_const.ll +++ b/test/CodeGen/X86/select_const.ll @@ -62,8 +62,8 @@ define i32 @select_1_or_0_zeroext(i1 zeroext %cond) { define i32 @select_1_or_0_signext(i1 signext %cond) { ; CHECK-LABEL: select_1_or_0_signext: ; CHECK: # BB#0: -; CHECK-NEXT: andb $1, %dil -; CHECK-NEXT: movzbl %dil, %eax +; CHECK-NEXT: andl $1, %edi +; CHECK-NEXT: movl %edi, %eax ; CHECK-NEXT: retq %sel = select i1 %cond, i32 1, i32 0 ret i32 %sel @@ -95,9 +95,8 @@ define i32 @select_0_or_neg1_zeroext(i1 zeroext %cond) { define i32 @select_0_or_neg1_signext(i1 signext %cond) { ; CHECK-LABEL: select_0_or_neg1_signext: ; CHECK: # BB#0: -; CHECK-NEXT: andb $1, %dil -; CHECK-NEXT: movzbl %dil, %eax -; CHECK-NEXT: decl %eax +; CHECK-NEXT: notl %edi +; CHECK-NEXT: movl %edi, %eax ; CHECK-NEXT: retq %sel = select i1 %cond, i32 0, i32 -1 ret i32 %sel @@ -129,7 +128,7 @@ define i32 @select_neg1_or_0_zeroext(i1 zeroext %cond) { define i32 @select_neg1_or_0_signext(i1 signext %cond) { ; CHECK-LABEL: select_neg1_or_0_signext: ; CHECK: # BB#0: -; CHECK-NEXT: movsbl %dil, %eax +; CHECK-NEXT: movl %edi, %eax ; CHECK-NEXT: retq %sel = select i1 %cond, i32 -1, i32 0 ret i32 %sel @@ -161,9 +160,8 @@ define i32 @select_Cplus1_C_zeroext(i1 zeroext %cond) { define i32 @select_Cplus1_C_signext(i1 signext %cond) { ; CHECK-LABEL: select_Cplus1_C_signext: ; CHECK: # BB#0: -; CHECK-NEXT: andb $1, %dil -; CHECK-NEXT: movzbl %dil, %eax -; CHECK-NEXT: addl $41, %eax +; CHECK-NEXT: movl $41, %eax +; CHECK-NEXT: subl %edi, %eax ; CHECK-NEXT: retq %sel = select i1 %cond, i32 42, i32 41 ret i32 %sel @@ -195,10 +193,9 @@ define i32 @select_C_Cplus1_zeroext(i1 zeroext %cond) { define i32 @select_C_Cplus1_signext(i1 signext %cond) { ; CHECK-LABEL: select_C_Cplus1_signext: ; CHECK: # BB#0: -; CHECK-NEXT: andb $1, %dil -; CHECK-NEXT: movzbl %dil, %ecx +; CHECK-NEXT: andl $1, %edi ; CHECK-NEXT: movl $42, %eax -; CHECK-NEXT: subl %ecx, %eax +; CHECK-NEXT: subl %edi, %eax ; CHECK-NEXT: retq %sel = select i1 %cond, i32 41, i32 42 ret i32 %sel diff --git a/test/CodeGen/X86/sext-i1.ll b/test/CodeGen/X86/sext-i1.ll index 0c840e69c7c..ce997f599c1 100644 --- a/test/CodeGen/X86/sext-i1.ll +++ b/test/CodeGen/X86/sext-i1.ll @@ -165,9 +165,8 @@ define i32 @select_0_or_1s_signext(i1 signext %cond) { ; ; X64-LABEL: select_0_or_1s_signext: ; X64: # BB#0: -; X64-NEXT: andb $1, %dil -; X64-NEXT: movzbl %dil, %eax -; X64-NEXT: decl %eax +; X64-NEXT: notl %edi +; X64-NEXT: movl %edi, %eax ; X64-NEXT: retq %not = xor i1 %cond, 1 %sext = sext i1 %not to i32 diff --git a/test/CodeGen/X86/split-store.ll b/test/CodeGen/X86/split-store.ll index 2c28be46053..04dafae94ba 100644 --- a/test/CodeGen/X86/split-store.ll +++ b/test/CodeGen/X86/split-store.ll @@ -197,13 +197,11 @@ define void @int12_int12_pair(i12 signext %tmp1, i12 signext %tmp2, i24* %ref.tm define void @int7_int7_pair(i7 signext %tmp1, i7 signext %tmp2, i14* %ref.tmp) { ; CHECK-LABEL: int7_int7_pair: ; CHECK: # BB#0: -; CHECK-NEXT: movzbl %sil, %eax -; CHECK-NEXT: shll $7, %eax -; CHECK-NEXT: andb $127, %dil -; CHECK-NEXT: movzbl %dil, %ecx -; CHECK-NEXT: orl %eax, %ecx -; CHECK-NEXT: andl $16383, %ecx # imm = 0x3FFF -; CHECK-NEXT: movw %cx, (%rdx) +; CHECK-NEXT: shll $7, %esi +; CHECK-NEXT: andl $127, %edi +; CHECK-NEXT: orl %esi, %edi +; CHECK-NEXT: andl $16383, %edi # imm = 0x3FFF +; CHECK-NEXT: movw %di, (%rdx) ; CHECK-NEXT: retq %t1 = zext i7 %tmp2 to i14 %t2 = shl nuw i14 %t1, 7 -- 2.40.0