diff options
author | Artyom Skrobov <Artyom.Skrobov@arm.com> | 2014-02-26 11:27:28 +0000 |
---|---|---|
committer | Artyom Skrobov <Artyom.Skrobov@arm.com> | 2014-02-26 11:27:28 +0000 |
commit | e7082383732df492d8fabd17c31300db08de7627 (patch) | |
tree | 449d776a03de2b2c617ed0252b2abf17e5681cc3 /lib | |
parent | 3d0b46969073ca31a74b5a19c16163b6b24fb770 (diff) | |
download | llvm-e7082383732df492d8fabd17c31300db08de7627.tar.gz llvm-e7082383732df492d8fabd17c31300db08de7627.tar.bz2 llvm-e7082383732df492d8fabd17c31300db08de7627.tar.xz |
ARMv8 IfConversion must skip narrow instructions that a) define CPSR and b) wouldn't affect CPSR in an IT block
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@202257 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib')
-rw-r--r-- | lib/Target/ARM/ARMBaseInstrInfo.cpp | 14 | ||||
-rw-r--r-- | lib/Target/ARM/ARMFeatures.h | 37 | ||||
-rw-r--r-- | lib/Target/ARM/AsmParser/ARMAsmParser.cpp | 4 |
3 files changed, 39 insertions, 16 deletions
diff --git a/lib/Target/ARM/ARMBaseInstrInfo.cpp b/lib/Target/ARM/ARMBaseInstrInfo.cpp index a244c5fb8a..320f54a327 100644 --- a/lib/Target/ARM/ARMBaseInstrInfo.cpp +++ b/lib/Target/ARM/ARMBaseInstrInfo.cpp @@ -535,6 +535,20 @@ bool ARMBaseInstrInfo::isPredicable(MachineInstr *MI) const { return true; } +template<> bool IsCPSRDead<MachineInstr>(MachineInstr* MI) { + for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) { + const MachineOperand &MO = MI->getOperand(i); + if (!MO.isReg() || MO.isUndef() || MO.isUse()) + continue; + if (MO.getReg() != ARM::CPSR) + continue; + if (!MO.isDead()) + return false; + } + // all definitions of CPSR are dead + return true; +} + /// FIXME: Works around a gcc miscompilation with -fstrict-aliasing. LLVM_ATTRIBUTE_NOINLINE static unsigned getNumJTEntries(const std::vector<MachineJumpTableEntry> &JT, diff --git a/lib/Target/ARM/ARMFeatures.h b/lib/Target/ARM/ARMFeatures.h index 2580f7bf7f..e2a228c18a 100644 --- a/lib/Target/ARM/ARMFeatures.h +++ b/lib/Target/ARM/ARMFeatures.h @@ -16,6 +16,9 @@ #include "ARM.h" +template<typename InstrType> // could be MachineInstr or MCInst +bool IsCPSRDead(InstrType *Instr); + namespace llvm { template<typename InstrType> // could be MachineInstr or MCInst @@ -26,25 +29,12 @@ inline bool isV8EligibleForIT(InstrType *Instr) { case ARM::tADC: case ARM::tADDi3: case ARM::tADDi8: - case ARM::tADDrSPi: case ARM::tADDrr: case ARM::tAND: case ARM::tASRri: case ARM::tASRrr: case ARM::tBIC: - case ARM::tCMNz: - case ARM::tCMPi8: - case ARM::tCMPr: case ARM::tEOR: - case ARM::tLDRBi: - case ARM::tLDRBr: - case ARM::tLDRHi: - case ARM::tLDRHr: - case ARM::tLDRSB: - case ARM::tLDRSH: - case ARM::tLDRi: - case ARM::tLDRr: - case ARM::tLDRspi: case ARM::tLSLri: case ARM::tLSLrr: case ARM::tLSRri: @@ -56,6 +46,24 @@ inline bool isV8EligibleForIT(InstrType *Instr) { case ARM::tROR: case ARM::tRSB: case ARM::tSBC: + case ARM::tSUBi3: + case ARM::tSUBi8: + case ARM::tSUBrr: + // Outside of an IT block, these set CPSR. + return IsCPSRDead(Instr); + case ARM::tADDrSPi: + case ARM::tCMNz: + case ARM::tCMPi8: + case ARM::tCMPr: + case ARM::tLDRBi: + case ARM::tLDRBr: + case ARM::tLDRHi: + case ARM::tLDRHr: + case ARM::tLDRSB: + case ARM::tLDRSH: + case ARM::tLDRi: + case ARM::tLDRr: + case ARM::tLDRspi: case ARM::tSTRBi: case ARM::tSTRBr: case ARM::tSTRHi: @@ -63,9 +71,6 @@ inline bool isV8EligibleForIT(InstrType *Instr) { case ARM::tSTRi: case ARM::tSTRr: case ARM::tSTRspi: - case ARM::tSUBi3: - case ARM::tSUBi8: - case ARM::tSUBrr: case ARM::tTST: return true; // there are some "conditionally deprecated" opcodes diff --git a/lib/Target/ARM/AsmParser/ARMAsmParser.cpp b/lib/Target/ARM/AsmParser/ARMAsmParser.cpp index 9bb1cf2b4c..7dc4d18a07 100644 --- a/lib/Target/ARM/AsmParser/ARMAsmParser.cpp +++ b/lib/Target/ARM/AsmParser/ARMAsmParser.cpp @@ -7850,6 +7850,10 @@ unsigned ARMAsmParser::checkTargetMatchPredicate(MCInst &Inst) { return Match_Success; } +template<> inline bool IsCPSRDead<MCInst>(MCInst* Instr) { + return true; // In an assembly source, no need to second-guess +} + static const char *getSubtargetFeatureName(unsigned Val); bool ARMAsmParser:: MatchAndEmitInstruction(SMLoc IDLoc, unsigned &Opcode, |