DelaySlotFiller.cpp revision 7c90f73a1b06040d971a3dd95a491031ae6238d5
146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)//===-- DelaySlotFiller.cpp - SPARC delay slot filler ---------------------===//
246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)//
346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)//                     The LLVM Compiler Infrastructure
446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)//
51320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// This file was developed by the LLVM research group and is distributed under
646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)// the University of Illinois Open Source License. See LICENSE.TXT for details.
71320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci//
8f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)//===----------------------------------------------------------------------===//
946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)//
10f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)// This is a simple local pass that fills delay slots with NOPs.
1146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)//
1246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)//===----------------------------------------------------------------------===//
1346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)
1446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "Sparc.h"
1546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "llvm/CodeGen/MachineFunctionPass.h"
1646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "llvm/CodeGen/MachineInstrBuilder.h"
1746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "llvm/Target/TargetMachine.h"
1846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "llvm/Target/TargetInstrInfo.h"
1946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "llvm/ADT/Statistic.h"
2046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)using namespace llvm;
211320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci
2246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)namespace {
231320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  Statistic<> FilledSlots("delayslotfiller", "Num. of delay slots filled");
241320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci
251320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci  struct Filler : public MachineFunctionPass {
2646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    /// Target machine description which we query for reg. names, data
2746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    /// layout, etc.
28f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    ///
291320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    TargetMachine &TM;
301320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    const TargetInstrInfo *TII;
311320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci
321320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    Filler(TargetMachine &tm) : TM(tm), TII(tm.getInstrInfo()) { }
331320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci
341320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    virtual const char *getPassName() const {
351320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci      return "SPARC Delay Slot Filler";
361320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    }
371320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci
38f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    bool runOnMachineBasicBlock(MachineBasicBlock &MBB);
39f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    bool runOnMachineFunction(MachineFunction &F) {
4046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)      bool Changed = false;
41      for (MachineFunction::iterator FI = F.begin(), FE = F.end();
42           FI != FE; ++FI)
43        Changed |= runOnMachineBasicBlock(*FI);
44      return Changed;
45    }
46
47  };
48} // end of anonymous namespace
49
50/// createSparcDelaySlotFillerPass - Returns a pass that fills in delay
51/// slots in Sparc MachineFunctions
52///
53FunctionPass *llvm::createSparcDelaySlotFillerPass(TargetMachine &tm) {
54  return new Filler(tm);
55}
56
57/// runOnMachineBasicBlock - Fill in delay slots for the given basic block.
58/// Currently, we fill delay slots with NOPs. We assume there is only one
59/// delay slot per delayed instruction.
60///
61bool Filler::runOnMachineBasicBlock(MachineBasicBlock &MBB) {
62  bool Changed = false;
63  for (MachineBasicBlock::iterator I = MBB.begin(); I != MBB.end(); ++I)
64    if (TII->hasDelaySlot(I->getOpcode())) {
65      MachineBasicBlock::iterator J = I;
66      ++J;
67      BuildMI(MBB, J, SP::NOP, 0);
68      ++FilledSlots;
69      Changed = true;
70    }
71  return Changed;
72}
73