From: Jakob Stoklund Olesen Date: Wed, 19 May 2010 20:36:22 +0000 (+0000) Subject: Add MachineInstr::readsVirtualRegister() in preparation for proper handling of X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=7ebc4d63db05ac214d36bc01b4d60adadaf923e5;p=oota-llvm.git Add MachineInstr::readsVirtualRegister() in preparation for proper handling of partial redefines. We are going to treat a partial redefine of a virtual register as a read-modify-write: %reg1024:6 = OP Unless the register is fully clobbered: %reg1024:6 = OP, %reg1024 MachineInstr::readsVirtualRegister() knows the difference. The first case is a read, the second isn't. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@104149 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/include/llvm/CodeGen/MachineInstr.h b/include/llvm/CodeGen/MachineInstr.h index eefbd36daae..ffec00fd8cf 100644 --- a/include/llvm/CodeGen/MachineInstr.h +++ b/include/llvm/CodeGen/MachineInstr.h @@ -230,10 +230,17 @@ public: /// readsRegister - Return true if the MachineInstr reads the specified /// register. If TargetRegisterInfo is passed, then it also checks if there /// is a read of a super-register. + /// This does not count partial redefines of virtual registers as reads: + /// %reg1024:6 = OP. bool readsRegister(unsigned Reg, const TargetRegisterInfo *TRI = NULL) const { return findRegisterUseOperandIdx(Reg, false, TRI) != -1; } + /// readsVirtualRegister - Return true if the MachineInstr reads the specified + /// virtual register. Take into account that a partial define is a + /// read-modify-write operation. + bool readsVirtualRegister(unsigned Reg) const; + /// killsRegister - Return true if the MachineInstr kills the specified /// register. If TargetRegisterInfo is passed, then it also checks if there is /// a kill of a super-register. diff --git a/lib/CodeGen/MachineInstr.cpp b/lib/CodeGen/MachineInstr.cpp index d909fb0ef3e..553b13938c9 100644 --- a/lib/CodeGen/MachineInstr.cpp +++ b/lib/CodeGen/MachineInstr.cpp @@ -781,7 +781,30 @@ int MachineInstr::findRegisterUseOperandIdx(unsigned Reg, bool isKill, } return -1; } - + +/// readsVirtualRegister - Return true if the MachineInstr reads the specified +/// virtual register. Take into account that a partial define is a +/// read-modify-write operation. +bool MachineInstr::readsVirtualRegister(unsigned Reg) const { + bool PartDef = false; // Partial redefine + bool FullDef = false; // Full define + + for (unsigned i = 0, e = getNumOperands(); i != e; ++i) { + const MachineOperand &MO = getOperand(i); + if (!MO.isReg() || MO.getReg() != Reg) + continue; + if (MO.isUse()) + return true; + if (MO.getSubReg()) + PartDef = true; + else + FullDef = true; + } + // A partial register definition causes a read unless the full register is + // also defined. + return PartDef && !FullDef; +} + /// findRegisterDefOperandIdx() - Returns the operand index that is a def of /// the specified register or -1 if it is not found. If isDead is true, defs /// that are not dead are skipped. If TargetRegisterInfo is non-null, then it