DelaySlotFiller.cpp revision 71e39dac0ce9676dd3d0a92164167e18499d40fa
17c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner//===-- DelaySlotFiller.cpp - SPARC delay slot filler ---------------------===//
2b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman//
320117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke//                     The LLVM Compiler Infrastructure
420117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke//
54ee451de366474b9c228b4e5fa573795a715216dChris Lattner// This file is distributed under the University of Illinois Open Source
64ee451de366474b9c228b4e5fa573795a715216dChris Lattner// License. See LICENSE.TXT for details.
7b5f662fa0314f7e7e690aae8ebff7136cc3a5ab0Misha Brukman//
820117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke//===----------------------------------------------------------------------===//
920117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke//
1071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju// This is a simple local pass that attempts to fill delay slots with useful
1171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju// instructions. If no instructions can be moved into the delay slot, then a
1271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju// NOP is placed.
1320117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke//===----------------------------------------------------------------------===//
1420117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
1571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju#define DEBUG_TYPE "delay-slot-filler"
167c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner#include "Sparc.h"
1720117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke#include "llvm/CodeGen/MachineFunctionPass.h"
1820117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke#include "llvm/CodeGen/MachineInstrBuilder.h"
1971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju#include "llvm/Support/CommandLine.h"
20870248b16491c9a9a604494b4e7aa94035af2158Brian Gaeke#include "llvm/Target/TargetMachine.h"
21870248b16491c9a9a604494b4e7aa94035af2158Brian Gaeke#include "llvm/Target/TargetInstrInfo.h"
2271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju#include "llvm/Target/TargetRegisterInfo.h"
2371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju#include "llvm/ADT/SmallSet.h"
2474dfcf12000fcec60e1854f7bb78d481347a0a4bBrian Gaeke#include "llvm/ADT/Statistic.h"
2571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
2620117102c2e10fa2c0fa74965894e28751a3df34Brian Gaekeusing namespace llvm;
2720117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
2895b2c7da5e83670881270c1cd231a240be0556d9Chris LattnerSTATISTIC(FilledSlots, "Number of delay slots filled");
2920117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
3071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindarajustatic cl::opt<bool> DisableDelaySlotFiller(
3171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  "disable-sparc-delay-filler",
3271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  cl::init(false),
3371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  cl::desc("Disable the Sparc delay slot filler."),
3471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  cl::Hidden);
3571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
3695b2c7da5e83670881270c1cd231a240be0556d9Chris Lattnernamespace {
3720117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke  struct Filler : public MachineFunctionPass {
3820117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke    /// Target machine description which we query for reg. names, data
3920117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke    /// layout, etc.
4020117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke    ///
4120117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke    TargetMachine &TM;
42870248b16491c9a9a604494b4e7aa94035af2158Brian Gaeke    const TargetInstrInfo *TII;
4320117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
441997473cf72957d0e70322e2fe6fe2ab141c58a6Devang Patel    static char ID;
45794fd75c67a2cdc128d67342c6d88a504d186896Devang Patel    Filler(TargetMachine &tm)
4690c579de5a383cee278acc3f7e7b9d0a656e6a35Owen Anderson      : MachineFunctionPass(ID), TM(tm), TII(tm.getInstrInfo()) { }
4720117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
487c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner    virtual const char *getPassName() const {
497c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner      return "SPARC Delay Slot Filler";
5020117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke    }
5120117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
527c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner    bool runOnMachineBasicBlock(MachineBasicBlock &MBB);
537c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner    bool runOnMachineFunction(MachineFunction &F) {
5420117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke      bool Changed = false;
557c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner      for (MachineFunction::iterator FI = F.begin(), FE = F.end();
5620117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke           FI != FE; ++FI)
577c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner        Changed |= runOnMachineBasicBlock(*FI);
5820117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke      return Changed;
5920117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke    }
6020117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
6171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    bool isDelayFiller(MachineBasicBlock &MBB,
6271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                       MachineBasicBlock::iterator candidate);
6371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
6471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    void insertCallUses(MachineBasicBlock::iterator MI,
6571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                        SmallSet<unsigned, 32>& RegUses);
6671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
6771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    void insertDefsUses(MachineBasicBlock::iterator MI,
6871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                        SmallSet<unsigned, 32>& RegDefs,
6971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                        SmallSet<unsigned, 32>& RegUses);
7071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
7171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    bool IsRegInSet(SmallSet<unsigned, 32>& RegSet,
7271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                    unsigned Reg);
7371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
7471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    bool delayHasHazard(MachineBasicBlock::iterator candidate,
7571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                        bool &sawLoad, bool &sawStore,
7671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                        SmallSet<unsigned, 32> &RegDefs,
7771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                        SmallSet<unsigned, 32> &RegUses);
7871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
7971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    MachineBasicBlock::iterator
8071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    findDelayInstr(MachineBasicBlock &MBB, MachineBasicBlock::iterator slot);
8171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
8271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
8320117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke  };
841997473cf72957d0e70322e2fe6fe2ab141c58a6Devang Patel  char Filler::ID = 0;
8520117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke} // end of anonymous namespace
8620117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
877c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner/// createSparcDelaySlotFillerPass - Returns a pass that fills in delay
887c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner/// slots in Sparc MachineFunctions
8920117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke///
907c90f73a1b06040d971a3dd95a491031ae6238d5Chris LattnerFunctionPass *llvm::createSparcDelaySlotFillerPass(TargetMachine &tm) {
917c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner  return new Filler(tm);
9220117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke}
9320117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke
9420117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke/// runOnMachineBasicBlock - Fill in delay slots for the given basic block.
9571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju/// We assume there is only one delay slot per delayed instruction.
9620117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke///
977c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattnerbool Filler::runOnMachineBasicBlock(MachineBasicBlock &MBB) {
980f51cc1759e2162485b5f9ee57b3b5bc8f5c6759Brian Gaeke  bool Changed = false;
9971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
1007c90f73a1b06040d971a3dd95a491031ae6238d5Chris Lattner  for (MachineBasicBlock::iterator I = MBB.begin(); I != MBB.end(); ++I)
101749c6f6b5ed301c84aac562e414486549d7b98ebChris Lattner    if (I->getDesc().hasDelaySlot()) {
10271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      MachineBasicBlock::iterator D = MBB.end();
10320117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke      MachineBasicBlock::iterator J = I;
10471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
10571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      if (!DisableDelaySlotFiller)
10671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        D = findDelayInstr(MBB, I);
10771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
10820117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke      ++FilledSlots;
1090f51cc1759e2162485b5f9ee57b3b5bc8f5c6759Brian Gaeke      Changed = true;
11071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
11171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      if (D == MBB.end())
11271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        BuildMI(MBB, ++J, I->getDebugLoc(), TII->get(SP::NOP));
11371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      else
11471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        MBB.splice(++J, &MBB, D);
11520117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke    }
1160f51cc1759e2162485b5f9ee57b3b5bc8f5c6759Brian Gaeke  return Changed;
11720117102c2e10fa2c0fa74965894e28751a3df34Brian Gaeke}
11871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
11971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman GovindarajuMachineBasicBlock::iterator
12071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman GovindarajuFiller::findDelayInstr(MachineBasicBlock &MBB,
12171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                       MachineBasicBlock::iterator slot)
12271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju{
12371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  SmallSet<unsigned, 32> RegDefs;
12471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  SmallSet<unsigned, 32> RegUses;
12571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  bool sawLoad = false;
12671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  bool sawStore = false;
12771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
12871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  MachineBasicBlock::iterator I = slot;
12971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
13071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  if (slot->getOpcode() == SP::RET)
13171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    return MBB.end();
13271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
13371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  if (slot->getOpcode() == SP::RETL) {
13471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    --I;
13571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (I->getOpcode() != SP::RESTORErr)
13671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      return MBB.end();
13771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    //change retl to ret
13871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    slot->setDesc(TII->get(SP::RET));
13971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    return I;
14071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  }
14171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
14271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  //Call's delay filler can def some of call's uses.
14371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  if (slot->getDesc().isCall())
14471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    insertCallUses(slot, RegUses);
14571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  else
14671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    insertDefsUses(slot, RegDefs, RegUses);
14771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
14871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  bool done = false;
14971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
15071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  while (!done) {
15171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    done = (I == MBB.begin());
15271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
15371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (!done)
15471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      --I;
15571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
15671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    // skip debug value
15771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (I->isDebugValue())
15871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      continue;
15971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
16071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
16171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (I->hasUnmodeledSideEffects()
16271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        || I->isInlineAsm()
16371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        || I->isLabel()
16471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        || I->getDesc().hasDelaySlot()
16571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        || isDelayFiller(MBB, I))
16671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      break;
16771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
16871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (delayHasHazard(I, sawLoad, sawStore, RegDefs, RegUses)) {
16971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      insertDefsUses(I, RegDefs, RegUses);
17071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      continue;
17171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    }
17271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
17371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    return I;
17471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  }
17571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  return MBB.end();
17671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju}
17771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
17871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindarajubool Filler::delayHasHazard(MachineBasicBlock::iterator candidate,
17971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                            bool &sawLoad,
18071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                            bool &sawStore,
18171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                            SmallSet<unsigned, 32> &RegDefs,
18271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                            SmallSet<unsigned, 32> &RegUses)
18371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju{
18471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
18571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  if (candidate->getDesc().mayLoad()) {
18671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    sawLoad = true;
18771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (sawStore)
18871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      return true;
18971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  }
19071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
19171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  if (candidate->getDesc().mayStore()) {
19271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (sawStore)
19371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      return true;
19471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    sawStore = true;
19571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (sawLoad)
19671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      return true;
19771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  }
19871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
19971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  for (unsigned i = 0, e = candidate->getNumOperands(); i!= e; ++i) {
20071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    const MachineOperand &MO = candidate->getOperand(i);
20171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (!MO.isReg())
20271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      continue; // skip
20371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
20471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    unsigned Reg = MO.getReg();
20571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
20671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (MO.isDef()) {
20771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      //check whether Reg is defined or used before delay slot.
20871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      if (IsRegInSet(RegDefs, Reg) || IsRegInSet(RegUses, Reg))
20971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        return true;
21071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    }
21171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (MO.isUse()) {
21271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      //check whether Reg is defined before delay slot.
21371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      if (IsRegInSet(RegDefs, Reg))
21471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        return true;
21571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    }
21671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  }
21771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  return false;
21871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju}
21971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
22071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
22171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindarajuvoid Filler::insertCallUses(MachineBasicBlock::iterator MI,
22271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                            SmallSet<unsigned, 32>& RegUses)
22371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju{
22471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
22571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  switch(MI->getOpcode()) {
22671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  default: llvm_unreachable("Unknown opcode.");
22771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  case SP::CALL: break;
22871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  case SP::JMPLrr:
22971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  case SP::JMPLri:
23071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    assert(MI->getNumOperands() >= 2);
23171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    const MachineOperand &Reg = MI->getOperand(0);
23271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    assert(Reg.isReg() && "JMPL first operand is not a register.");
23371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    assert(Reg.isUse() && "JMPL first operand is not a use.");
23471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    RegUses.insert(Reg.getReg());
23571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
23671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    const MachineOperand &RegOrImm = MI->getOperand(1);
23771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (RegOrImm.isImm())
23871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju        break;
23971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    assert(RegOrImm.isReg() && "JMPLrr second operand is not a register.");
24071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    assert(RegOrImm.isUse() && "JMPLrr second operand is not a use.");
24171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    RegUses.insert(RegOrImm.getReg());
24271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    break;
24371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  }
24471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju}
24571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
24671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju//Insert Defs and Uses of MI into the sets RegDefs and RegUses.
24771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindarajuvoid Filler::insertDefsUses(MachineBasicBlock::iterator MI,
24871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                            SmallSet<unsigned, 32>& RegDefs,
24971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                            SmallSet<unsigned, 32>& RegUses)
25071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju{
25171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
25271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    const MachineOperand &MO = MI->getOperand(i);
25371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (!MO.isReg())
25471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      continue;
25571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
25671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    unsigned Reg = MO.getReg();
25771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (Reg == 0)
25871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      continue;
25971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (MO.isDef())
26071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      RegDefs.insert(Reg);
26171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (MO.isUse())
26271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      RegUses.insert(Reg);
26371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
26471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  }
26571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju}
26671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
26771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju//returns true if the Reg or its alias is in the RegSet.
26871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindarajubool Filler::IsRegInSet(SmallSet<unsigned, 32>& RegSet, unsigned Reg)
26971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju{
27071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  if (RegSet.count(Reg))
27171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    return true;
27271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  // check Aliased Registers
27371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  for (const unsigned *Alias = TM.getRegisterInfo()->getAliasSet(Reg);
27471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju       *Alias; ++ Alias)
27571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    if (RegSet.count(*Alias))
27671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju      return true;
27771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
27871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  return false;
27971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju}
28071e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju
28171e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju// return true if the candidate is a delay filler.
28271e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindarajubool Filler::isDelayFiller(MachineBasicBlock &MBB,
28371e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju                           MachineBasicBlock::iterator candidate)
28471e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju{
28571e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  if (candidate == MBB.begin())
28671e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju    return false;
28771e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  const TargetInstrDesc &prevdesc = (--candidate)->getDesc();
28871e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju  return prevdesc.hasDelaySlot();
28971e39dac0ce9676dd3d0a92164167e18499d40faVenkatraman Govindaraju}
290