diff options
author | Juergen Ributzka <juergen@apple.com> | 2014-10-27 19:38:05 +0000 |
---|---|---|
committer | Juergen Ributzka <juergen@apple.com> | 2014-10-27 19:38:05 +0000 |
commit | 90f741a2ce6422ad7fc6db111a470f3da5b5942b (patch) | |
tree | 87a77761e85877da294ea547fe2165be357ef4c9 /llvm | |
parent | 68c29da4c5a6e3f5443c3b2bfc0ee6d2f44002c8 (diff) | |
download | bcm5719-llvm-90f741a2ce6422ad7fc6db111a470f3da5b5942b.tar.gz bcm5719-llvm-90f741a2ce6422ad7fc6db111a470f3da5b5942b.zip |
[FastISel][AArch64] Use 'cbz' also for null values (pointers).
The pattern matching for a 'ConstantInt' value was too restrictive. Checking for
a 'Constant' with a bull value is sufficient for using an 'cbz/cbnz' instruction.
This fixes rdar://problem/18784732.
llvm-svn: 220709
Diffstat (limited to 'llvm')
-rw-r--r-- | llvm/lib/Target/AArch64/AArch64FastISel.cpp | 27 | ||||
-rw-r--r-- | llvm/test/CodeGen/AArch64/fast-isel-cbz.ll | 11 |
2 files changed, 23 insertions, 15 deletions
diff --git a/llvm/lib/Target/AArch64/AArch64FastISel.cpp b/llvm/lib/Target/AArch64/AArch64FastISel.cpp index d6269284801..09bdab7fe8d 100644 --- a/llvm/lib/Target/AArch64/AArch64FastISel.cpp +++ b/llvm/lib/Target/AArch64/AArch64FastISel.cpp @@ -2087,12 +2087,12 @@ bool AArch64FastISel::emitCompareAndBranch(const BranchInst *BI) { const Value *LHS = CI->getOperand(0); const Value *RHS = CI->getOperand(1); - Type *Ty = LHS->getType(); - if (!Ty->isIntegerTy()) - return false; + MVT VT; + if (!isTypeSupported(LHS->getType(), VT)) + return false; - unsigned BW = cast<IntegerType>(Ty)->getBitWidth(); - if (BW != 1 && BW != 8 && BW != 16 && BW != 32 && BW != 64) + unsigned BW = VT.getSizeInBits(); + if (BW > 64) return false; MachineBasicBlock *TBB = FuncInfo.MBBMap[BI->getSuccessor(0)]; @@ -2107,14 +2107,14 @@ bool AArch64FastISel::emitCompareAndBranch(const BranchInst *BI) { int TestBit = -1; bool IsCmpNE; if ((Predicate == CmpInst::ICMP_EQ) || (Predicate == CmpInst::ICMP_NE)) { - if (const auto *C = dyn_cast<ConstantInt>(LHS)) + if (const auto *C = dyn_cast<Constant>(LHS)) if (C->isNullValue()) std::swap(LHS, RHS); - if (!isa<ConstantInt>(RHS)) + if (!isa<Constant>(RHS)) return false; - if (!cast<ConstantInt>(RHS)->isNullValue()) + if (!cast<Constant>(RHS)->isNullValue()) return false; if (const auto *AI = dyn_cast<BinaryOperator>(LHS)) @@ -2134,10 +2134,10 @@ bool AArch64FastISel::emitCompareAndBranch(const BranchInst *BI) { } IsCmpNE = Predicate == CmpInst::ICMP_NE; } else if (Predicate == CmpInst::ICMP_SLT) { - if (!isa<ConstantInt>(RHS)) + if (!isa<Constant>(RHS)) return false; - if (!cast<ConstantInt>(RHS)->isNullValue()) + if (!cast<Constant>(RHS)->isNullValue()) return false; TestBit = BW - 1; @@ -2178,11 +2178,8 @@ bool AArch64FastISel::emitCompareAndBranch(const BranchInst *BI) { SrcReg = fastEmitInst_extractsubreg(MVT::i32, SrcReg, SrcIsKill, AArch64::sub_32); - if ((BW < 32) && !IsBitTest) { - EVT CmpEVT = TLI.getValueType(Ty, true); - SrcReg = - emitIntExt(CmpEVT.getSimpleVT(), SrcReg, MVT::i32, /*isZExt*/ true); - } + if ((BW < 32) && !IsBitTest) + SrcReg = emitIntExt(VT, SrcReg, MVT::i32, /*IsZExt=*/true); // Emit the combined compare and branch instruction. SrcReg = constrainOperandRegClass(II, SrcReg, II.getNumDefs()); diff --git a/llvm/test/CodeGen/AArch64/fast-isel-cbz.ll b/llvm/test/CodeGen/AArch64/fast-isel-cbz.ll index 4cd4b539401..20c5df105ad 100644 --- a/llvm/test/CodeGen/AArch64/fast-isel-cbz.ll +++ b/llvm/test/CodeGen/AArch64/fast-isel-cbz.ll @@ -58,3 +58,14 @@ bb1: ret i32 0 } +define i32 @icmp_eq_ptr(i8* %a) { +; CHECK-LABEL: icmp_eq_ptr +; CHECK: cbz x0, {{LBB.+_2}} + %1 = icmp eq i8* %a, null + br i1 %1, label %bb1, label %bb2 +bb2: + ret i32 1 +bb1: + ret i32 0 +} + |