summaryrefslogtreecommitdiffstats
path: root/contrib/llvm/patches/patch-r262261-llvm-r199014-sparc.diff
diff options
context:
space:
mode:
Diffstat (limited to 'contrib/llvm/patches/patch-r262261-llvm-r199014-sparc.diff')
-rw-r--r--contrib/llvm/patches/patch-r262261-llvm-r199014-sparc.diff133
1 files changed, 133 insertions, 0 deletions
diff --git a/contrib/llvm/patches/patch-r262261-llvm-r199014-sparc.diff b/contrib/llvm/patches/patch-r262261-llvm-r199014-sparc.diff
new file mode 100644
index 0000000..6db27a06
--- /dev/null
+++ b/contrib/llvm/patches/patch-r262261-llvm-r199014-sparc.diff
@@ -0,0 +1,133 @@
+Pull in r199014 from upstream llvm trunk (by Venkatraman Govindaraju):
+
+ [Sparc] Bundle instruction with delay slow and its filler. Now, we can use -verify-machineinstrs with SPARC backend.
+
+Introduced here: http://svn.freebsd.org/changeset/base/262261
+
+Index: lib/Target/Sparc/DelaySlotFiller.cpp
+===================================================================
+--- lib/Target/Sparc/DelaySlotFiller.cpp
++++ lib/Target/Sparc/DelaySlotFiller.cpp
+@@ -19,6 +19,7 @@
+ #include "llvm/ADT/Statistic.h"
+ #include "llvm/CodeGen/MachineFunctionPass.h"
+ #include "llvm/CodeGen/MachineInstrBuilder.h"
++#include "llvm/CodeGen/MachineRegisterInfo.h"
+ #include "llvm/Support/CommandLine.h"
+ #include "llvm/Target/TargetInstrInfo.h"
+ #include "llvm/Target/TargetMachine.h"
+@@ -55,6 +56,11 @@ namespace {
+ bool runOnMachineBasicBlock(MachineBasicBlock &MBB);
+ bool runOnMachineFunction(MachineFunction &F) {
+ bool Changed = false;
++
++ // This pass invalidates liveness information when it reorders
++ // instructions to fill delay slot.
++ F.getRegInfo().invalidateLiveness();
++
+ for (MachineFunction::iterator FI = F.begin(), FE = F.end();
+ FI != FE; ++FI)
+ Changed |= runOnMachineBasicBlock(*FI);
+@@ -61,9 +67,6 @@ namespace {
+ return Changed;
+ }
+
+- bool isDelayFiller(MachineBasicBlock &MBB,
+- MachineBasicBlock::iterator candidate);
+-
+ void insertCallDefsUses(MachineBasicBlock::iterator MI,
+ SmallSet<unsigned, 32>& RegDefs,
+ SmallSet<unsigned, 32>& RegUses);
+@@ -152,6 +155,10 @@ bool Filler::runOnMachineBasicBlock(MachineBasicBl
+ assert (J != MBB.end() && "MI needs a delay instruction.");
+ BuildMI(MBB, ++J, MI->getDebugLoc(),
+ TII->get(SP::UNIMP)).addImm(structSize);
++ // Bundle the delay filler and unimp with the instruction.
++ MIBundleBuilder(MBB, MachineBasicBlock::iterator(MI), J);
++ } else {
++ MIBundleBuilder(MBB, MachineBasicBlock::iterator(MI), I);
+ }
+ }
+ return Changed;
+@@ -209,7 +216,7 @@ Filler::findDelayInstr(MachineBasicBlock &MBB,
+ || I->isInlineAsm()
+ || I->isLabel()
+ || I->hasDelaySlot()
+- || isDelayFiller(MBB, I))
++ || I->isBundledWithSucc())
+ break;
+
+ if (delayHasHazard(I, sawLoad, sawStore, RegDefs, RegUses)) {
+@@ -332,18 +339,6 @@ bool Filler::IsRegInSet(SmallSet<unsigned, 32>& Re
+ return false;
+ }
+
+-// return true if the candidate is a delay filler.
+-bool Filler::isDelayFiller(MachineBasicBlock &MBB,
+- MachineBasicBlock::iterator candidate)
+-{
+- if (candidate == MBB.begin())
+- return false;
+- if (candidate->getOpcode() == SP::UNIMP)
+- return true;
+- --candidate;
+- return candidate->hasDelaySlot();
+-}
+-
+ bool Filler::needsUnimp(MachineBasicBlock::iterator I, unsigned &StructSize)
+ {
+ if (!I->isCall())
+@@ -484,10 +479,10 @@ bool Filler::tryCombineRestoreWithPrevInst(Machine
+ && MBBI->getOperand(1).getReg() == SP::G0
+ && MBBI->getOperand(2).getReg() == SP::G0);
+
+- MachineBasicBlock::iterator PrevInst = MBBI; --PrevInst;
++ MachineBasicBlock::iterator PrevInst = llvm::prior(MBBI);
+
+- // It cannot combine with a delay filler.
+- if (isDelayFiller(MBB, PrevInst))
++ // It cannot be combined with a bundled instruction.
++ if (PrevInst->isBundledWithSucc())
+ return false;
+
+ const TargetInstrInfo *TII = TM.getInstrInfo();
+Index: lib/Target/Sparc/SparcAsmPrinter.cpp
+===================================================================
+--- lib/Target/Sparc/SparcAsmPrinter.cpp
++++ lib/Target/Sparc/SparcAsmPrinter.cpp
+@@ -184,7 +184,6 @@ static void LowerGETPCXAndEmitMCInsts(const Machin
+
+ void SparcAsmPrinter::EmitInstruction(const MachineInstr *MI)
+ {
+- MCInst TmpInst;
+
+ switch (MI->getOpcode()) {
+ default: break;
+@@ -195,8 +194,13 @@ void SparcAsmPrinter::EmitInstruction(const Machin
+ LowerGETPCXAndEmitMCInsts(MI, OutStreamer, OutContext);
+ return;
+ }
+- LowerSparcMachineInstrToMCInst(MI, TmpInst, *this);
+- OutStreamer.EmitInstruction(TmpInst);
++ MachineBasicBlock::const_instr_iterator I = MI;
++ MachineBasicBlock::const_instr_iterator E = MI->getParent()->instr_end();
++ do {
++ MCInst TmpInst;
++ LowerSparcMachineInstrToMCInst(I, TmpInst, *this);
++ OutStreamer.EmitInstruction(TmpInst);
++ } while ((++I != E) && I->isInsideBundle()); // Delay slot check.
+ }
+
+ void SparcAsmPrinter::EmitFunctionBodyStart() {
+Index: test/CodeGen/SPARC/2011-01-19-DelaySlot.ll
+===================================================================
+--- test/CodeGen/SPARC/2011-01-19-DelaySlot.ll
++++ test/CodeGen/SPARC/2011-01-19-DelaySlot.ll
+@@ -1,5 +1,5 @@
+-;RUN: llc -march=sparc < %s | FileCheck %s
+-;RUN: llc -march=sparc -O0 < %s | FileCheck %s -check-prefix=UNOPT
++;RUN: llc -march=sparc < %s -verify-machineinstrs | FileCheck %s
++;RUN: llc -march=sparc -O0 < %s -verify-machineinstrs | FileCheck %s -check-prefix=UNOPT
+
+
+ define i32 @test(i32 %a) nounwind {
OpenPOWER on IntegriCloud