xref: /minix3/external/bsd/llvm/dist/llvm/lib/CodeGen/MachineInstrBundle.cpp (revision 0a6a1f1d05b60e214de2f05a7310ddd1f0e590e7)
1f4a2713aSLionel Sambuc //===-- lib/CodeGen/MachineInstrBundle.cpp --------------------------------===//
2f4a2713aSLionel Sambuc //
3f4a2713aSLionel Sambuc //                     The LLVM Compiler Infrastructure
4f4a2713aSLionel Sambuc //
5f4a2713aSLionel Sambuc // This file is distributed under the University of Illinois Open Source
6f4a2713aSLionel Sambuc // License. See LICENSE.TXT for details.
7f4a2713aSLionel Sambuc //
8f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
9f4a2713aSLionel Sambuc 
10f4a2713aSLionel Sambuc #include "llvm/CodeGen/MachineInstrBundle.h"
11f4a2713aSLionel Sambuc #include "llvm/ADT/SmallSet.h"
12f4a2713aSLionel Sambuc #include "llvm/ADT/SmallVector.h"
13f4a2713aSLionel Sambuc #include "llvm/CodeGen/MachineFunctionPass.h"
14f4a2713aSLionel Sambuc #include "llvm/CodeGen/MachineInstrBuilder.h"
15f4a2713aSLionel Sambuc #include "llvm/CodeGen/Passes.h"
16f4a2713aSLionel Sambuc #include "llvm/Target/TargetInstrInfo.h"
17f4a2713aSLionel Sambuc #include "llvm/Target/TargetMachine.h"
18f4a2713aSLionel Sambuc #include "llvm/Target/TargetRegisterInfo.h"
19*0a6a1f1dSLionel Sambuc #include "llvm/Target/TargetSubtargetInfo.h"
20f4a2713aSLionel Sambuc using namespace llvm;
21f4a2713aSLionel Sambuc 
22f4a2713aSLionel Sambuc namespace {
23f4a2713aSLionel Sambuc   class UnpackMachineBundles : public MachineFunctionPass {
24f4a2713aSLionel Sambuc   public:
25f4a2713aSLionel Sambuc     static char ID; // Pass identification
UnpackMachineBundles()26f4a2713aSLionel Sambuc     UnpackMachineBundles() : MachineFunctionPass(ID) {
27f4a2713aSLionel Sambuc       initializeUnpackMachineBundlesPass(*PassRegistry::getPassRegistry());
28f4a2713aSLionel Sambuc     }
29f4a2713aSLionel Sambuc 
30*0a6a1f1dSLionel Sambuc     bool runOnMachineFunction(MachineFunction &MF) override;
31f4a2713aSLionel Sambuc   };
32f4a2713aSLionel Sambuc } // end anonymous namespace
33f4a2713aSLionel Sambuc 
34f4a2713aSLionel Sambuc char UnpackMachineBundles::ID = 0;
35f4a2713aSLionel Sambuc char &llvm::UnpackMachineBundlesID = UnpackMachineBundles::ID;
36f4a2713aSLionel Sambuc INITIALIZE_PASS(UnpackMachineBundles, "unpack-mi-bundles",
37f4a2713aSLionel Sambuc                 "Unpack machine instruction bundles", false, false)
38f4a2713aSLionel Sambuc 
runOnMachineFunction(MachineFunction & MF)39f4a2713aSLionel Sambuc bool UnpackMachineBundles::runOnMachineFunction(MachineFunction &MF) {
40f4a2713aSLionel Sambuc   bool Changed = false;
41f4a2713aSLionel Sambuc   for (MachineFunction::iterator I = MF.begin(), E = MF.end(); I != E; ++I) {
42f4a2713aSLionel Sambuc     MachineBasicBlock *MBB = &*I;
43f4a2713aSLionel Sambuc 
44f4a2713aSLionel Sambuc     for (MachineBasicBlock::instr_iterator MII = MBB->instr_begin(),
45f4a2713aSLionel Sambuc            MIE = MBB->instr_end(); MII != MIE; ) {
46f4a2713aSLionel Sambuc       MachineInstr *MI = &*MII;
47f4a2713aSLionel Sambuc 
48f4a2713aSLionel Sambuc       // Remove BUNDLE instruction and the InsideBundle flags from bundled
49f4a2713aSLionel Sambuc       // instructions.
50f4a2713aSLionel Sambuc       if (MI->isBundle()) {
51f4a2713aSLionel Sambuc         while (++MII != MIE && MII->isBundledWithPred()) {
52f4a2713aSLionel Sambuc           MII->unbundleFromPred();
53f4a2713aSLionel Sambuc           for (unsigned i = 0, e = MII->getNumOperands(); i != e; ++i) {
54f4a2713aSLionel Sambuc             MachineOperand &MO = MII->getOperand(i);
55f4a2713aSLionel Sambuc             if (MO.isReg() && MO.isInternalRead())
56f4a2713aSLionel Sambuc               MO.setIsInternalRead(false);
57f4a2713aSLionel Sambuc           }
58f4a2713aSLionel Sambuc         }
59f4a2713aSLionel Sambuc         MI->eraseFromParent();
60f4a2713aSLionel Sambuc 
61f4a2713aSLionel Sambuc         Changed = true;
62f4a2713aSLionel Sambuc         continue;
63f4a2713aSLionel Sambuc       }
64f4a2713aSLionel Sambuc 
65f4a2713aSLionel Sambuc       ++MII;
66f4a2713aSLionel Sambuc     }
67f4a2713aSLionel Sambuc   }
68f4a2713aSLionel Sambuc 
69f4a2713aSLionel Sambuc   return Changed;
70f4a2713aSLionel Sambuc }
71f4a2713aSLionel Sambuc 
72f4a2713aSLionel Sambuc 
73f4a2713aSLionel Sambuc namespace {
74f4a2713aSLionel Sambuc   class FinalizeMachineBundles : public MachineFunctionPass {
75f4a2713aSLionel Sambuc   public:
76f4a2713aSLionel Sambuc     static char ID; // Pass identification
FinalizeMachineBundles()77f4a2713aSLionel Sambuc     FinalizeMachineBundles() : MachineFunctionPass(ID) {
78f4a2713aSLionel Sambuc       initializeFinalizeMachineBundlesPass(*PassRegistry::getPassRegistry());
79f4a2713aSLionel Sambuc     }
80f4a2713aSLionel Sambuc 
81*0a6a1f1dSLionel Sambuc     bool runOnMachineFunction(MachineFunction &MF) override;
82f4a2713aSLionel Sambuc   };
83f4a2713aSLionel Sambuc } // end anonymous namespace
84f4a2713aSLionel Sambuc 
85f4a2713aSLionel Sambuc char FinalizeMachineBundles::ID = 0;
86f4a2713aSLionel Sambuc char &llvm::FinalizeMachineBundlesID = FinalizeMachineBundles::ID;
87f4a2713aSLionel Sambuc INITIALIZE_PASS(FinalizeMachineBundles, "finalize-mi-bundles",
88f4a2713aSLionel Sambuc                 "Finalize machine instruction bundles", false, false)
89f4a2713aSLionel Sambuc 
runOnMachineFunction(MachineFunction & MF)90f4a2713aSLionel Sambuc bool FinalizeMachineBundles::runOnMachineFunction(MachineFunction &MF) {
91f4a2713aSLionel Sambuc   return llvm::finalizeBundles(MF);
92f4a2713aSLionel Sambuc }
93f4a2713aSLionel Sambuc 
94f4a2713aSLionel Sambuc 
95f4a2713aSLionel Sambuc /// finalizeBundle - Finalize a machine instruction bundle which includes
96f4a2713aSLionel Sambuc /// a sequence of instructions starting from FirstMI to LastMI (exclusive).
97f4a2713aSLionel Sambuc /// This routine adds a BUNDLE instruction to represent the bundle, it adds
98f4a2713aSLionel Sambuc /// IsInternalRead markers to MachineOperands which are defined inside the
99f4a2713aSLionel Sambuc /// bundle, and it copies externally visible defs and uses to the BUNDLE
100f4a2713aSLionel Sambuc /// instruction.
finalizeBundle(MachineBasicBlock & MBB,MachineBasicBlock::instr_iterator FirstMI,MachineBasicBlock::instr_iterator LastMI)101f4a2713aSLionel Sambuc void llvm::finalizeBundle(MachineBasicBlock &MBB,
102f4a2713aSLionel Sambuc                           MachineBasicBlock::instr_iterator FirstMI,
103f4a2713aSLionel Sambuc                           MachineBasicBlock::instr_iterator LastMI) {
104f4a2713aSLionel Sambuc   assert(FirstMI != LastMI && "Empty bundle?");
105f4a2713aSLionel Sambuc   MIBundleBuilder Bundle(MBB, FirstMI, LastMI);
106f4a2713aSLionel Sambuc 
107*0a6a1f1dSLionel Sambuc   MachineFunction &MF = *MBB.getParent();
108*0a6a1f1dSLionel Sambuc   const TargetInstrInfo *TII = MF.getSubtarget().getInstrInfo();
109*0a6a1f1dSLionel Sambuc   const TargetRegisterInfo *TRI = MF.getSubtarget().getRegisterInfo();
110f4a2713aSLionel Sambuc 
111*0a6a1f1dSLionel Sambuc   MachineInstrBuilder MIB =
112*0a6a1f1dSLionel Sambuc       BuildMI(MF, FirstMI->getDebugLoc(), TII->get(TargetOpcode::BUNDLE));
113f4a2713aSLionel Sambuc   Bundle.prepend(MIB);
114f4a2713aSLionel Sambuc 
115f4a2713aSLionel Sambuc   SmallVector<unsigned, 32> LocalDefs;
116f4a2713aSLionel Sambuc   SmallSet<unsigned, 32> LocalDefSet;
117f4a2713aSLionel Sambuc   SmallSet<unsigned, 8> DeadDefSet;
118f4a2713aSLionel Sambuc   SmallSet<unsigned, 16> KilledDefSet;
119f4a2713aSLionel Sambuc   SmallVector<unsigned, 8> ExternUses;
120f4a2713aSLionel Sambuc   SmallSet<unsigned, 8> ExternUseSet;
121f4a2713aSLionel Sambuc   SmallSet<unsigned, 8> KilledUseSet;
122f4a2713aSLionel Sambuc   SmallSet<unsigned, 8> UndefUseSet;
123f4a2713aSLionel Sambuc   SmallVector<MachineOperand*, 4> Defs;
124f4a2713aSLionel Sambuc   for (; FirstMI != LastMI; ++FirstMI) {
125f4a2713aSLionel Sambuc     for (unsigned i = 0, e = FirstMI->getNumOperands(); i != e; ++i) {
126f4a2713aSLionel Sambuc       MachineOperand &MO = FirstMI->getOperand(i);
127f4a2713aSLionel Sambuc       if (!MO.isReg())
128f4a2713aSLionel Sambuc         continue;
129f4a2713aSLionel Sambuc       if (MO.isDef()) {
130f4a2713aSLionel Sambuc         Defs.push_back(&MO);
131f4a2713aSLionel Sambuc         continue;
132f4a2713aSLionel Sambuc       }
133f4a2713aSLionel Sambuc 
134f4a2713aSLionel Sambuc       unsigned Reg = MO.getReg();
135f4a2713aSLionel Sambuc       if (!Reg)
136f4a2713aSLionel Sambuc         continue;
137f4a2713aSLionel Sambuc       assert(TargetRegisterInfo::isPhysicalRegister(Reg));
138f4a2713aSLionel Sambuc       if (LocalDefSet.count(Reg)) {
139f4a2713aSLionel Sambuc         MO.setIsInternalRead();
140f4a2713aSLionel Sambuc         if (MO.isKill())
141f4a2713aSLionel Sambuc           // Internal def is now killed.
142f4a2713aSLionel Sambuc           KilledDefSet.insert(Reg);
143f4a2713aSLionel Sambuc       } else {
144*0a6a1f1dSLionel Sambuc         if (ExternUseSet.insert(Reg).second) {
145f4a2713aSLionel Sambuc           ExternUses.push_back(Reg);
146f4a2713aSLionel Sambuc           if (MO.isUndef())
147f4a2713aSLionel Sambuc             UndefUseSet.insert(Reg);
148f4a2713aSLionel Sambuc         }
149f4a2713aSLionel Sambuc         if (MO.isKill())
150f4a2713aSLionel Sambuc           // External def is now killed.
151f4a2713aSLionel Sambuc           KilledUseSet.insert(Reg);
152f4a2713aSLionel Sambuc       }
153f4a2713aSLionel Sambuc     }
154f4a2713aSLionel Sambuc 
155f4a2713aSLionel Sambuc     for (unsigned i = 0, e = Defs.size(); i != e; ++i) {
156f4a2713aSLionel Sambuc       MachineOperand &MO = *Defs[i];
157f4a2713aSLionel Sambuc       unsigned Reg = MO.getReg();
158f4a2713aSLionel Sambuc       if (!Reg)
159f4a2713aSLionel Sambuc         continue;
160f4a2713aSLionel Sambuc 
161*0a6a1f1dSLionel Sambuc       if (LocalDefSet.insert(Reg).second) {
162f4a2713aSLionel Sambuc         LocalDefs.push_back(Reg);
163f4a2713aSLionel Sambuc         if (MO.isDead()) {
164f4a2713aSLionel Sambuc           DeadDefSet.insert(Reg);
165f4a2713aSLionel Sambuc         }
166f4a2713aSLionel Sambuc       } else {
167f4a2713aSLionel Sambuc         // Re-defined inside the bundle, it's no longer killed.
168f4a2713aSLionel Sambuc         KilledDefSet.erase(Reg);
169f4a2713aSLionel Sambuc         if (!MO.isDead())
170f4a2713aSLionel Sambuc           // Previously defined but dead.
171f4a2713aSLionel Sambuc           DeadDefSet.erase(Reg);
172f4a2713aSLionel Sambuc       }
173f4a2713aSLionel Sambuc 
174f4a2713aSLionel Sambuc       if (!MO.isDead()) {
175f4a2713aSLionel Sambuc         for (MCSubRegIterator SubRegs(Reg, TRI); SubRegs.isValid(); ++SubRegs) {
176f4a2713aSLionel Sambuc           unsigned SubReg = *SubRegs;
177*0a6a1f1dSLionel Sambuc           if (LocalDefSet.insert(SubReg).second)
178f4a2713aSLionel Sambuc             LocalDefs.push_back(SubReg);
179f4a2713aSLionel Sambuc         }
180f4a2713aSLionel Sambuc       }
181f4a2713aSLionel Sambuc     }
182f4a2713aSLionel Sambuc 
183f4a2713aSLionel Sambuc     Defs.clear();
184f4a2713aSLionel Sambuc   }
185f4a2713aSLionel Sambuc 
186f4a2713aSLionel Sambuc   SmallSet<unsigned, 32> Added;
187f4a2713aSLionel Sambuc   for (unsigned i = 0, e = LocalDefs.size(); i != e; ++i) {
188f4a2713aSLionel Sambuc     unsigned Reg = LocalDefs[i];
189*0a6a1f1dSLionel Sambuc     if (Added.insert(Reg).second) {
190f4a2713aSLionel Sambuc       // If it's not live beyond end of the bundle, mark it dead.
191f4a2713aSLionel Sambuc       bool isDead = DeadDefSet.count(Reg) || KilledDefSet.count(Reg);
192f4a2713aSLionel Sambuc       MIB.addReg(Reg, getDefRegState(true) | getDeadRegState(isDead) |
193f4a2713aSLionel Sambuc                  getImplRegState(true));
194f4a2713aSLionel Sambuc     }
195f4a2713aSLionel Sambuc   }
196f4a2713aSLionel Sambuc 
197f4a2713aSLionel Sambuc   for (unsigned i = 0, e = ExternUses.size(); i != e; ++i) {
198f4a2713aSLionel Sambuc     unsigned Reg = ExternUses[i];
199f4a2713aSLionel Sambuc     bool isKill = KilledUseSet.count(Reg);
200f4a2713aSLionel Sambuc     bool isUndef = UndefUseSet.count(Reg);
201f4a2713aSLionel Sambuc     MIB.addReg(Reg, getKillRegState(isKill) | getUndefRegState(isUndef) |
202f4a2713aSLionel Sambuc                getImplRegState(true));
203f4a2713aSLionel Sambuc   }
204f4a2713aSLionel Sambuc }
205f4a2713aSLionel Sambuc 
206f4a2713aSLionel Sambuc /// finalizeBundle - Same functionality as the previous finalizeBundle except
207f4a2713aSLionel Sambuc /// the last instruction in the bundle is not provided as an input. This is
208f4a2713aSLionel Sambuc /// used in cases where bundles are pre-determined by marking instructions
209f4a2713aSLionel Sambuc /// with 'InsideBundle' marker. It returns the MBB instruction iterator that
210f4a2713aSLionel Sambuc /// points to the end of the bundle.
211f4a2713aSLionel Sambuc MachineBasicBlock::instr_iterator
finalizeBundle(MachineBasicBlock & MBB,MachineBasicBlock::instr_iterator FirstMI)212f4a2713aSLionel Sambuc llvm::finalizeBundle(MachineBasicBlock &MBB,
213f4a2713aSLionel Sambuc                      MachineBasicBlock::instr_iterator FirstMI) {
214f4a2713aSLionel Sambuc   MachineBasicBlock::instr_iterator E = MBB.instr_end();
215*0a6a1f1dSLionel Sambuc   MachineBasicBlock::instr_iterator LastMI = std::next(FirstMI);
216f4a2713aSLionel Sambuc   while (LastMI != E && LastMI->isInsideBundle())
217f4a2713aSLionel Sambuc     ++LastMI;
218f4a2713aSLionel Sambuc   finalizeBundle(MBB, FirstMI, LastMI);
219f4a2713aSLionel Sambuc   return LastMI;
220f4a2713aSLionel Sambuc }
221f4a2713aSLionel Sambuc 
222f4a2713aSLionel Sambuc /// finalizeBundles - Finalize instruction bundles in the specified
223f4a2713aSLionel Sambuc /// MachineFunction. Return true if any bundles are finalized.
finalizeBundles(MachineFunction & MF)224f4a2713aSLionel Sambuc bool llvm::finalizeBundles(MachineFunction &MF) {
225f4a2713aSLionel Sambuc   bool Changed = false;
226f4a2713aSLionel Sambuc   for (MachineFunction::iterator I = MF.begin(), E = MF.end(); I != E; ++I) {
227f4a2713aSLionel Sambuc     MachineBasicBlock &MBB = *I;
228f4a2713aSLionel Sambuc     MachineBasicBlock::instr_iterator MII = MBB.instr_begin();
229f4a2713aSLionel Sambuc     MachineBasicBlock::instr_iterator MIE = MBB.instr_end();
230f4a2713aSLionel Sambuc     if (MII == MIE)
231f4a2713aSLionel Sambuc       continue;
232f4a2713aSLionel Sambuc     assert(!MII->isInsideBundle() &&
233f4a2713aSLionel Sambuc            "First instr cannot be inside bundle before finalization!");
234f4a2713aSLionel Sambuc 
235f4a2713aSLionel Sambuc     for (++MII; MII != MIE; ) {
236f4a2713aSLionel Sambuc       if (!MII->isInsideBundle())
237f4a2713aSLionel Sambuc         ++MII;
238f4a2713aSLionel Sambuc       else {
239*0a6a1f1dSLionel Sambuc         MII = finalizeBundle(MBB, std::prev(MII));
240f4a2713aSLionel Sambuc         Changed = true;
241f4a2713aSLionel Sambuc       }
242f4a2713aSLionel Sambuc     }
243f4a2713aSLionel Sambuc   }
244f4a2713aSLionel Sambuc 
245f4a2713aSLionel Sambuc   return Changed;
246f4a2713aSLionel Sambuc }
247f4a2713aSLionel Sambuc 
248f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
249f4a2713aSLionel Sambuc // MachineOperand iterator
250f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
251f4a2713aSLionel Sambuc 
252f4a2713aSLionel Sambuc MachineOperandIteratorBase::VirtRegInfo
analyzeVirtReg(unsigned Reg,SmallVectorImpl<std::pair<MachineInstr *,unsigned>> * Ops)253f4a2713aSLionel Sambuc MachineOperandIteratorBase::analyzeVirtReg(unsigned Reg,
254f4a2713aSLionel Sambuc                     SmallVectorImpl<std::pair<MachineInstr*, unsigned> > *Ops) {
255f4a2713aSLionel Sambuc   VirtRegInfo RI = { false, false, false };
256f4a2713aSLionel Sambuc   for(; isValid(); ++*this) {
257f4a2713aSLionel Sambuc     MachineOperand &MO = deref();
258f4a2713aSLionel Sambuc     if (!MO.isReg() || MO.getReg() != Reg)
259f4a2713aSLionel Sambuc       continue;
260f4a2713aSLionel Sambuc 
261f4a2713aSLionel Sambuc     // Remember each (MI, OpNo) that refers to Reg.
262f4a2713aSLionel Sambuc     if (Ops)
263f4a2713aSLionel Sambuc       Ops->push_back(std::make_pair(MO.getParent(), getOperandNo()));
264f4a2713aSLionel Sambuc 
265f4a2713aSLionel Sambuc     // Both defs and uses can read virtual registers.
266f4a2713aSLionel Sambuc     if (MO.readsReg()) {
267f4a2713aSLionel Sambuc       RI.Reads = true;
268f4a2713aSLionel Sambuc       if (MO.isDef())
269f4a2713aSLionel Sambuc         RI.Tied = true;
270f4a2713aSLionel Sambuc     }
271f4a2713aSLionel Sambuc 
272f4a2713aSLionel Sambuc     // Only defs can write.
273f4a2713aSLionel Sambuc     if (MO.isDef())
274f4a2713aSLionel Sambuc       RI.Writes = true;
275f4a2713aSLionel Sambuc     else if (!RI.Tied && MO.getParent()->isRegTiedToDefOperand(getOperandNo()))
276f4a2713aSLionel Sambuc       RI.Tied = true;
277f4a2713aSLionel Sambuc   }
278f4a2713aSLionel Sambuc   return RI;
279f4a2713aSLionel Sambuc }
280f4a2713aSLionel Sambuc 
281f4a2713aSLionel Sambuc MachineOperandIteratorBase::PhysRegInfo
analyzePhysReg(unsigned Reg,const TargetRegisterInfo * TRI)282f4a2713aSLionel Sambuc MachineOperandIteratorBase::analyzePhysReg(unsigned Reg,
283f4a2713aSLionel Sambuc                                            const TargetRegisterInfo *TRI) {
284f4a2713aSLionel Sambuc   bool AllDefsDead = true;
285f4a2713aSLionel Sambuc   PhysRegInfo PRI = {false, false, false, false, false, false};
286f4a2713aSLionel Sambuc 
287f4a2713aSLionel Sambuc   assert(TargetRegisterInfo::isPhysicalRegister(Reg) &&
288f4a2713aSLionel Sambuc          "analyzePhysReg not given a physical register!");
289f4a2713aSLionel Sambuc   for (; isValid(); ++*this) {
290f4a2713aSLionel Sambuc     MachineOperand &MO = deref();
291f4a2713aSLionel Sambuc 
292f4a2713aSLionel Sambuc     if (MO.isRegMask() && MO.clobbersPhysReg(Reg))
293f4a2713aSLionel Sambuc       PRI.Clobbers = true;    // Regmask clobbers Reg.
294f4a2713aSLionel Sambuc 
295f4a2713aSLionel Sambuc     if (!MO.isReg())
296f4a2713aSLionel Sambuc       continue;
297f4a2713aSLionel Sambuc 
298f4a2713aSLionel Sambuc     unsigned MOReg = MO.getReg();
299f4a2713aSLionel Sambuc     if (!MOReg || !TargetRegisterInfo::isPhysicalRegister(MOReg))
300f4a2713aSLionel Sambuc       continue;
301f4a2713aSLionel Sambuc 
302f4a2713aSLionel Sambuc     bool IsRegOrSuperReg = MOReg == Reg || TRI->isSubRegister(MOReg, Reg);
303f4a2713aSLionel Sambuc     bool IsRegOrOverlapping = MOReg == Reg || TRI->regsOverlap(MOReg, Reg);
304f4a2713aSLionel Sambuc 
305f4a2713aSLionel Sambuc     if (IsRegOrSuperReg && MO.readsReg()) {
306f4a2713aSLionel Sambuc       // Reg or a super-reg is read, and perhaps killed also.
307f4a2713aSLionel Sambuc       PRI.Reads = true;
308f4a2713aSLionel Sambuc       PRI.Kills = MO.isKill();
309f4a2713aSLionel Sambuc     }
310f4a2713aSLionel Sambuc 
311f4a2713aSLionel Sambuc     if (IsRegOrOverlapping && MO.readsReg()) {
312f4a2713aSLionel Sambuc       PRI.ReadsOverlap = true;// Reg or an overlapping register is read.
313f4a2713aSLionel Sambuc     }
314f4a2713aSLionel Sambuc 
315f4a2713aSLionel Sambuc     if (!MO.isDef())
316f4a2713aSLionel Sambuc       continue;
317f4a2713aSLionel Sambuc 
318f4a2713aSLionel Sambuc     if (IsRegOrSuperReg) {
319f4a2713aSLionel Sambuc       PRI.Defines = true;     // Reg or a super-register is defined.
320f4a2713aSLionel Sambuc       if (!MO.isDead())
321f4a2713aSLionel Sambuc         AllDefsDead = false;
322f4a2713aSLionel Sambuc     }
323f4a2713aSLionel Sambuc     if (IsRegOrOverlapping)
324f4a2713aSLionel Sambuc       PRI.Clobbers = true;    // Reg or an overlapping reg is defined.
325f4a2713aSLionel Sambuc   }
326f4a2713aSLionel Sambuc 
327f4a2713aSLionel Sambuc   if (AllDefsDead && PRI.Defines)
328f4a2713aSLionel Sambuc     PRI.DefinesDead = true;   // Reg or super-register was defined and was dead.
329f4a2713aSLionel Sambuc 
330f4a2713aSLionel Sambuc   return PRI;
331f4a2713aSLionel Sambuc }
332