[CodeGen] Use MachineOperand::print in the MIRPrinter for MO_Register.

Work towards the unification of MIR and debug output by refactoring the
interfaces.

For MachineOperand::print, keep a simple version that can be easily called
from `dump()`, and a more complex one which will be called from both the
MIRPrinter and MachineInstr::print.

Add extra checks inside MachineOperand for detached operands (operands
with getParent() == nullptr).

https://reviews.llvm.org/D40836

* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/kill: ([^ ]+) ([^ ]+)<def> ([^ ]+)/kill: \1 def \2 \3/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/kill: ([^ ]+) ([^ ]+) ([^ ]+)<def>/kill: \1 \2 def \3/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/kill: def ([^ ]+) ([^ ]+) ([^ ]+)<def>/kill: def \1 \2 def \3/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/<def>//g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<kill>/killed \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<imp-use,kill>/implicit killed \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<dead>/dead \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<def[ ]*,[ ]*dead>/dead \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<imp-def[ ]*,[ ]*dead>/implicit-def dead \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<imp-def>/implicit-def \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<imp-use>/implicit \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<internal>/internal \1/g'
* find . \( -name "*.mir" -o -name "*.cpp" -o -name "*.h" -o -name "*.ll" -o -name "*.s" \) -type f -print0 | xargs -0 sed -i '' -E 's/([^ ]+)<undef>/undef \1/g'

llvm-svn: 320022
This commit is contained in:
Francis Visoiu Mistrih 2017-12-07 10:40:31 +00:00
parent 62ef18562b
commit a8a83d150f
331 changed files with 4206 additions and 4121 deletions

View File

@ -204,7 +204,7 @@ public:
const MDNode *Variable,
const MDNode *Expr);
/// Build and insert \p Res<def> = G_FRAME_INDEX \p Idx
/// Build and insert \p Res = G_FRAME_INDEX \p Idx
///
/// G_FRAME_INDEX materializes the address of an alloca value or other
/// stack-based object.
@ -215,7 +215,7 @@ public:
/// \return a MachineInstrBuilder for the newly created instruction.
MachineInstrBuilder buildFrameIndex(unsigned Res, int Idx);
/// Build and insert \p Res<def> = G_GLOBAL_VALUE \p GV
/// Build and insert \p Res = G_GLOBAL_VALUE \p GV
///
/// G_GLOBAL_VALUE materializes the address of the specified global
/// into \p Res.
@ -227,7 +227,7 @@ public:
/// \return a MachineInstrBuilder for the newly created instruction.
MachineInstrBuilder buildGlobalValue(unsigned Res, const GlobalValue *GV);
/// Build and insert \p Res<def> = G_ADD \p Op0, \p Op1
/// Build and insert \p Res = G_ADD \p Op0, \p Op1
///
/// G_ADD sets \p Res to the sum of integer parameters \p Op0 and \p Op1,
/// truncated to their width.
@ -245,7 +245,7 @@ public:
return buildAdd(Res, (getRegFromArg(UseArgs))...);
}
/// Build and insert \p Res<def> = G_SUB \p Op0, \p Op1
/// Build and insert \p Res = G_SUB \p Op0, \p Op1
///
/// G_SUB sets \p Res to the sum of integer parameters \p Op0 and \p Op1,
/// truncated to their width.
@ -258,7 +258,7 @@ public:
MachineInstrBuilder buildSub(unsigned Res, unsigned Op0,
unsigned Op1);
/// Build and insert \p Res<def> = G_MUL \p Op0, \p Op1
/// Build and insert \p Res = G_MUL \p Op0, \p Op1
///
/// G_MUL sets \p Res to the sum of integer parameters \p Op0 and \p Op1,
/// truncated to their width.
@ -271,7 +271,7 @@ public:
MachineInstrBuilder buildMul(unsigned Res, unsigned Op0,
unsigned Op1);
/// Build and insert \p Res<def> = G_GEP \p Op0, \p Op1
/// Build and insert \p Res = G_GEP \p Op0, \p Op1
///
/// G_GEP adds \p Op1 bytes to the pointer specified by \p Op0,
/// storing the resulting pointer in \p Res.
@ -285,7 +285,7 @@ public:
MachineInstrBuilder buildGEP(unsigned Res, unsigned Op0,
unsigned Op1);
/// Materialize and insert \p Res<def> = G_GEP \p Op0, (G_CONSTANT \p Value)
/// Materialize and insert \p Res = G_GEP \p Op0, (G_CONSTANT \p Value)
///
/// G_GEP adds \p Value bytes to the pointer specified by \p Op0,
/// storing the resulting pointer in \p Res. If \p Value is zero then no
@ -305,7 +305,7 @@ public:
const LLT &ValueTy,
uint64_t Value);
/// Build and insert \p Res<def> = G_PTR_MASK \p Op0, \p NumBits
/// Build and insert \p Res = G_PTR_MASK \p Op0, \p NumBits
///
/// G_PTR_MASK clears the low bits of a pointer operand without destroying its
/// pointer properties. This has the effect of rounding the address *down* to
@ -321,7 +321,7 @@ public:
MachineInstrBuilder buildPtrMask(unsigned Res, unsigned Op0,
uint32_t NumBits);
/// Build and insert \p Res<def>, \p CarryOut<def> = G_UADDE \p Op0,
/// Build and insert \p Res, \p CarryOut = G_UADDE \p Op0,
/// \p Op1, \p CarryIn
///
/// G_UADDE sets \p Res to \p Op0 + \p Op1 + \p CarryIn (truncated to the bit
@ -338,7 +338,7 @@ public:
MachineInstrBuilder buildUAdde(unsigned Res, unsigned CarryOut, unsigned Op0,
unsigned Op1, unsigned CarryIn);
/// Build and insert \p Res<def> = G_AND \p Op0, \p Op1
/// Build and insert \p Res = G_AND \p Op0, \p Op1
///
/// G_AND sets \p Res to the bitwise and of integer parameters \p Op0 and \p
/// Op1.
@ -355,7 +355,7 @@ public:
MachineInstrBuilder buildAnd(unsigned Res, unsigned Op0,
unsigned Op1);
/// Build and insert \p Res<def> = G_OR \p Op0, \p Op1
/// Build and insert \p Res = G_OR \p Op0, \p Op1
///
/// G_OR sets \p Res to the bitwise or of integer parameters \p Op0 and \p
/// Op1.
@ -367,7 +367,7 @@ public:
/// \return a MachineInstrBuilder for the newly created instruction.
MachineInstrBuilder buildOr(unsigned Res, unsigned Op0, unsigned Op1);
/// Build and insert \p Res<def> = G_ANYEXT \p Op0
/// Build and insert \p Res = G_ANYEXT \p Op0
///
/// G_ANYEXT produces a register of the specified width, with bits 0 to
/// sizeof(\p Ty) * 8 set to \p Op. The remaining bits are unspecified
@ -387,7 +387,7 @@ public:
return buildAnyExt(getDestFromArg(Res), getRegFromArg(Arg));
}
/// Build and insert \p Res<def> = G_SEXT \p Op
/// Build and insert \p Res = G_SEXT \p Op
///
/// G_SEXT produces a register of the specified width, with bits 0 to
/// sizeof(\p Ty) * 8 set to \p Op. The remaining bits are duplicated from the
@ -401,7 +401,7 @@ public:
/// \return The newly created instruction.
MachineInstrBuilder buildSExt(unsigned Res, unsigned Op);
/// Build and insert \p Res<def> = G_ZEXT \p Op
/// Build and insert \p Res = G_ZEXT \p Op
///
/// G_ZEXT produces a register of the specified width, with bits 0 to
/// sizeof(\p Ty) * 8 set to \p Op. The remaining bits are 0. For a vector
@ -415,7 +415,7 @@ public:
/// \return The newly created instruction.
MachineInstrBuilder buildZExt(unsigned Res, unsigned Op);
/// Build and insert \p Res<def> = G_SEXT \p Op, \p Res = G_TRUNC \p Op, or
/// Build and insert \p Res = G_SEXT \p Op, \p Res = G_TRUNC \p Op, or
/// \p Res = COPY \p Op depending on the differing sizes of \p Res and \p Op.
/// ///
/// \pre setBasicBlock or setMI must have been called.
@ -425,7 +425,7 @@ public:
/// \return The newly created instruction.
MachineInstrBuilder buildSExtOrTrunc(unsigned Res, unsigned Op);
/// Build and insert \p Res<def> = G_ZEXT \p Op, \p Res = G_TRUNC \p Op, or
/// Build and insert \p Res = G_ZEXT \p Op, \p Res = G_TRUNC \p Op, or
/// \p Res = COPY \p Op depending on the differing sizes of \p Res and \p Op.
/// ///
/// \pre setBasicBlock or setMI must have been called.
@ -435,7 +435,7 @@ public:
/// \return The newly created instruction.
MachineInstrBuilder buildZExtOrTrunc(unsigned Res, unsigned Op);
// Build and insert \p Res<def> = G_ANYEXT \p Op, \p Res = G_TRUNC \p Op, or
// Build and insert \p Res = G_ANYEXT \p Op, \p Res = G_TRUNC \p Op, or
/// \p Res = COPY \p Op depending on the differing sizes of \p Res and \p Op.
/// ///
/// \pre setBasicBlock or setMI must have been called.
@ -449,7 +449,7 @@ public:
}
MachineInstrBuilder buildAnyExtOrTrunc(unsigned Res, unsigned Op);
/// Build and insert \p Res<def> = \p ExtOpc, \p Res = G_TRUNC \p
/// Build and insert \p Res = \p ExtOpc, \p Res = G_TRUNC \p
/// Op, or \p Res = COPY \p Op depending on the differing sizes of \p Res and
/// \p Op.
/// ///
@ -534,7 +534,7 @@ public:
/// \return The newly created instruction.
MachineInstrBuilder buildFConstant(unsigned Res, const ConstantFP &Val);
/// Build and insert \p Res<def> = COPY Op
/// Build and insert \p Res = COPY Op
///
/// Register-to-register COPY sets \p Res to \p Op.
///
@ -547,7 +547,7 @@ public:
return buildCopy(getDestFromArg(Res), getRegFromArg(Src));
}
/// Build and insert `Res<def> = G_LOAD Addr, MMO`.
/// Build and insert `Res = G_LOAD Addr, MMO`.
///
/// Loads the value stored at \p Addr. Puts the result in \p Res.
///
@ -571,7 +571,7 @@ public:
MachineInstrBuilder buildStore(unsigned Val, unsigned Addr,
MachineMemOperand &MMO);
/// Build and insert `Res0<def>, ... = G_EXTRACT Src, Idx0`.
/// Build and insert `Res0, ... = G_EXTRACT Src, Idx0`.
///
/// \pre setBasicBlock or setMI must have been called.
/// \pre \p Res and \p Src must be generic virtual registers.
@ -598,7 +598,7 @@ public:
void buildSequence(unsigned Res, ArrayRef<unsigned> Ops,
ArrayRef<uint64_t> Indices);
/// Build and insert \p Res<def> = G_MERGE_VALUES \p Op0, ...
/// Build and insert \p Res = G_MERGE_VALUES \p Op0, ...
///
/// G_MERGE_VALUES combines the input elements contiguously into a larger
/// register.
@ -611,7 +611,7 @@ public:
/// \return a MachineInstrBuilder for the newly created instruction.
MachineInstrBuilder buildMerge(unsigned Res, ArrayRef<unsigned> Ops);
/// Build and insert \p Res0<def>, ... = G_UNMERGE_VALUES \p Op
/// Build and insert \p Res0, ... = G_UNMERGE_VALUES \p Op
///
/// G_UNMERGE_VALUES splits contiguous bits of the input into multiple
///
@ -639,7 +639,7 @@ public:
MachineInstrBuilder buildIntrinsic(Intrinsic::ID ID, unsigned Res,
bool HasSideEffects);
/// Build and insert \p Res<def> = G_FPTRUNC \p Op
/// Build and insert \p Res = G_FPTRUNC \p Op
///
/// G_FPTRUNC converts a floating-point value into one with a smaller type.
///
@ -651,7 +651,7 @@ public:
/// \return The newly created instruction.
MachineInstrBuilder buildFPTrunc(unsigned Res, unsigned Op);
/// Build and insert \p Res<def> = G_TRUNC \p Op
/// Build and insert \p Res = G_TRUNC \p Op
///
/// G_TRUNC extracts the low bits of a type. For a vector type each element is
/// truncated independently before being packed into the destination.
@ -711,7 +711,7 @@ public:
MachineInstrBuilder buildSelect(unsigned Res, unsigned Tst,
unsigned Op0, unsigned Op1);
/// Build and insert \p Res<def> = G_INSERT_VECTOR_ELT \p Val,
/// Build and insert \p Res = G_INSERT_VECTOR_ELT \p Val,
/// \p Elt, \p Idx
///
/// \pre setBasicBlock or setMI must have been called.
@ -724,7 +724,7 @@ public:
MachineInstrBuilder buildInsertVectorElement(unsigned Res, unsigned Val,
unsigned Elt, unsigned Idx);
/// Build and insert \p Res<def> = G_EXTRACT_VECTOR_ELT \p Val, \p Idx
/// Build and insert \p Res = G_EXTRACT_VECTOR_ELT \p Val, \p Idx
///
/// \pre setBasicBlock or setMI must have been called.
/// \pre \p Res must be a generic virtual register with scalar type.
@ -735,7 +735,7 @@ public:
MachineInstrBuilder buildExtractVectorElement(unsigned Res, unsigned Val,
unsigned Idx);
/// Build and insert `OldValRes<def> = G_ATOMIC_CMPXCHG Addr, CmpVal, NewVal,
/// Build and insert `OldValRes = G_ATOMIC_CMPXCHG Addr, CmpVal, NewVal,
/// MMO`.
///
/// Atomically replace the value at \p Addr with \p NewVal if it is currently

View File

@ -20,11 +20,11 @@
/// register.
///
/// X86 Example:
/// %ymm0<def> = ...
/// %xmm0<def> = ... (Kills %xmm0, all %xmm0s sub-registers, and %ymm0)
/// %ymm0 = ...
/// %xmm0 = ... (Kills %xmm0, all %xmm0s sub-registers, and %ymm0)
///
/// %ymm0<def> = ...
/// %xmm0<def> = ..., %ymm0<imp-use> (%ymm0 and all its sub-registers are alive)
/// %ymm0 = ...
/// %xmm0 = ..., implicit %ymm0 (%ymm0 and all its sub-registers are alive)
//===----------------------------------------------------------------------===//
#ifndef LLVM_CODEGEN_LIVEPHYSREGS_H

View File

@ -702,8 +702,8 @@ public:
LQR_Unknown ///< Register liveness not decidable from local neighborhood.
};
/// Return whether (physical) register \p Reg has been <def>ined and not
/// <kill>ed as of just before \p Before.
/// Return whether (physical) register \p Reg has been defined and not
/// killed as of just before \p Before.
///
/// Search is localised to a neighborhood of \p Neighborhood instructions
/// before (searching for defs or kills) and \p Neighborhood instructions

View File

@ -44,6 +44,7 @@ class MachineRegisterInfo;
class ModuleSlotTracker;
class raw_ostream;
template <typename T> class SmallVectorImpl;
class SmallBitVector;
class StringRef;
class TargetInstrInfo;
class TargetRegisterClass;
@ -1220,6 +1221,15 @@ public:
/// Debugging support
/// @{
/// Determine the generic type to be printed (if needed) on uses and defs.
LLT getTypeToPrint(unsigned OpIdx, SmallBitVector &PrintedTypes,
const MachineRegisterInfo &MRI) const;
/// Return true when an instruction has tied register that can't be determined
/// by the instruction's descriptor. This is useful for MIR printing, to
/// determine whether we need to print the ties or not.
bool hasComplexRegisterTies() const;
/// Print this MI to \p OS.
/// Only print the defs and the opcode if \p SkipOpers is true.
/// Otherwise, also print operands if \p SkipDebugLoc is true.

View File

@ -150,7 +150,7 @@ public:
///
struct VirtRegInfo {
/// Reads - One of the operands read the virtual register. This does not
/// include <undef> or <internal> use operands, see MO::readsReg().
/// include undef or internal use operands, see MO::readsReg().
bool Reads;
/// Writes - One of the operands writes the virtual register.

View File

@ -17,6 +17,7 @@
#include "llvm/ADT/DenseMap.h"
#include "llvm/IR/Intrinsics.h"
#include "llvm/Support/DataTypes.h"
#include "llvm/Support/LowLevelTypeImpl.h"
#include <cassert>
namespace llvm {
@ -116,7 +117,7 @@ private:
/// the same register. In that case, the instruction may depend on those
/// operands reading the same dont-care value. For example:
///
/// %1<def> = XOR %2<undef>, %2<undef>
/// %1 = XOR undef %2, undef %2
///
/// Any register can be used for %2, and its value doesn't matter, but
/// the two operands must be the same register.
@ -226,11 +227,33 @@ public:
///
void clearParent() { ParentMI = nullptr; }
/// Print the MachineOperand to \p os.
/// Providing a valid \p TRI and \p IntrinsicInfo results in a more
/// target-specific printing. If \p TRI and \p IntrinsicInfo are null, the
/// function will try to pick it up from the parent.
void print(raw_ostream &os, const TargetRegisterInfo *TRI = nullptr,
const TargetIntrinsicInfo *IntrinsicInfo = nullptr) const;
void print(raw_ostream &os, ModuleSlotTracker &MST,
const TargetRegisterInfo *TRI = nullptr,
const TargetIntrinsicInfo *IntrinsicInfo = nullptr) const;
/// More complex way of printing a MachineOperand.
/// \param TypeToPrint specifies the generic type to be printed on uses and
/// defs. It can be determined using MachineInstr::getTypeToPrint.
/// \param PrintDef - whether we want to print `def` on an operand which
/// isDef. Sometimes, if the operand is printed before '=', we don't print
/// `def`.
/// \param ShouldPrintRegisterTies - whether we want to print register ties.
/// Sometimes they are easily determined by the instruction's descriptor
/// (MachineInstr::hasComplexRegiterTies can determine if it's needed).
/// \param TiedOperandIdx - if we need to print register ties this needs to
/// provide the index of the tied register. If not, it will be ignored.
/// \param TRI - provide more target-specific information to the printer.
/// Unlike the previous function, this one will not try and get the
/// information from it's parent.
/// \param IntrinsicInfo - same as \p TRI.
void print(raw_ostream &os, ModuleSlotTracker &MST, LLT TypeToPrint,
bool PrintDef, bool ShouldPrintRegisterTies,
unsigned TiedOperandIdx, const TargetRegisterInfo *TRI,
const TargetIntrinsicInfo *IntrinsicInfo) const;
void dump() const;
//===--------------------------------------------------------------------===//
@ -831,7 +854,7 @@ template <> struct DenseMapInfo<MachineOperand> {
};
inline raw_ostream &operator<<(raw_ostream &OS, const MachineOperand &MO) {
MO.print(OS, nullptr);
MO.print(OS);
return OS;
}

View File

@ -547,7 +547,7 @@ public:
/// Represents a predicate at the MachineFunction level. The control flow a
/// MachineBranchPredicate represents is:
///
/// Reg <def>= LHS `Predicate` RHS == ConditionDef
/// Reg = LHS `Predicate` RHS == ConditionDef
/// if Reg then goto TrueDest else goto FalseDest
///
struct MachineBranchPredicate {
@ -1432,7 +1432,7 @@ public:
/// For example, AVX instructions may copy part of a register operand into
/// the unused high bits of the destination register.
///
/// vcvtsi2sdq %rax, %xmm0<undef>, %xmm14
/// vcvtsi2sdq %rax, undef %xmm0, %xmm14
///
/// In the code above, vcvtsi2sdq copies %xmm0[127:64] into %xmm14 creating a
/// false dependence on any previous write to %xmm0.

View File

@ -1167,6 +1167,11 @@ Printable printRegUnit(unsigned Unit, const TargetRegisterInfo *TRI);
/// registers on a \ref raw_ostream.
Printable printVRegOrUnit(unsigned VRegOrUnit, const TargetRegisterInfo *TRI);
/// \brief Create Printable object to print register classes or register banks
/// on a \ref raw_ostream.
Printable printRegClassOrBank(unsigned Reg, const MachineRegisterInfo &RegInfo,
const TargetRegisterInfo *TRI);
} // end namespace llvm
#endif // LLVM_CODEGEN_TARGETREGISTERINFO_H

View File

@ -448,11 +448,11 @@ void AggressiveAntiDepBreaker::ScanInstruction(MachineInstr &MI,
// FIXME: The issue with predicated instruction is more complex. We are being
// conservatively here because the kill markers cannot be trusted after
// if-conversion:
// %r6<def> = LDR %sp, %reg0, 92, pred:14, pred:%reg0; mem:LD4[FixedStack14]
// %r6 = LDR %sp, %reg0, 92, pred:14, pred:%reg0; mem:LD4[FixedStack14]
// ...
// STR %r0, %r6<kill>, %reg0, 0, pred:0, pred:%cpsr; mem:ST4[%395]
// %r6<def> = LDR %sp, %reg0, 100, pred:0, pred:%cpsr; mem:LD4[FixedStack12]
// STR %r0, %r6<kill>, %reg0, 0, pred:14, pred:%reg0; mem:ST4[%396](align=8)
// STR %r0, killed %r6, %reg0, 0, pred:0, pred:%cpsr; mem:ST4[%395]
// %r6 = LDR %sp, %reg0, 100, pred:0, pred:%cpsr; mem:LD4[FixedStack12]
// STR %r0, killed %r6, %reg0, 0, pred:14, pred:%reg0; mem:ST4[%396](align=8)
//
// The first R6 kill is not really a kill since it's killed by a predicated
// instruction which may not be executed. The second R6 def may or may not

View File

@ -815,10 +815,8 @@ static void emitKill(const MachineInstr *MI, AsmPrinter &AP) {
for (unsigned i = 0, e = MI->getNumOperands(); i != e; ++i) {
const MachineOperand &Op = MI->getOperand(i);
assert(Op.isReg() && "KILL instruction must have only register operands");
OS << ' '
<< printReg(Op.getReg(),
AP.MF->getSubtarget().getRegisterInfo())
<< (Op.isDef() ? "<def>" : "<kill>");
OS << ' ' << (Op.isDef() ? "def " : "killed ")
<< printReg(Op.getReg(), AP.MF->getSubtarget().getRegisterInfo());
}
AP.OutStreamer->AddComment(OS.str());
AP.OutStreamer->AddBlankLine();

View File

@ -1968,7 +1968,7 @@ bool BranchFolder::HoistCommonCodeInSuccs(MachineBasicBlock *MBB) {
//
// BB2:
// r1 = op2, ...
// = op3, r1<kill>
// = op3, killed r1
IsSafe = false;
break;
}

View File

@ -170,11 +170,11 @@ void CriticalAntiDepBreaker::PrescanInstruction(MachineInstr &MI) {
// FIXME: The issue with predicated instruction is more complex. We are being
// conservative here because the kill markers cannot be trusted after
// if-conversion:
// %r6<def> = LDR %sp, %reg0, 92, pred:14, pred:%reg0; mem:LD4[FixedStack14]
// %r6 = LDR %sp, %reg0, 92, pred:14, pred:%reg0; mem:LD4[FixedStack14]
// ...
// STR %r0, %r6<kill>, %reg0, 0, pred:0, pred:%cpsr; mem:ST4[%395]
// %r6<def> = LDR %sp, %reg0, 100, pred:0, pred:%cpsr; mem:LD4[FixedStack12]
// STR %r0, %r6<kill>, %reg0, 0, pred:14, pred:%reg0; mem:ST4[%396](align=8)
// STR %r0, killed %r6, %reg0, 0, pred:0, pred:%cpsr; mem:ST4[%395]
// %r6 = LDR %sp, %reg0, 100, pred:0, pred:%cpsr; mem:LD4[FixedStack12]
// STR %r0, killed %r6, %reg0, 0, pred:14, pred:%reg0; mem:ST4[%396](align=8)
//
// The first R6 kill is not really a kill since it's killed by a predicated
// instruction which may not be executed. The second R6 def may or may not

View File

@ -104,7 +104,7 @@ bool ExpandPostRA::LowerSubregToReg(MachineInstr *MI) {
if (DstSubReg == InsReg) {
// No need to insert an identity copy instruction.
// Watch out for case like this:
// %rax<def> = SUBREG_TO_REG 0, %eax<kill>, 3
// %rax = SUBREG_TO_REG 0, killed %eax, 3
// We must leave %rax live.
if (DstReg != InsReg) {
MI->setDesc(TII->get(TargetOpcode::KILL));

View File

@ -421,7 +421,7 @@ bool ImplicitNullChecks::canHoistInst(MachineInstr *FaultingMI,
// test %rcx, %rcx
// je _null_block
// _non_null_block:
// %rdx<def> = INST
// %rdx = INST
// ...
//
// This restriction does not apply to the faulting load inst because in

View File

@ -360,7 +360,7 @@ bool InlineSpiller::isSibling(unsigned Reg) {
///
/// x = def
/// spill x
/// y = use x<kill>
/// y = use killed x
///
/// This hoist only helps when the copy kills its source.
///

View File

@ -700,7 +700,7 @@ void LiveIntervals::addKillFlags(const VirtRegMap *VRM) {
//
// %eax = COPY %5
// FOO %5 <--- MI, cancel kill because %eax is live.
// BAR %eax<kill>
// BAR killed %eax
//
// There should be no kill flag on FOO when %5 is rewritten as %eax.
for (auto &RUP : RU) {
@ -721,7 +721,7 @@ void LiveIntervals::addKillFlags(const VirtRegMap *VRM) {
// Example:
// %1 = ... ; R32: %1
// %2:high16 = ... ; R64: %2
// = read %2<kill> ; R64: %2
// = read killed %2 ; R64: %2
// = read %1 ; R32: %1
// The <kill> flag is correct for %2, but the register allocator may
// assign R0L to %1, and R0 to %2 because the low 32bits of R0

View File

@ -235,7 +235,7 @@ void LiveVariables::HandlePhysRegUse(unsigned Reg, MachineInstr &MI) {
// Otherwise, the last sub-register def implicitly defines this register.
// e.g.
// AH =
// AL = ... <imp-def EAX>, <imp-kill AH>
// AL = ... implicit-def EAX, implicit killed AH
// = AH
// ...
// = EAX
@ -321,17 +321,17 @@ bool LiveVariables::HandlePhysRegKill(unsigned Reg, MachineInstr *MI) {
// AH =
//
// = AX
// = AL, AX<imp-use, kill>
// = AL, implicit killed AX
// AX =
//
// Or whole register is defined, but not used at all.
// AX<dead> =
// dead AX =
// ...
// AX =
//
// Or whole register is defined, but only partly used.
// AX<dead> = AL<imp-def>
// = AL<kill>
// dead AX = implicit-def AL
// = killed AL
// AX =
MachineInstr *LastPartDef = nullptr;
unsigned LastPartDefDist = 0;
@ -364,7 +364,7 @@ bool LiveVariables::HandlePhysRegKill(unsigned Reg, MachineInstr *MI) {
if (!PhysRegUse[Reg]) {
// Partial uses. Mark register def dead and add implicit def of
// sub-registers which are used.
// EAX<dead> = op AL<imp-def>
// dead EAX = op implicit-def AL
// That is, EAX def is dead but AL def extends pass it.
PhysRegDef[Reg]->addRegisterDead(Reg, TRI, true);
for (MCSubRegIterator SubRegs(Reg, TRI); SubRegs.isValid(); ++SubRegs) {

View File

@ -164,7 +164,7 @@ public:
void printTargetFlags(const MachineOperand &Op);
void print(const MachineInstr &MI, unsigned OpIdx,
const TargetRegisterInfo *TRI, bool ShouldPrintRegisterTies,
LLT TypeToPrint, bool IsDef = false);
LLT TypeToPrint, bool PrintDef = true);
void print(const LLVMContext &Context, const TargetInstrInfo &TII,
const MachineMemOperand &Op);
void printSyncScope(const LLVMContext &Context, SyncScope::ID SSID);
@ -257,25 +257,11 @@ static void printCustomRegMask(const uint32_t *RegMask, raw_ostream &OS,
OS << ')';
}
static void printRegClassOrBank(unsigned Reg, raw_ostream &OS,
const MachineRegisterInfo &RegInfo,
const TargetRegisterInfo *TRI) {
if (RegInfo.getRegClassOrNull(Reg))
OS << StringRef(TRI->getRegClassName(RegInfo.getRegClass(Reg))).lower();
else if (RegInfo.getRegBankOrNull(Reg))
OS << StringRef(RegInfo.getRegBankOrNull(Reg)->getName()).lower();
else {
OS << "_";
assert((RegInfo.def_empty(Reg) || RegInfo.getType(Reg).isValid()) &&
"Generic registers must have a valid type");
}
}
static void printRegClassOrBank(unsigned Reg, yaml::StringValue &Dest,
const MachineRegisterInfo &RegInfo,
const TargetRegisterInfo *TRI) {
raw_string_ostream OS(Dest.Value);
printRegClassOrBank(Reg, OS, RegInfo, TRI);
OS << printRegClassOrBank(Reg, RegInfo, TRI);
}
@ -289,7 +275,7 @@ void MIRPrinter::convert(yaml::MachineFunction &MF,
unsigned Reg = TargetRegisterInfo::index2VirtReg(I);
yaml::VirtualRegisterDefinition VReg;
VReg.ID = I;
printRegClassOrBank(Reg, VReg.Class, RegInfo, TRI);
::printRegClassOrBank(Reg, VReg.Class, RegInfo, TRI);
unsigned PreferredReg = RegInfo.getSimpleHint(Reg);
if (PreferredReg)
printRegMIR(PreferredReg, VReg.PreferredRegister, TRI);
@ -661,44 +647,6 @@ void MIPrinter::print(const MachineBasicBlock &MBB) {
OS.indent(2) << "}\n";
}
/// Return true when an instruction has tied register that can't be determined
/// by the instruction's descriptor.
static bool hasComplexRegisterTies(const MachineInstr &MI) {
const MCInstrDesc &MCID = MI.getDesc();
for (unsigned I = 0, E = MI.getNumOperands(); I < E; ++I) {
const auto &Operand = MI.getOperand(I);
if (!Operand.isReg() || Operand.isDef())
// Ignore the defined registers as MCID marks only the uses as tied.
continue;
int ExpectedTiedIdx = MCID.getOperandConstraint(I, MCOI::TIED_TO);
int TiedIdx = Operand.isTied() ? int(MI.findTiedOperandIdx(I)) : -1;
if (ExpectedTiedIdx != TiedIdx)
return true;
}
return false;
}
static LLT getTypeToPrint(const MachineInstr &MI, unsigned OpIdx,
SmallBitVector &PrintedTypes,
const MachineRegisterInfo &MRI) {
const MachineOperand &Op = MI.getOperand(OpIdx);
if (!Op.isReg())
return LLT{};
if (MI.isVariadic() || OpIdx >= MI.getNumExplicitOperands())
return MRI.getType(Op.getReg());
auto &OpInfo = MI.getDesc().OpInfo[OpIdx];
if (!OpInfo.isGenericType())
return MRI.getType(Op.getReg());
if (PrintedTypes[OpInfo.getGenericTypeIndex()])
return LLT{};
PrintedTypes.set(OpInfo.getGenericTypeIndex());
return MRI.getType(Op.getReg());
}
void MIPrinter::print(const MachineInstr &MI) {
const auto *MF = MI.getMF();
const auto &MRI = MF->getRegInfo();
@ -711,7 +659,7 @@ void MIPrinter::print(const MachineInstr &MI) {
assert(MI.getNumOperands() == 1 && "Expected 1 operand in CFI instruction");
SmallBitVector PrintedTypes(8);
bool ShouldPrintRegisterTies = hasComplexRegisterTies(MI);
bool ShouldPrintRegisterTies = MI.hasComplexRegisterTies();
unsigned I = 0, E = MI.getNumOperands();
for (; I < E && MI.getOperand(I).isReg() && MI.getOperand(I).isDef() &&
!MI.getOperand(I).isImplicit();
@ -719,8 +667,8 @@ void MIPrinter::print(const MachineInstr &MI) {
if (I)
OS << ", ";
print(MI, I, TRI, ShouldPrintRegisterTies,
getTypeToPrint(MI, I, PrintedTypes, MRI),
/*IsDef=*/true);
MI.getTypeToPrint(I, PrintedTypes, MRI),
/*PrintDef=*/false);
}
if (I)
@ -736,7 +684,7 @@ void MIPrinter::print(const MachineInstr &MI) {
if (NeedComma)
OS << ", ";
print(MI, I, TRI, ShouldPrintRegisterTies,
getTypeToPrint(MI, I, PrintedTypes, MRI));
MI.getTypeToPrint(I, PrintedTypes, MRI));
NeedComma = true;
}
@ -902,44 +850,17 @@ static const char *getTargetIndexName(const MachineFunction &MF, int Index) {
void MIPrinter::print(const MachineInstr &MI, unsigned OpIdx,
const TargetRegisterInfo *TRI,
bool ShouldPrintRegisterTies, LLT TypeToPrint,
bool IsDef) {
bool PrintDef) {
const MachineOperand &Op = MI.getOperand(OpIdx);
printTargetFlags(Op);
switch (Op.getType()) {
case MachineOperand::MO_Register: {
unsigned Reg = Op.getReg();
if (Op.isImplicit())
OS << (Op.isDef() ? "implicit-def " : "implicit ");
else if (!IsDef && Op.isDef())
// Print the 'def' flag only when the operand is defined after '='.
OS << "def ";
if (Op.isInternalRead())
OS << "internal ";
if (Op.isDead())
OS << "dead ";
if (Op.isKill())
OS << "killed ";
if (Op.isUndef())
OS << "undef ";
if (Op.isEarlyClobber())
OS << "early-clobber ";
if (Op.isDebug())
OS << "debug-use ";
OS << printReg(Reg, TRI);
// Print the sub register.
if (Op.getSubReg() != 0)
OS << '.' << TRI->getSubRegIndexName(Op.getSubReg());
if (TargetRegisterInfo::isVirtualRegister(Reg)) {
const MachineRegisterInfo &MRI = Op.getParent()->getMF()->getRegInfo();
if (IsDef || MRI.def_empty(Reg)) {
OS << ':';
printRegClassOrBank(Reg, OS, MRI, TRI);
}
}
unsigned TiedOperandIdx = 0;
if (ShouldPrintRegisterTies && Op.isTied() && !Op.isDef())
OS << "(tied-def " << Op.getParent()->findTiedOperandIdx(OpIdx) << ")";
if (TypeToPrint.isValid())
OS << '(' << TypeToPrint << ')';
TiedOperandIdx = Op.getParent()->findTiedOperandIdx(OpIdx);
const TargetIntrinsicInfo *TII = MI.getMF()->getTarget().getIntrinsicInfo();
Op.print(OS, MST, TypeToPrint, PrintDef, ShouldPrintRegisterTies,
TiedOperandIdx, TRI, TII);
break;
}
case MachineOperand::MO_Immediate:

View File

@ -623,10 +623,10 @@ bool MachineCSE::ProcessBlock(MachineBasicBlock *MBB) {
// Go through implicit defs of CSMI and MI, and clear the kill flags on
// their uses in all the instructions between CSMI and MI.
// We might have made some of the kill flags redundant, consider:
// subs ... %nzcv<imp-def> <- CSMI
// csinc ... %nzcv<imp-use,kill> <- this kill flag isn't valid anymore
// subs ... %nzcv<imp-def> <- MI, to be eliminated
// csinc ... %nzcv<imp-use,kill>
// subs ... implicit-def %nzcv <- CSMI
// csinc ... implicit killed %nzcv <- this kill flag isn't valid anymore
// subs ... implicit-def %nzcv <- MI, to be eliminated
// csinc ... implicit killed %nzcv
// Since we eliminated MI, and reused a register imp-def'd by CSMI
// (here %nzcv), that register, if it was killed before MI, should have
// that kill flag removed, because it's lifetime was extended.

View File

@ -226,19 +226,19 @@ void MachineCopyPropagation::CopyPropagateBlock(MachineBasicBlock &MBB) {
// The two copies cancel out and the source of the first copy
// hasn't been overridden, eliminate the second one. e.g.
// %ecx<def> = COPY %eax
// %ecx = COPY %eax
// ... nothing clobbered eax.
// %eax<def> = COPY %ecx
// %eax = COPY %ecx
// =>
// %ecx<def> = COPY %eax
// %ecx = COPY %eax
//
// or
//
// %ecx<def> = COPY %eax
// %ecx = COPY %eax
// ... nothing clobbered eax.
// %ecx<def> = COPY %eax
// %ecx = COPY %eax
// =>
// %ecx<def> = COPY %eax
// %ecx = COPY %eax
if (eraseIfRedundant(*MI, Def, Src) || eraseIfRedundant(*MI, Src, Def))
continue;
@ -262,11 +262,11 @@ void MachineCopyPropagation::CopyPropagateBlock(MachineBasicBlock &MBB) {
// If 'Def' is previously source of another copy, then this earlier copy's
// source is no longer available. e.g.
// %xmm9<def> = copy %xmm2
// %xmm9 = copy %xmm2
// ...
// %xmm2<def> = copy %xmm0
// %xmm2 = copy %xmm0
// ...
// %xmm2<def> = copy %xmm9
// %xmm2 = copy %xmm9
ClobberRegister(Def);
for (const MachineOperand &MO : MI->implicit_operands()) {
if (!MO.isReg() || !MO.isDef())

View File

@ -18,6 +18,7 @@
#include "llvm/ADT/Hashing.h"
#include "llvm/ADT/None.h"
#include "llvm/ADT/STLExtras.h"
#include "llvm/ADT/SmallBitVector.h"
#include "llvm/ADT/SmallString.h"
#include "llvm/ADT/SmallVector.h"
#include "llvm/Analysis/AliasAnalysis.h"
@ -742,7 +743,7 @@ MachineInstr::readsWritesVirtualRegister(unsigned Reg,
if (MO.isUse())
Use |= !MO.isUndef();
else if (MO.getSubReg() && !MO.isUndef())
// A partial <def,undef> doesn't count as reading the register.
// A partial def undef doesn't count as reading the register.
PartDef = true;
else
FullDef = true;
@ -1163,6 +1164,41 @@ void MachineInstr::copyImplicitOps(MachineFunction &MF,
}
}
bool MachineInstr::hasComplexRegisterTies() const {
const MCInstrDesc &MCID = getDesc();
for (unsigned I = 0, E = getNumOperands(); I < E; ++I) {
const auto &Operand = getOperand(I);
if (!Operand.isReg() || Operand.isDef())
// Ignore the defined registers as MCID marks only the uses as tied.
continue;
int ExpectedTiedIdx = MCID.getOperandConstraint(I, MCOI::TIED_TO);
int TiedIdx = Operand.isTied() ? int(findTiedOperandIdx(I)) : -1;
if (ExpectedTiedIdx != TiedIdx)
return true;
}
return false;
}
LLT MachineInstr::getTypeToPrint(unsigned OpIdx, SmallBitVector &PrintedTypes,
const MachineRegisterInfo &MRI) const {
const MachineOperand &Op = getOperand(OpIdx);
if (!Op.isReg())
return LLT{};
if (isVariadic() || OpIdx >= getNumExplicitOperands())
return MRI.getType(Op.getReg());
auto &OpInfo = getDesc().OpInfo[OpIdx];
if (!OpInfo.isGenericType())
return MRI.getType(Op.getReg());
if (PrintedTypes[OpInfo.getGenericTypeIndex()])
return LLT{};
PrintedTypes.set(OpInfo.getGenericTypeIndex());
return MRI.getType(Op.getReg());
}
#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
LLVM_DUMP_METHOD void MachineInstr::dump() const {
dbgs() << " ";
@ -1204,21 +1240,31 @@ void MachineInstr::print(raw_ostream &OS, ModuleSlotTracker &MST,
// Save a list of virtual registers.
SmallVector<unsigned, 8> VirtRegs;
SmallBitVector PrintedTypes(8);
bool ShouldPrintRegisterTies = hasComplexRegisterTies();
auto getTiedOperandIdx = [&](unsigned OpIdx) {
if (!ShouldPrintRegisterTies)
return 0U;
const MachineOperand &MO = getOperand(OpIdx);
if (MO.isReg() && MO.isTied() && !MO.isDef())
return findTiedOperandIdx(OpIdx);
return 0U;
};
// Print explicitly defined operands on the left of an assignment syntax.
unsigned StartOp = 0, e = getNumOperands();
for (; StartOp < e && getOperand(StartOp).isReg() &&
getOperand(StartOp).isDef() &&
!getOperand(StartOp).isImplicit();
getOperand(StartOp).isDef() && !getOperand(StartOp).isImplicit();
++StartOp) {
if (StartOp != 0) OS << ", ";
getOperand(StartOp).print(OS, MST, TRI, IntrinsicInfo);
if (StartOp != 0)
OS << ", ";
LLT TypeToPrint = MRI ? getTypeToPrint(StartOp, PrintedTypes, *MRI) : LLT{};
unsigned TiedOperandIdx = getTiedOperandIdx(StartOp);
getOperand(StartOp).print(OS, MST, TypeToPrint, /*PrintDef=*/false,
ShouldPrintRegisterTies, TiedOperandIdx, TRI,
IntrinsicInfo);
unsigned Reg = getOperand(StartOp).getReg();
if (TargetRegisterInfo::isVirtualRegister(Reg)) {
if (TargetRegisterInfo::isVirtualRegister(Reg))
VirtRegs.push_back(Reg);
LLT Ty = MRI ? MRI->getType(Reg) : LLT{};
if (Ty.isValid())
OS << '(' << Ty << ')';
}
}
if (StartOp != 0)
@ -1241,7 +1287,12 @@ void MachineInstr::print(raw_ostream &OS, ModuleSlotTracker &MST,
if (isInlineAsm() && e >= InlineAsm::MIOp_FirstOperand) {
// Print asm string.
OS << " ";
getOperand(InlineAsm::MIOp_AsmString).print(OS, MST, TRI);
const unsigned OpIdx = InlineAsm::MIOp_AsmString;
LLT TypeToPrint = MRI ? getTypeToPrint(OpIdx, PrintedTypes, *MRI) : LLT{};
unsigned TiedOperandIdx = getTiedOperandIdx(StartOp);
getOperand(OpIdx).print(OS, MST, TypeToPrint, /*PrintDef=*/true,
ShouldPrintRegisterTies, TiedOperandIdx, TRI,
IntrinsicInfo);
// Print HasSideEffects, MayLoad, MayStore, IsAlignStack
unsigned ExtraInfo = getOperand(InlineAsm::MIOp_ExtraInfo).getImm();
@ -1284,8 +1335,12 @@ void MachineInstr::print(raw_ostream &OS, ModuleSlotTracker &MST,
auto *DIV = dyn_cast<DILocalVariable>(MO.getMetadata());
if (DIV && !DIV->getName().empty())
OS << "!\"" << DIV->getName() << '\"';
else
MO.print(OS, MST, TRI);
else {
LLT TypeToPrint = MRI ? getTypeToPrint(i, PrintedTypes, *MRI) : LLT{};
unsigned TiedOperandIdx = getTiedOperandIdx(StartOp);
MO.print(OS, MST, TypeToPrint, /*PrintDef=*/true,
ShouldPrintRegisterTies, TiedOperandIdx, TRI, IntrinsicInfo);
}
} else if (TRI && (isInsertSubreg() || isRegSequence() ||
(isSubregToReg() && i == 3)) && MO.isImm()) {
OS << TRI->getSubRegIndexName(MO.getImm());
@ -1347,8 +1402,12 @@ void MachineInstr::print(raw_ostream &OS, ModuleSlotTracker &MST,
// Compute the index of the next operand descriptor.
AsmDescOp += 1 + InlineAsm::getNumOperandRegisters(Flag);
} else
MO.print(OS, MST, TRI);
} else {
LLT TypeToPrint = MRI ? getTypeToPrint(i, PrintedTypes, *MRI) : LLT{};
unsigned TiedOperandIdx = getTiedOperandIdx(StartOp);
MO.print(OS, MST, TypeToPrint, /*PrintDef=*/true, ShouldPrintRegisterTies,
TiedOperandIdx, TRI, IntrinsicInfo);
}
}
bool HaveSemi = false;

View File

@ -15,10 +15,11 @@
#include "llvm/Analysis/Loads.h"
#include "llvm/CodeGen/MIRPrinter.h"
#include "llvm/CodeGen/MachineRegisterInfo.h"
#include "llvm/Target/TargetIntrinsicInfo.h"
#include "llvm/CodeGen/TargetRegisterInfo.h"
#include "llvm/IR/Constants.h"
#include "llvm/IR/ModuleSlotTracker.h"
#include "llvm/Target/TargetIntrinsicInfo.h"
#include "llvm/Target/TargetMachine.h"
using namespace llvm;
@ -333,75 +334,86 @@ hash_code llvm::hash_value(const MachineOperand &MO) {
llvm_unreachable("Invalid machine operand type");
}
// Try to crawl up to the machine function and get TRI and IntrinsicInfo from
// it.
static void tryToGetTargetInfo(const MachineOperand &MO,
const TargetRegisterInfo *&TRI,
const TargetIntrinsicInfo *&IntrinsicInfo) {
if (const MachineInstr *MI = MO.getParent()) {
if (const MachineBasicBlock *MBB = MI->getParent()) {
if (const MachineFunction *MF = MBB->getParent()) {
TRI = MF->getSubtarget().getRegisterInfo();
IntrinsicInfo = MF->getTarget().getIntrinsicInfo();
}
}
}
}
void MachineOperand::print(raw_ostream &OS, const TargetRegisterInfo *TRI,
const TargetIntrinsicInfo *IntrinsicInfo) const {
tryToGetTargetInfo(*this, TRI, IntrinsicInfo);
ModuleSlotTracker DummyMST(nullptr);
print(OS, DummyMST, TRI, IntrinsicInfo);
print(OS, DummyMST, LLT{}, /*PrintDef=*/false,
/*ShouldPrintRegisterTies=*/true,
/*TiedOperandIdx=*/0, TRI, IntrinsicInfo);
}
void MachineOperand::print(raw_ostream &OS, ModuleSlotTracker &MST,
LLT TypeToPrint, bool PrintDef,
bool ShouldPrintRegisterTies,
unsigned TiedOperandIdx,
const TargetRegisterInfo *TRI,
const TargetIntrinsicInfo *IntrinsicInfo) const {
switch (getType()) {
case MachineOperand::MO_Register:
OS << printReg(getReg(), TRI, getSubReg());
if (isDef() || isKill() || isDead() || isImplicit() || isUndef() ||
isInternalRead() || isEarlyClobber() || isTied()) {
OS << '<';
bool NeedComma = false;
if (isDef()) {
if (NeedComma)
OS << ',';
if (isEarlyClobber())
OS << "earlyclobber,";
if (isImplicit())
OS << "imp-";
OS << "def";
NeedComma = true;
// <def,read-undef> only makes sense when getSubReg() is set.
// Don't clutter the output otherwise.
if (isUndef() && getSubReg())
OS << ",read-undef";
} else if (isImplicit()) {
OS << "imp-use";
NeedComma = true;
}
if (isKill()) {
if (NeedComma)
OS << ',';
OS << "kill";
NeedComma = true;
}
if (isDead()) {
if (NeedComma)
OS << ',';
OS << "dead";
NeedComma = true;
}
if (isUndef() && isUse()) {
if (NeedComma)
OS << ',';
OS << "undef";
NeedComma = true;
}
if (isInternalRead()) {
if (NeedComma)
OS << ',';
OS << "internal";
NeedComma = true;
}
if (isTied()) {
if (NeedComma)
OS << ',';
OS << "tied";
if (TiedTo != 15)
OS << unsigned(TiedTo - 1);
}
OS << '>';
case MachineOperand::MO_Register: {
unsigned Reg = getReg();
if (isImplicit())
OS << (isDef() ? "implicit-def " : "implicit ");
else if (PrintDef && isDef())
// Print the 'def' flag only when the operand is defined after '='.
OS << "def ";
if (isInternalRead())
OS << "internal ";
if (isDead())
OS << "dead ";
if (isKill())
OS << "killed ";
if (isUndef())
OS << "undef ";
if (isEarlyClobber())
OS << "early-clobber ";
if (isDebug())
OS << "debug-use ";
OS << printReg(Reg, TRI);
// Print the sub register.
if (unsigned SubReg = getSubReg()) {
if (TRI)
OS << '.' << TRI->getSubRegIndexName(SubReg);
else
OS << ".subreg" << SubReg;
}
// Print the register class / bank.
if (TargetRegisterInfo::isVirtualRegister(Reg)) {
if (const MachineInstr *MI = getParent()) {
if (const MachineBasicBlock *MBB = MI->getParent()) {
if (const MachineFunction *MF = MBB->getParent()) {
const MachineRegisterInfo &MRI = MF->getRegInfo();
if (!PrintDef || MRI.def_empty(Reg)) {
OS << ':';
OS << printRegClassOrBank(Reg, MRI, TRI);
}
}
}
}
}
// Print ties.
if (ShouldPrintRegisterTies && isTied() && !isDef())
OS << "(tied-def " << TiedOperandIdx << ")";
// Print types.
if (TypeToPrint.isValid())
OS << '(' << TypeToPrint << ')';
break;
}
case MachineOperand::MO_Immediate:
OS << getImm();
break;
@ -475,23 +487,27 @@ void MachineOperand::print(raw_ostream &OS, ModuleSlotTracker &MST,
OS << '>';
break;
case MachineOperand::MO_RegisterMask: {
unsigned NumRegsInMask = 0;
unsigned NumRegsEmitted = 0;
OS << "<regmask";
for (unsigned i = 0; i < TRI->getNumRegs(); ++i) {
unsigned MaskWord = i / 32;
unsigned MaskBit = i % 32;
if (getRegMask()[MaskWord] & (1 << MaskBit)) {
if (PrintRegMaskNumRegs < 0 ||
NumRegsEmitted <= static_cast<unsigned>(PrintRegMaskNumRegs)) {
OS << " " << printReg(i, TRI);
NumRegsEmitted++;
if (TRI) {
unsigned NumRegsInMask = 0;
unsigned NumRegsEmitted = 0;
for (unsigned i = 0; i < TRI->getNumRegs(); ++i) {
unsigned MaskWord = i / 32;
unsigned MaskBit = i % 32;
if (getRegMask()[MaskWord] & (1 << MaskBit)) {
if (PrintRegMaskNumRegs < 0 ||
NumRegsEmitted <= static_cast<unsigned>(PrintRegMaskNumRegs)) {
OS << " " << printReg(i, TRI);
NumRegsEmitted++;
}
NumRegsInMask++;
}
NumRegsInMask++;
}
if (NumRegsEmitted != NumRegsInMask)
OS << " and " << (NumRegsInMask - NumRegsEmitted) << " more...";
} else {
OS << " ...";
}
if (NumRegsEmitted != NumRegsInMask)
OS << " and " << (NumRegsInMask - NumRegsEmitted) << " more...";
OS << ">";
break;
}

View File

@ -246,14 +246,14 @@ MachineSinking::AllUsesDominatedByBlock(unsigned Reg,
// %bb.1: derived from LLVM BB %bb4.preheader
// Predecessors according to CFG: %bb.0
// ...
// %reg16385<def> = DEC64_32r %reg16437, %eflags<imp-def,dead>
// %reg16385 = DEC64_32r %reg16437, implicit-def dead %eflags
// ...
// JE_4 <%bb.37>, %eflags<imp-use>
// JE_4 <%bb.37>, implicit %eflags
// Successors according to CFG: %bb.37 %bb.2
//
// %bb.2: derived from LLVM BB %bb.nph
// Predecessors according to CFG: %bb.0 %bb.1
// %reg16386<def> = PHI %reg16434, %bb.0, %reg16385, %bb.1
// %reg16386 = PHI %reg16434, %bb.0, %reg16385, %bb.1
BreakPHIEdge = true;
for (MachineOperand &MO : MRI->use_nodbg_operands(Reg)) {
MachineInstr *UseInst = MO.getParent();

View File

@ -1961,7 +1961,7 @@ void MachineVerifier::verifyLiveRangeSegment(const LiveRange &LR,
if (MOI->isDef()) {
if (Sub != 0) {
hasSubRegDef = true;
// An operand %0:sub0<def> reads %0:sub1..n. Invert the lane
// An operand %0:sub0 reads %0:sub1..n. Invert the lane
// mask for subregister defs. Read-undef defs will be handled by
// readsReg below.
SLM = ~SLM;

View File

@ -272,7 +272,7 @@ void RegAllocFast::addKillFlag(const LiveReg &LR) {
// subreg of this register and given we don't track which
// lanes are actually dead, we cannot insert a kill flag here.
// Otherwise we may end up in a situation like this:
// ... = (MO) physreg:sub1, physreg <implicit-use, kill>
// ... = (MO) physreg:sub1, implicit killed physreg
// ... <== Here we would allow later pass to reuse physreg:sub1
// which is potentially wrong.
// LR:sub0 = ...
@ -675,7 +675,7 @@ RegAllocFast::LiveRegMap::iterator RegAllocFast::reloadVirtReg(MachineInstr &MI,
} else if (MO.isKill()) {
// We must remove kill flags from uses of reloaded registers because the
// register would be killed immediately, and there might be a second use:
// %foo = OR %x<kill>, %x
// %foo = OR killed %x, %x
// This would cause a second reload of %x into a different register.
DEBUG(dbgs() << "Clearing clean kill: " << MO << "\n");
MO.setIsKill(false);

View File

@ -667,7 +667,7 @@ bool RegisterCoalescer::removeCopyByCommutingDef(const CoalescerPair &CP,
// its other operand is coalesced to the copy dest register, see if we can
// transform the copy into a noop by commuting the definition. For example,
//
// A3 = op A2 B0<kill>
// A3 = op A2 killed B0
// ...
// B1 = A3 <- this copy
// ...
@ -675,7 +675,7 @@ bool RegisterCoalescer::removeCopyByCommutingDef(const CoalescerPair &CP,
//
// ==>
//
// B2 = op B0 A2<kill>
// B2 = op B0 killed A2
// ...
// B1 = B2 <- now an identity copy
// ...
@ -768,7 +768,7 @@ bool RegisterCoalescer::removeCopyByCommutingDef(const CoalescerPair &CP,
// ...
// B = A
// ...
// C = A<kill>
// C = killed A
// ...
// = B
@ -1254,7 +1254,7 @@ bool RegisterCoalescer::reMaterializeTrivialDef(const CoalescerPair &CP,
// Make sure that the subrange for resultant undef is removed
// For example:
// %1:sub1<def,read-undef> = LOAD CONSTANT 1
// %2<def> = COPY %1
// %2 = COPY %1
// ==>
// %2:sub1<def, read-undef> = LOAD CONSTANT 1
// ; Correct but need to remove the subrange for %2:sub0
@ -1297,7 +1297,7 @@ bool RegisterCoalescer::reMaterializeTrivialDef(const CoalescerPair &CP,
// = somedef %1 ; %1 GR8
// =>
// %1 = somedef ; %1 GR8
// ECX<def, dead> = remat ; CL<imp-def>
// dead ECX = remat ; implicit-def CL
// = somedef %1 ; %1 GR8
// %1 will see the inteferences with CL but not with CH since
// no live-ranges would have been created for ECX.
@ -1352,7 +1352,7 @@ bool RegisterCoalescer::eliminateUndefCopy(MachineInstr *CopyMI) {
// ProcessImpicitDefs may leave some copies of <undef> values, it only removes
// local variables. When we have a copy like:
//
// %1 = COPY %2<undef>
// %1 = COPY undef %2
//
// We delete the copy and remove the corresponding value number from %1.
// Any uses of that value number are marked as <undef>.
@ -1927,7 +1927,7 @@ bool RegisterCoalescer::joinReservedPhysReg(CoalescerPair &CP) {
//
// %dst:ssub0<def,read-undef> = FOO
// %src = BAR
// %dst:ssub1<def> = COPY %src
// %dst:ssub1 = COPY %src
//
// The live range of %src overlaps the %dst value defined by FOO, but
// merging %src into %dst:ssub1 is only going to clobber the ssub1 lane
@ -1942,9 +1942,9 @@ bool RegisterCoalescer::joinReservedPhysReg(CoalescerPair &CP) {
// is live, but never read. This can happen because we don't compute
// individual live ranges per lane.
//
// %dst<def> = FOO
// %dst = FOO
// %src = BAR
// %dst:ssub1<def> = COPY %src
// %dst:ssub1 = COPY %src
//
// This kind of interference is only resolved locally. If the clobbered
// lane value escapes the block, the join is aborted.
@ -2287,7 +2287,7 @@ JoinVals::analyzeValue(unsigned ValNo, JoinVals &Other) {
//
// This adds ssub1 to the set of valid lanes in %src:
//
// %src:ssub1<def> = FOO
// %src:ssub1 = FOO
//
// This leaves only ssub1 valid, making any other lanes undef:
//
@ -2425,9 +2425,9 @@ JoinVals::analyzeValue(unsigned ValNo, JoinVals &Other) {
//
// 1 %dst:ssub0 = FOO <-- OtherVNI
// 2 %src = BAR <-- VNI
// 3 %dst:ssub1 = COPY %src<kill> <-- Eliminate this copy.
// 4 BAZ %dst<kill>
// 5 QUUX %src<kill>
// 3 %dst:ssub1 = COPY killed %src <-- Eliminate this copy.
// 4 BAZ killed %dst
// 5 QUUX killed %src
//
// Here OtherVNI will map to itself in [1;2), but to VNI in [2;5). CR_Replace
// handles this complex value mapping.
@ -2437,7 +2437,7 @@ JoinVals::analyzeValue(unsigned ValNo, JoinVals &Other) {
// If the other live range is killed by DefMI and the live ranges are still
// overlapping, it must be because we're looking at an early clobber def:
//
// %dst<def,early-clobber> = ASM %src<kill>
// %dst<def,early-clobber> = ASM killed %src
//
// In this case, it is illegal to merge the two live ranges since the early
// clobber def would clobber %src before it was read.
@ -2682,7 +2682,7 @@ void JoinVals::pruneValues(JoinVals &Other,
if (!Def.isBlock()) {
if (changeInstrs) {
// Remove <def,read-undef> flags. This def is now a partial redef.
// Also remove <def,dead> flags since the joined live range will
// Also remove dead flags since the joined live range will
// continue past this instruction.
for (MachineOperand &MO :
Indexes->getInstructionFromIndex(Def)->operands()) {

View File

@ -213,7 +213,7 @@ void RegScavenger::forward() {
continue;
if (!isRegUsed(Reg)) {
// Check if it's partial live: e.g.
// D0 = insert_subreg D0<undef>, S0
// D0 = insert_subreg undef D0, S0
// ... D0
// The problem is the insert_subreg could be eliminated. The use of
// D0 is using a partially undef value. This is not *incorrect* since

View File

@ -1379,7 +1379,7 @@ void SplitEditor::rewriteAssigned(bool ExtendRanges) {
// for a partially defined original register. For example:
// %0:subreg_hireg<def,read-undef> = ...
// ...
// %1<def> = COPY %0
// %1 = COPY %0
if (S.empty())
continue;
SubLRC.reset(&VRM.getMachineFunction(), LIS.getSlotIndexes(), &MDT,

View File

@ -144,6 +144,21 @@ Printable printVRegOrUnit(unsigned Unit, const TargetRegisterInfo *TRI) {
});
}
Printable printRegClassOrBank(unsigned Reg, const MachineRegisterInfo &RegInfo,
const TargetRegisterInfo *TRI) {
return Printable([Reg, &RegInfo, TRI](raw_ostream &OS) {
if (RegInfo.getRegClassOrNull(Reg))
OS << StringRef(TRI->getRegClassName(RegInfo.getRegClass(Reg))).lower();
else if (RegInfo.getRegBankOrNull(Reg))
OS << StringRef(RegInfo.getRegBankOrNull(Reg)->getName()).lower();
else {
OS << "_";
assert((RegInfo.def_empty(Reg) || RegInfo.getType(Reg).isValid()) &&
"Generic registers must have a valid type");
}
});
}
} // end namespace llvm
/// getAllocatableClass - Return the maximal subclass of the given register

View File

@ -458,8 +458,8 @@ static bool isPlainlyKilled(MachineInstr *MI, unsigned Reg,
/// For example, in this code:
///
/// %reg1034 = copy %reg1024
/// %reg1035 = copy %reg1025<kill>
/// %reg1036 = add %reg1034<kill>, %reg1035<kill>
/// %reg1035 = copy killed %reg1025
/// %reg1036 = add killed %reg1034, killed %reg1035
///
/// %reg1034 is not considered to be killed, since it is copied from a
/// register which is not killed. Treating it as not killed lets the
@ -591,31 +591,31 @@ isProfitableToCommute(unsigned regA, unsigned regB, unsigned regC,
// general, we want no uses between this instruction and the definition of
// the two-address register.
// e.g.
// %reg1028<def> = EXTRACT_SUBREG %reg1027<kill>, 1
// %reg1029<def> = MOV8rr %reg1028
// %reg1029<def> = SHR8ri %reg1029, 7, %eflags<imp-def,dead>
// insert => %reg1030<def> = MOV8rr %reg1028
// %reg1030<def> = ADD8rr %reg1028<kill>, %reg1029<kill>, %eflags<imp-def,dead>
// %reg1028 = EXTRACT_SUBREG killed %reg1027, 1
// %reg1029 = MOV8rr %reg1028
// %reg1029 = SHR8ri %reg1029, 7, implicit dead %eflags
// insert => %reg1030 = MOV8rr %reg1028
// %reg1030 = ADD8rr killed %reg1028, killed %reg1029, implicit dead %eflags
// In this case, it might not be possible to coalesce the second MOV8rr
// instruction if the first one is coalesced. So it would be profitable to
// commute it:
// %reg1028<def> = EXTRACT_SUBREG %reg1027<kill>, 1
// %reg1029<def> = MOV8rr %reg1028
// %reg1029<def> = SHR8ri %reg1029, 7, %eflags<imp-def,dead>
// insert => %reg1030<def> = MOV8rr %reg1029
// %reg1030<def> = ADD8rr %reg1029<kill>, %reg1028<kill>, %eflags<imp-def,dead>
// %reg1028 = EXTRACT_SUBREG killed %reg1027, 1
// %reg1029 = MOV8rr %reg1028
// %reg1029 = SHR8ri %reg1029, 7, implicit dead %eflags
// insert => %reg1030 = MOV8rr %reg1029
// %reg1030 = ADD8rr killed %reg1029, killed %reg1028, implicit dead %eflags
if (!isPlainlyKilled(MI, regC, LIS))
return false;
// Ok, we have something like:
// %reg1030<def> = ADD8rr %reg1028<kill>, %reg1029<kill>, %eflags<imp-def,dead>
// %reg1030 = ADD8rr killed %reg1028, killed %reg1029, implicit dead %eflags
// let's see if it's worth commuting it.
// Look for situations like this:
// %reg1024<def> = MOV r1
// %reg1025<def> = MOV r0
// %reg1026<def> = ADD %reg1024, %reg1025
// %reg1024 = MOV r1
// %reg1025 = MOV r0
// %reg1026 = ADD %reg1024, %reg1025
// r0 = MOV %reg1026
// Commute the ADD to hopefully eliminate an otherwise unavoidable copy.
unsigned ToRegA = getMappedReg(regA, DstRegMap);
@ -713,9 +713,9 @@ bool TwoAddressInstructionPass::commuteInstruction(MachineInstr *MI,
bool
TwoAddressInstructionPass::isProfitableToConv3Addr(unsigned RegA,unsigned RegB){
// Look for situations like this:
// %reg1024<def> = MOV r1
// %reg1025<def> = MOV r0
// %reg1026<def> = ADD %reg1024, %reg1025
// %reg1024 = MOV r1
// %reg1025 = MOV r0
// %reg1026 = ADD %reg1024, %reg1025
// r2 = MOV %reg1026
// Turn ADD into a 3-address instruction to avoid a copy.
unsigned FromRegB = getMappedReg(RegB, SrcRegMap);
@ -1466,7 +1466,7 @@ collectTiedOperands(MachineInstr *MI, TiedOperandMap &TiedOperands) {
assert(SrcReg && SrcMO.isUse() && "two address instruction invalid");
// Deal with <undef> uses immediately - simply rewrite the src operand.
// Deal with undef uses immediately - simply rewrite the src operand.
if (SrcMO.isUndef() && !DstMO.getSubReg()) {
// Constrain the DstReg register class if required.
if (TargetRegisterInfo::isVirtualRegister(DstReg))
@ -1778,8 +1778,8 @@ bool TwoAddressInstructionPass::runOnMachineFunction(MachineFunction &Func) {
///
/// Becomes:
///
/// %dst:ssub0<def,undef> = COPY %v1
/// %dst:ssub1<def> = COPY %v2
/// undef %dst:ssub0 = COPY %v1
/// %dst:ssub1 = COPY %v2
void TwoAddressInstructionPass::
eliminateRegSequence(MachineBasicBlock::iterator &MBBI) {
MachineInstr &MI = *MBBI;
@ -1803,7 +1803,7 @@ eliminateRegSequence(MachineBasicBlock::iterator &MBBI) {
MachineOperand &UseMO = MI.getOperand(i);
unsigned SrcReg = UseMO.getReg();
unsigned SubIdx = MI.getOperand(i+1).getImm();
// Nothing needs to be inserted for <undef> operands.
// Nothing needs to be inserted for undef operands.
if (UseMO.isUndef())
continue;
@ -1825,7 +1825,7 @@ eliminateRegSequence(MachineBasicBlock::iterator &MBBI) {
.addReg(DstReg, RegState::Define, SubIdx)
.add(UseMO);
// The first def needs an <undef> flag because there is no live register
// The first def needs an undef flag because there is no live register
// before it.
if (!DefEmitted) {
CopyMI->getOperand(0).setIsUndef(true);

View File

@ -380,8 +380,8 @@ void VirtRegRewriter::handleIdentityCopy(MachineInstr &MI) const {
++NumIdCopies;
// Copies like:
// %r0 = COPY %r0<undef>
// %al = COPY %al, %eax<imp-def>
// %r0 = COPY undef %r0
// %al = COPY %al, implicit-def %eax
// give us additional liveness information: The target (super-)register
// must not be valid before this point. Replace the COPY with a KILL
// instruction to maintain this information.
@ -488,7 +488,7 @@ void VirtRegRewriter::rewrite() {
if (SubReg != 0) {
if (NoSubRegLiveness) {
// A virtual register kill refers to the whole register, so we may
// have to add <imp-use,kill> operands for the super-register. A
// have to add implicit killed operands for the super-register. A
// partial redef always kills and redefines the super-register.
if ((MO.readsReg() && (MO.isDef() || MO.isKill())) ||
(MO.isDef() && subRegLiveThrough(*MI, PhysReg)))
@ -513,9 +513,9 @@ void VirtRegRewriter::rewrite() {
}
}
// The <def,undef> and <def,internal> flags only make sense for
// The def undef and def internal flags only make sense for
// sub-register defs, and we are substituting a full physreg. An
// <imp-use,kill> operand from the SuperKills list will represent the
// implicit killed operand from the SuperKills list will represent the
// partial read of the super-register.
if (MO.isDef()) {
MO.setIsUndef(false);

View File

@ -161,9 +161,9 @@ namespace {
/// A Chain is a sequence of instructions that are linked together by
/// an accumulation operand. For example:
///
/// fmul d0<def>, ?
/// fmla d1<def>, ?, ?, d0<kill>
/// fmla d2<def>, ?, ?, d1<kill>
/// fmul def d0, ?
/// fmla def d1, ?, ?, killed d0
/// fmla def d2, ?, ?, killed d1
///
/// There may be other instructions interleaved in the sequence that
/// do not belong to the chain. These other instructions must not use

View File

@ -2801,7 +2801,7 @@ MachineInstr *AArch64InstrInfo::foldMemoryOperandImpl(
LiveIntervals *LIS) const {
// This is a bit of a hack. Consider this instruction:
//
// %0<def> = COPY %sp; GPR64all:%0
// %0 = COPY %sp; GPR64all:%0
//
// We explicitly chose GPR64all for the virtual register so such a copy might
// be eliminated by RegisterCoalescer. However, that may not be possible, and
@ -2830,7 +2830,7 @@ MachineInstr *AArch64InstrInfo::foldMemoryOperandImpl(
// Handle the case where a copy is being spilled or filled but the source
// and destination register class don't match. For example:
//
// %0<def> = COPY %xzr; GPR64common:%0
// %0 = COPY %xzr; GPR64common:%0
//
// In this case we can still safely fold away the COPY and generate the
// following spill code:
@ -2840,7 +2840,7 @@ MachineInstr *AArch64InstrInfo::foldMemoryOperandImpl(
// This also eliminates spilled cross register class COPYs (e.g. between x and
// d regs) of the same size. For example:
//
// %0<def> = COPY %1; GPR64:%0, FPR64:%1
// %0 = COPY %1; GPR64:%0, FPR64:%1
//
// will be filled as
//

View File

@ -830,8 +830,8 @@ AArch64LoadStoreOpt::mergePairedInsns(MachineBasicBlock::iterator I,
if (SExtIdx != -1) {
// Generate the sign extension for the proper result of the ldp.
// I.e., with X1, that would be:
// %w1<def> = KILL %w1, %x1<imp-def>
// %x1<def> = SBFMXri %x1<kill>, 0, 31
// %w1 = KILL %w1, implicit-def %x1
// %x1 = SBFMXri killed %x1, 0, 31
MachineOperand &DstMO = MIB->getOperand(SExtIdx);
// Right now, DstMO has the extended register, since it comes from an
// extended opcode.

View File

@ -1450,8 +1450,7 @@ bool AMDGPUMachineCFGStructurizer::shrinkPHI(MachineInstr &PHI,
unsigned *ReplaceReg) {
DEBUG(dbgs() << "Shrink PHI: ");
DEBUG(PHI.dump());
DEBUG(dbgs() << " to " << printReg(getPHIDestReg(PHI), TRI)
<< "<def> = PHI(");
DEBUG(dbgs() << " to " << printReg(getPHIDestReg(PHI), TRI) << " = PHI(");
bool Replaced = false;
unsigned NumInputs = getPHINumInputs(PHI);
@ -1507,8 +1506,7 @@ void AMDGPUMachineCFGStructurizer::replacePHI(
SmallVector<unsigned, 2> &PHIRegionIndices) {
DEBUG(dbgs() << "Replace PHI: ");
DEBUG(PHI.dump());
DEBUG(dbgs() << " with " << printReg(getPHIDestReg(PHI), TRI)
<< "<def> = PHI(");
DEBUG(dbgs() << " with " << printReg(getPHIDestReg(PHI), TRI) << " = PHI(");
bool HasExternalEdge = false;
unsigned NumInputs = getPHINumInputs(PHI);
@ -1566,7 +1564,7 @@ void AMDGPUMachineCFGStructurizer::replaceEntryPHI(
DEBUG(dbgs() << " register " << printReg(CombinedSourceReg, TRI) << "\n");
PHI.eraseFromParent();
} else {
DEBUG(dbgs() << printReg(getPHIDestReg(PHI), TRI) << "<def> = PHI(");
DEBUG(dbgs() << printReg(getPHIDestReg(PHI), TRI) << " = PHI(");
MachineBasicBlock *MBB = PHI.getParent();
MachineInstrBuilder MIB =
BuildMI(*MBB, PHI, PHI.getDebugLoc(), TII->get(TargetOpcode::PHI),
@ -1751,7 +1749,7 @@ void AMDGPUMachineCFGStructurizer::insertMergePHI(MachineBasicBlock *IfBB,
return;
}
DEBUG(dbgs() << "Merge PHI (" << printMBBReference(*MergeBB)
<< "): " << printReg(DestRegister, TRI) << "<def> = PHI("
<< "): " << printReg(DestRegister, TRI) << " = PHI("
<< printReg(IfSourceRegister, TRI) << ", "
<< printMBBReference(*IfBB) << printReg(CodeSourceRegister, TRI)
<< ", " << printMBBReference(*CodeBB) << ")\n");
@ -2147,7 +2145,7 @@ void AMDGPUMachineCFGStructurizer::createEntryPHI(LinearizedRegion *CurrentRegio
const DebugLoc &DL = Entry->findDebugLoc(Entry->begin());
MachineInstrBuilder MIB = BuildMI(*Entry, Entry->instr_begin(), DL,
TII->get(TargetOpcode::PHI), DestReg);
DEBUG(dbgs() << "Entry PHI " << printReg(DestReg, TRI) << "<def> = PHI(");
DEBUG(dbgs() << "Entry PHI " << printReg(DestReg, TRI) << " = PHI(");
unsigned CurrentBackedgeReg = 0;
@ -2172,7 +2170,7 @@ void AMDGPUMachineCFGStructurizer::createEntryPHI(LinearizedRegion *CurrentRegio
BackedgePHI.addMBB((*SRI).second);
CurrentBackedgeReg = NewBackedgeReg;
DEBUG(dbgs() << "Inserting backedge PHI: "
<< printReg(NewBackedgeReg, TRI) << "<def> = PHI("
<< printReg(NewBackedgeReg, TRI) << " = PHI("
<< printReg(CurrentBackedgeReg, TRI) << ", "
<< printMBBReference(*getPHIPred(*PHIDefInstr, 0))
<< ", "
@ -2441,8 +2439,7 @@ void AMDGPUMachineCFGStructurizer::splitLoopPHI(MachineInstr &PHI,
MachineInstrBuilder MIB =
BuildMI(*EntrySucc, EntrySucc->instr_begin(), PHI.getDebugLoc(),
TII->get(TargetOpcode::PHI), NewDestReg);
DEBUG(dbgs() << "Split Entry PHI " << printReg(NewDestReg, TRI)
<< "<def> = PHI(");
DEBUG(dbgs() << "Split Entry PHI " << printReg(NewDestReg, TRI) << " = PHI(");
MIB.addReg(PHISource);
MIB.addMBB(Entry);
DEBUG(dbgs() << printReg(PHISource, TRI) << ", "

View File

@ -144,8 +144,8 @@ def VTX_READ_32_cm
// to be caused by ALU instructions in the next instruction group that wrote
// to the $src_gpr registers of the VTX_READ.
// e.g.
// %t3_x<def> = VTX_READ_PARAM_32_eg %t2_x<kill>, 24
// %t2_x<def> = MOV %zero
// %t3_x = VTX_READ_PARAM_32_eg killed %t2_x, 24
// %t2_x = MOV %zero
//Adding this constraint prevents this from happening.
let Constraints = "$src_gpr.ptr = $dst_gpr";
}

View File

@ -212,8 +212,8 @@ def VTX_READ_32_eg
// to be caused by ALU instructions in the next instruction group that wrote
// to the $src_gpr registers of the VTX_READ.
// e.g.
// %t3_x<def> = VTX_READ_PARAM_32_eg %t2_x<kill>, 24
// %t2_x<def> = MOV %zero
// %t3_x = VTX_READ_PARAM_32_eg killed %t2_x, 24
// %t2_x = MOV %zero
//Adding this constraint prevents this from happening.
let Constraints = "$src_gpr.ptr = $dst_gpr";
}

View File

@ -12,15 +12,15 @@
/// common data and/or have enough undef subreg using swizzle abilities.
///
/// For instance let's consider the following pseudo code :
/// %5<def> = REG_SEQ %1, sub0, %2, sub1, %3, sub2, undef, sub3
/// %5 = REG_SEQ %1, sub0, %2, sub1, %3, sub2, undef, sub3
/// ...
/// %7<def> = REG_SEQ %1, sub0, %3, sub1, undef, sub2, %4, sub3
/// %7 = REG_SEQ %1, sub0, %3, sub1, undef, sub2, %4, sub3
/// (swizzable Inst) %7, SwizzleMask : sub0, sub1, sub2, sub3
///
/// is turned into :
/// %5<def> = REG_SEQ %1, sub0, %2, sub1, %3, sub2, undef, sub3
/// %5 = REG_SEQ %1, sub0, %2, sub1, %3, sub2, undef, sub3
/// ...
/// %7<def> = INSERT_SUBREG %4, sub3
/// %7 = INSERT_SUBREG %4, sub3
/// (swizzable Inst) %7, SwizzleMask : sub0, sub2, sub1, sub3
///
/// This allow regalloc to reduce register pressure for vector registers and

View File

@ -17,8 +17,8 @@
/// %vgpr0 = V_MOV_B32_e32 0.0
/// if (...) {
/// %vgpr1 = ...
/// %vgpr2 = WWM %vgpr1<kill>
/// ... = %vgpr2<kill>
/// %vgpr2 = WWM killed %vgpr1
/// ... = killed %vgpr2
/// %vgpr0 = V_MOV_B32_e32 1.0
/// }
/// ... = %vgpr0

View File

@ -971,9 +971,9 @@ bool SIFoldOperands::runOnMachineFunction(MachineFunction &MF) {
// Prevent folding operands backwards in the function. For example,
// the COPY opcode must not be replaced by 1 in this example:
//
// %3<def> = COPY %vgpr0; VGPR_32:%3
// %3 = COPY %vgpr0; VGPR_32:%3
// ...
// %vgpr0<def> = V_MOV_B32_e32 1, %exec<imp-use>
// %vgpr0 = V_MOV_B32_e32 1, implicit %exec
MachineOperand &Dst = MI.getOperand(0);
if (Dst.isReg() &&
!TargetRegisterInfo::isVirtualRegister(Dst.getReg()))

View File

@ -480,7 +480,7 @@ Optional<int64_t> SIPeepholeSDWA::foldToImm(const MachineOperand &Op) const {
}
// If this is not immediate then it can be copy of immediate value, e.g.:
// %1<def> = S_MOV_B32 255;
// %1 = S_MOV_B32 255;
if (Op.isReg()) {
for (const MachineOperand &Def : MRI->def_operands(Op.getReg())) {
if (!isSameReg(Op, Def))

View File

@ -1447,7 +1447,7 @@ bool ARMBaseInstrInfo::expandPostRAPseudo(MachineInstr &MI) const {
DEBUG(dbgs() << "widening: " << MI);
MachineInstrBuilder MIB(*MI.getParent()->getParent(), MI);
// Get rid of the old <imp-def> of DstRegD. Leave it if it defines a Q-reg
// Get rid of the old implicit-def of DstRegD. Leave it if it defines a Q-reg
// or some other super-register.
int ImpDefIdx = MI.findRegisterDefOperandIdx(DstRegD);
if (ImpDefIdx != -1)
@ -1650,7 +1650,7 @@ bool ARMBaseInstrInfo::produceSameValue(const MachineInstr &MI0,
}
for (unsigned i = 3, e = MI0.getNumOperands(); i != e; ++i) {
// %12<def> = PICLDR %11, 0, pred:14, pred:%noreg
// %12 = PICLDR %11, 0, pred:14, pred:%noreg
const MachineOperand &MO0 = MI0.getOperand(i);
const MachineOperand &MO1 = MI1.getOperand(i);
if (!MO0.isIdenticalTo(MO1))
@ -4668,7 +4668,7 @@ void ARMBaseInstrInfo::setExecutionDomain(MachineInstr &MI,
NewMIB = BuildMI(*MI.getParent(), MI, MI.getDebugLoc(), get(ARM::VEXTd32),
DDst);
// On the first instruction, both DSrc and DDst may be <undef> if present.
// On the first instruction, both DSrc and DDst may be undef if present.
// Specifically when the original instruction didn't have them as an
// <imp-use>.
unsigned CurReg = SrcLane == 1 && DstLane == 1 ? DSrc : DDst;
@ -4688,7 +4688,7 @@ void ARMBaseInstrInfo::setExecutionDomain(MachineInstr &MI,
MIB.addReg(DDst, RegState::Define);
// On the second instruction, DDst has definitely been defined above, so
// it is not <undef>. DSrc, if present, can be <undef> as above.
// it is not undef. DSrc, if present, can be undef as above.
CurReg = SrcLane == 1 && DstLane == 0 ? DSrc : DDst;
CurUndef = CurReg == DSrc && !MI.readsRegister(CurReg, TRI);
MIB.addReg(CurReg, getUndefRegState(CurUndef));
@ -4771,7 +4771,7 @@ unsigned ARMBaseInstrInfo::getPartialRegUpdateClearance(
// We must be able to clobber the whole D-reg.
if (TargetRegisterInfo::isVirtualRegister(Reg)) {
// Virtual register must be a foo:ssub_0<def,undef> operand.
// Virtual register must be a def undef foo:ssub_0 operand.
if (!MO.getSubReg() || MI.readsVirtualRegister(Reg))
return 0;
} else if (ARM::SPRRegClass.contains(Reg)) {

View File

@ -922,7 +922,7 @@ bool ARMExpandPseudo::ExpandCMP_SWAP_64(MachineBasicBlock &MBB,
// .Lloadcmp:
// ldrexd rDestLo, rDestHi, [rAddr]
// cmp rDestLo, rDesiredLo
// sbcs rTempReg<dead>, rDestHi, rDesiredHi
// sbcs dead rTempReg, rDestHi, rDesiredHi
// bne .Ldone
unsigned LDREXD = IsThumb ? ARM::t2LDREXD : ARM::LDREXD;
MachineInstrBuilder MIB;

View File

@ -9168,7 +9168,7 @@ void ARMTargetLowering::AdjustInstrPostInstrSelection(MachineInstr &MI,
// operand is still set to noreg. If needed, set the optional operand's
// register to CPSR, and remove the redundant implicit def.
//
// e.g. ADCS (..., CPSR<imp-def>) -> ADC (... opt:CPSR<def>).
// e.g. ADCS (..., implicit-def CPSR) -> ADC (... opt:def CPSR).
// Rename pseudo opcodes.
unsigned NewOpc = convertAddSubFlagsOpcode(MI.getOpcode());

View File

@ -1697,7 +1697,7 @@ bool ARMLoadStoreOpt::FixInvalidRegPairOp(MachineBasicBlock &MBB,
if (OddReg == EvenReg && EvenDeadKill) {
// If the two source operands are the same, the kill marker is
// probably on the first one. e.g.
// t2STRDi8 %r5<kill>, %r5, %r9<kill>, 0, 14, %reg0
// t2STRDi8 killed %r5, %r5, killed %r9, 0, 14, %reg0
EvenDeadKill = false;
OddDeadKill = true;
}

View File

@ -573,7 +573,7 @@ void BPFDAGToDAGISel::PreprocessTrunc(SDNode *Node,
return;
} else {
// The PHI node looks like:
// %2<def> = PHI %0, <%bb.1>, %1, <%bb.3>
// %2 = PHI %0, <%bb.1>, %1, <%bb.3>
// Trace each incoming definition, e.g., (%0, %bb.1) and (%1, %bb.3)
// The AND operation can be removed if both %0 in %bb.1 and %1 in
// %bb.3 are defined with with a load matching the MaskN.

View File

@ -368,7 +368,7 @@ void HexagonBlockRanges::computeInitialLiveRanges(InstrIndexMap &IndexMap,
}
}
// Defs and clobbers can overlap, e.g.
// %d0<def,dead> = COPY %5, %r0<imp-def>, %r1<imp-def>
// dead %d0 = COPY %5, implicit-def %r0, implicit-def %r1
for (RegisterRef R : Defs)
Clobbers.erase(R);

View File

@ -187,7 +187,7 @@ namespace {
// Mapping: vreg -> cell
// The keys are registers _without_ subregisters. This won't allow
// definitions in the form of "vreg:subreg<def> = ...". Such definitions
// definitions in the form of "vreg:subreg = ...". Such definitions
// would be questionable from the point of view of SSA, since the "vreg"
// could not be initialized in its entirety (specifically, an instruction
// defining the "other part" of "vreg" would also count as a definition
@ -1977,7 +1977,7 @@ bool HexagonConstEvaluator::evaluate(const MachineInstr &MI,
{
const MachineOperand &VO = MI.getOperand(1);
// The operand of CONST32 can be a blockaddress, e.g.
// %0<def> = CONST32 <blockaddress(@eat, %l)>
// %0 = CONST32 <blockaddress(@eat, %l)>
// Do this check for all instructions for safety.
if (!VO.isImm())
return false;
@ -3147,7 +3147,7 @@ bool HexagonConstEvaluator::rewriteHexBranch(MachineInstr &BrI,
BrI.setDesc(JD);
while (BrI.getNumOperands() > 0)
BrI.RemoveOperand(0);
// This ensures that all implicit operands (e.g. %r31<imp-def>, etc)
// This ensures that all implicit operands (e.g. implicit-def %r31, etc)
// are present in the rewritten branch.
for (auto &Op : NI->operands())
BrI.addOperand(Op);

View File

@ -351,11 +351,11 @@ bool HexagonCopyToCombine::isSafeToMoveTogether(MachineInstr &I1,
// kill flag for a register (a removeRegisterKilled() analogous to
// addRegisterKilled) that handles aliased register correctly.
// * or has a killed aliased register use of I1's use reg
// %d4<def> = A2_tfrpi 16
// %r6<def> = A2_tfr %r9
// %r8<def> = KILL %r8, %d4<imp-use,kill>
// %d4 = A2_tfrpi 16
// %r6 = A2_tfr %r9
// %r8 = KILL %r8, implicit killed %d4
// If we want to move R6 = across the KILL instruction we would have
// to remove the %d4<imp-use,kill> operand. For now, we are
// to remove the implicit killed %d4 operand. For now, we are
// conservative and disallow the move.
// we can't move I1 across it.
if (MI.isDebugValue()) {

View File

@ -25,38 +25,38 @@
//
// Example:
//
// %40<def> = L2_loadrub_io %39<kill>, 1
// %41<def> = S2_tstbit_i %40<kill>, 0
// J2_jumpt %41<kill>, <%bb.5>, %pc<imp-def,dead>
// J2_jump <%bb.4>, %pc<imp-def,dead>
// %40 = L2_loadrub_io killed %39, 1
// %41 = S2_tstbit_i killed %40, 0
// J2_jumpt killed %41, <%bb.5>, implicit dead %pc
// J2_jump <%bb.4>, implicit dead %pc
// Successors according to CFG: %bb.4(62) %bb.5(62)
//
// %bb.4: derived from LLVM BB %if.then
// Predecessors according to CFG: %bb.3
// %11<def> = A2_addp %6, %10
// %11 = A2_addp %6, %10
// S2_storerd_io %32, 16, %11
// Successors according to CFG: %bb.5
//
// %bb.5: derived from LLVM BB %if.end
// Predecessors according to CFG: %bb.3 %bb.4
// %12<def> = PHI %6, <%bb.3>, %11, <%bb.4>
// %13<def> = A2_addp %7, %12
// %42<def> = C2_cmpeqi %9, 10
// J2_jumpf %42<kill>, <%bb.3>, %pc<imp-def,dead>
// J2_jump <%bb.6>, %pc<imp-def,dead>
// %12 = PHI %6, <%bb.3>, %11, <%bb.4>
// %13 = A2_addp %7, %12
// %42 = C2_cmpeqi %9, 10
// J2_jumpf killed %42, <%bb.3>, implicit dead %pc
// J2_jump <%bb.6>, implicit dead %pc
// Successors according to CFG: %bb.6(4) %bb.3(124)
//
// would become:
//
// %40<def> = L2_loadrub_io %39<kill>, 1
// %41<def> = S2_tstbit_i %40<kill>, 0
// spec-> %11<def> = A2_addp %6, %10
// %40 = L2_loadrub_io killed %39, 1
// %41 = S2_tstbit_i killed %40, 0
// spec-> %11 = A2_addp %6, %10
// pred-> S2_pstorerdf_io %41, %32, 16, %11
// %46<def> = PS_pselect %41, %6, %11
// %13<def> = A2_addp %7, %46
// %42<def> = C2_cmpeqi %9, 10
// J2_jumpf %42<kill>, <%bb.3>, %pc<imp-def,dead>
// J2_jump <%bb.6>, %pc<imp-def,dead>
// %46 = PS_pselect %41, %6, %11
// %13 = A2_addp %7, %46
// %42 = C2_cmpeqi %9, 10
// J2_jumpf killed %42, <%bb.3>, implicit dead %pc
// J2_jump <%bb.6>, implicit dead %pc
// Successors according to CFG: %bb.6 %bb.3
#include "Hexagon.h"

View File

@ -28,14 +28,14 @@
// definitions are predicable, then in the second step, the conditional
// transfers will then be rewritten as predicated instructions. E.g.
// %0 = A2_or %1, %2
// %3 = A2_tfrt %99, %0<kill>
// %3 = A2_tfrt %99, killed %0
// will be rewritten as
// %3 = A2_port %99, %1, %2
//
// This replacement has two variants: "up" and "down". Consider this case:
// %0 = A2_or %1, %2
// ... [intervening instructions] ...
// %3 = A2_tfrt %99, %0<kill>
// %3 = A2_tfrt %99, killed %0
// variant "up":
// %3 = A2_port %99, %1, %2
// ... [intervening instructions, %0->vreg3] ...
@ -65,15 +65,15 @@
// will see both instructions as actual definitions, and will mark the
// first one as dead. The definition is not actually dead, and this
// situation will need to be fixed. For example:
// %1<def,dead> = A2_tfrt ... ; marked as dead
// %1<def> = A2_tfrf ...
// dead %1 = A2_tfrt ... ; marked as dead
// %1 = A2_tfrf ...
//
// Since any of the individual predicated transfers may end up getting
// removed (in case it is an identity copy), some pre-existing def may
// be marked as dead after live interval recomputation:
// %1<def,dead> = ... ; marked as dead
// dead %1 = ... ; marked as dead
// ...
// %1<def> = A2_tfrf ... ; if A2_tfrt is removed
// %1 = A2_tfrf ... ; if A2_tfrt is removed
// This case happens if %1 was used as a source in A2_tfrt, which means
// that is it actually live at the A2_tfrf, and so the now dead definition
// of %1 will need to be updated to non-dead at some point.

View File

@ -1720,7 +1720,7 @@ bool HexagonHardwareLoops::fixupInductionVariable(MachineLoop *L) {
MachineOperand &MO = PredDef->getOperand(i);
if (MO.isReg()) {
// Skip all implicit references. In one case there was:
// %140<def> = FCMPUGT32_rr %138, %139, %usr<imp-use>
// %140 = FCMPUGT32_rr %138, %139, implicit %usr
if (MO.isImplicit())
continue;
if (MO.isUse()) {

View File

@ -1615,8 +1615,8 @@ DFAPacketizer *HexagonInstrInfo::CreateTargetScheduleState(
}
// Inspired by this pair:
// %r13<def> = L2_loadri_io %r29, 136; mem:LD4[FixedStack0]
// S2_storeri_io %r29, 132, %r1<kill>; flags: mem:ST4[FixedStack1]
// %r13 = L2_loadri_io %r29, 136; mem:LD4[FixedStack0]
// S2_storeri_io %r29, 132, killed %r1; flags: mem:ST4[FixedStack1]
// Currently AA considers the addresses in these instructions to be aliasing.
bool HexagonInstrInfo::areMemAccessesTriviallyDisjoint(
MachineInstr &MIa, MachineInstr &MIb, AliasAnalysis *AA) const {
@ -3515,7 +3515,7 @@ HexagonII::SubInstructionGroup HexagonInstrInfo::getDuplexCandidateGroup(
case Hexagon::EH_RETURN_JMPR:
case Hexagon::PS_jmpret:
// jumpr r31
// Actual form JMPR %pc<imp-def>, %r31<imp-use>, %r0<imp-use,internal>.
// Actual form JMPR implicit-def %pc, implicit %r31, implicit internal %r0
DstReg = MI.getOperand(0).getReg();
if (Hexagon::IntRegsRegClass.contains(DstReg) && (Hexagon::R31 == DstReg))
return HexagonII::HSIG_L2;
@ -3705,7 +3705,7 @@ HexagonII::SubInstructionGroup HexagonInstrInfo::getDuplexCandidateGroup(
case Hexagon::C2_cmovenewif:
// if ([!]P0[.new]) Rd = #0
// Actual form:
// %r16<def> = C2_cmovenewit %p0<internal>, 0, %r16<imp-use,undef>;
// %r16 = C2_cmovenewit internal %p0, 0, implicit undef %r16;
DstReg = MI.getOperand(0).getReg();
SrcReg = MI.getOperand(1).getReg();
if (isIntRegForSubInst(DstReg) &&

View File

@ -129,9 +129,9 @@ static bool canBeFeederToNewValueJump(const HexagonInstrInfo *QII,
// using -- if (QRI->isSubRegister(feederReg, cmpReg1) logic
// before the callsite of this function
// But we can not as it comes in the following fashion.
// %d0<def> = Hexagon_S2_lsr_r_p %d0<kill>, %r2<kill>
// %r0<def> = KILL %r0, %d0<imp-use,kill>
// %p0<def> = CMPEQri %r0<kill>, 0
// %d0 = Hexagon_S2_lsr_r_p killed %d0, killed %r2
// %r0 = KILL %r0, implicit killed %d0
// %p0 = CMPEQri killed %r0, 0
// Hence, we need to check if it's a KILL instruction.
if (II->getOpcode() == TargetOpcode::KILL)
return false;
@ -196,9 +196,9 @@ static bool commonChecksToProhibitNewValueJump(bool afterRA,
// to new value jump. If they are in the path, bail out.
// KILL sets kill flag on the opcode. It also sets up a
// single register, out of pair.
// %d0<def> = S2_lsr_r_p %d0<kill>, %r2<kill>
// %r0<def> = KILL %r0, %d0<imp-use,kill>
// %p0<def> = C2_cmpeqi %r0<kill>, 0
// %d0 = S2_lsr_r_p killed %d0, killed %r2
// %r0 = KILL %r0, implicit killed %d0
// %p0 = C2_cmpeqi killed %r0, 0
// PHI can be anything after RA.
// COPY can remateriaze things in between feeder, compare and nvj.
if (MII->getOpcode() == TargetOpcode::KILL ||

View File

@ -8,27 +8,27 @@
// This peephole pass optimizes in the following cases.
// 1. Optimizes redundant sign extends for the following case
// Transform the following pattern
// %170<def> = SXTW %166
// %170 = SXTW %166
// ...
// %176<def> = COPY %170:isub_lo
// %176 = COPY %170:isub_lo
//
// Into
// %176<def> = COPY %166
// %176 = COPY %166
//
// 2. Optimizes redundant negation of predicates.
// %15<def> = CMPGTrr %6, %2
// %15 = CMPGTrr %6, %2
// ...
// %16<def> = NOT_p %15<kill>
// %16 = NOT_p killed %15
// ...
// JMP_c %16<kill>, <%bb.1>, %pc<imp-def,dead>
// JMP_c killed %16, <%bb.1>, implicit dead %pc
//
// Into
// %15<def> = CMPGTrr %6, %2;
// %15 = CMPGTrr %6, %2;
// ...
// JMP_cNot %15<kill>, <%bb.1>, %pc<imp-def,dead>;
// JMP_cNot killed %15, <%bb.1>, implicit dead %pc;
//
// Note: The peephole pass makes the instrucstions like
// %170<def> = SXTW %166 or %16<def> = NOT_p %15<kill>
// %170 = SXTW %166 or %16 = NOT_p killed %15
// redundant and relies on some form of dead removal instructions, like
// DCE or DIE to actually eliminate them.
@ -132,7 +132,7 @@ bool HexagonPeephole::runOnMachineFunction(MachineFunction &MF) {
NextI = std::next(I);
MachineInstr &MI = *I;
// Look for sign extends:
// %170<def> = SXTW %166
// %170 = SXTW %166
if (!DisableOptSZExt && MI.getOpcode() == Hexagon::A2_sxtw) {
assert(MI.getNumOperands() == 2);
MachineOperand &Dst = MI.getOperand(0);
@ -143,13 +143,13 @@ bool HexagonPeephole::runOnMachineFunction(MachineFunction &MF) {
if (TargetRegisterInfo::isVirtualRegister(DstReg) &&
TargetRegisterInfo::isVirtualRegister(SrcReg)) {
// Map the following:
// %170<def> = SXTW %166
// %170 = SXTW %166
// PeepholeMap[170] = %166
PeepholeMap[DstReg] = SrcReg;
}
}
// Look for %170<def> = COMBINE_ir_V4 (0, %169)
// Look for %170 = COMBINE_ir_V4 (0, %169)
// %170:DoublRegs, %169:IntRegs
if (!DisableOptExtTo64 && MI.getOpcode() == Hexagon::A4_combineir) {
assert(MI.getNumOperands() == 3);
@ -192,14 +192,14 @@ bool HexagonPeephole::runOnMachineFunction(MachineFunction &MF) {
if (TargetRegisterInfo::isVirtualRegister(DstReg) &&
TargetRegisterInfo::isVirtualRegister(SrcReg)) {
// Map the following:
// %170<def> = NOT_xx %166
// %170 = NOT_xx %166
// PeepholeMap[170] = %166
PeepholeMap[DstReg] = SrcReg;
}
}
// Look for copy:
// %176<def> = COPY %170:isub_lo
// %176 = COPY %170:isub_lo
if (!DisableOptSZExt && MI.isCopy()) {
assert(MI.getNumOperands() == 2);
MachineOperand &Dst = MI.getOperand(0);

View File

@ -772,8 +772,8 @@ bool HexagonPacketizerList::canPromoteToNewValueStore(const MachineInstr &MI,
// If data definition is because of implicit definition of the register,
// do not newify the store. Eg.
// %r9<def> = ZXTH %r12, %d6<imp-use>, %r12<imp-def>
// S2_storerh_io %r8, 2, %r12<kill>; mem:ST2[%scevgep343]
// %r9 = ZXTH %r12, implicit %d6, implicit-def %r12
// S2_storerh_io %r8, 2, killed %r12; mem:ST2[%scevgep343]
for (auto &MO : PacketMI.operands()) {
if (MO.isRegMask() && MO.clobbersPhysReg(DepReg))
return false;
@ -787,8 +787,8 @@ bool HexagonPacketizerList::canPromoteToNewValueStore(const MachineInstr &MI,
// Handle imp-use of super reg case. There is a target independent side
// change that should prevent this situation but I am handling it for
// just-in-case. For example, we cannot newify R2 in the following case:
// %r3<def> = A2_tfrsi 0;
// S2_storeri_io %r0<kill>, 0, %r2<kill>, %d1<imp-use,kill>;
// %r3 = A2_tfrsi 0;
// S2_storeri_io killed %r0, 0, killed %r2, implicit killed %d1;
for (auto &MO : MI.operands()) {
if (MO.isReg() && MO.isUse() && MO.isImplicit() && MO.getReg() == DepReg)
return false;
@ -892,12 +892,12 @@ bool HexagonPacketizerList::canPromoteToDotNew(const MachineInstr &MI,
// Go through the packet instructions and search for an anti dependency between
// them and DepReg from MI. Consider this case:
// Trying to add
// a) %r1<def> = TFRI_cdNotPt %p3, 2
// a) %r1 = TFRI_cdNotPt %p3, 2
// to this packet:
// {
// b) %p0<def> = C2_or %p3<kill>, %p0<kill>
// c) %p3<def> = C2_tfrrp %r23
// d) %r1<def> = C2_cmovenewit %p3, 4
// b) %p0 = C2_or killed %p3, killed %p0
// c) %p3 = C2_tfrrp %r23
// d) %r1 = C2_cmovenewit %p3, 4
// }
// The P3 from a) and d) will be complements after
// a)'s P3 is converted to .new form
@ -962,11 +962,11 @@ bool HexagonPacketizerList::arePredicatesComplements(MachineInstr &MI1,
// One corner case deals with the following scenario:
// Trying to add
// a) %r24<def> = A2_tfrt %p0, %r25
// a) %r24 = A2_tfrt %p0, %r25
// to this packet:
// {
// b) %r25<def> = A2_tfrf %p0, %r24
// c) %p0<def> = C2_cmpeqi %r26, 1
// b) %r25 = A2_tfrf %p0, %r24
// c) %p0 = C2_cmpeqi %r26, 1
// }
//
// On general check a) and b) are complements, but presence of c) will
@ -1543,7 +1543,7 @@ bool HexagonPacketizerList::isLegalToPacketizeTogether(SUnit *SUI, SUnit *SUJ) {
// There are certain anti-dependencies that cannot be ignored.
// Specifically:
// J2_call ... %r0<imp-def> ; SUJ
// J2_call ... implicit-def %r0 ; SUJ
// R0 = ... ; SUI
// Those cannot be packetized together, since the call will observe
// the effect of the assignment to R0.

View File

@ -272,7 +272,7 @@ unsigned HexagonMCInstrInfo::getDuplexCandidateGroup(MCInst const &MCI) {
case Hexagon::J2_jumpr:
case Hexagon::PS_jmpret:
// jumpr r31
// Actual form JMPR %pc<imp-def>, %r31<imp-use>, %r0<imp-use,internal>.
// Actual form JMPR implicit-def %pc, implicit %r31, implicit internal %r0.
DstReg = MCI.getOperand(0).getReg();
if (Hexagon::R31 == DstReg)
return HexagonII::HSIG_L2;
@ -471,7 +471,7 @@ unsigned HexagonMCInstrInfo::getDuplexCandidateGroup(MCInst const &MCI) {
case Hexagon::C2_cmovenewif:
// if ([!]P0[.new]) Rd = #0
// Actual form:
// %r16<def> = C2_cmovenewit %p0<internal>, 0, %r16<imp-use,undef>;
// %r16 = C2_cmovenewit internal %p0, 0, implicit undef %r16;
DstReg = MCI.getOperand(0).getReg(); // Rd
PredReg = MCI.getOperand(1).getReg(); // P0
if (HexagonMCInstrInfo::isIntRegForSubInst(DstReg) &&

View File

@ -113,9 +113,10 @@ bool llvm::HexagonMCShuffle(MCContext &Context, bool Fatal,
if (!HexagonMCInstrInfo::bundleSize(MCB)) {
// There once was a bundle:
// BUNDLE %d2<imp-def>, %r4<imp-def>, %r5<imp-def>, %d7<imp-def>, ...
// * %d2<def> = IMPLICIT_DEF; flags:
// * %d7<def> = IMPLICIT_DEF; flags:
// BUNDLE implicit-def %d2, implicit-def %r4, implicit-def %r5,
// implicit-def %d7, ...
// * %d2 = IMPLICIT_DEF; flags:
// * %d7 = IMPLICIT_DEF; flags:
// After the IMPLICIT_DEFs were removed by the asm printer, the bundle
// became empty.
DEBUG(dbgs() << "Skipping empty bundle");
@ -137,9 +138,10 @@ llvm::HexagonMCShuffle(MCContext &Context, MCInstrInfo const &MCII,
if (!HexagonMCInstrInfo::bundleSize(MCB)) {
// There once was a bundle:
// BUNDLE %d2<imp-def>, %r4<imp-def>, %r5<imp-def>, %d7<imp-def>, ...
// * %d2<def> = IMPLICIT_DEF; flags:
// * %d7<def> = IMPLICIT_DEF; flags:
// BUNDLE implicit-def %d2, implicit-def %r4, implicit-def %r5,
// implicit-def %d7, ...
// * %d2 = IMPLICIT_DEF; flags:
// * %d7 = IMPLICIT_DEF; flags:
// After the IMPLICIT_DEFs were removed by the asm printer, the bundle
// became empty.
DEBUG(dbgs() << "Skipping empty bundle");

View File

@ -183,7 +183,7 @@
// This is typically used to prevent keeping registers artificially live
// in cases when they are defined via predicated instructions. For example:
// r0 = add-if-true cond, r10, r11 (1)
// r0 = add-if-false cond, r12, r13, r0<imp-use> (2)
// r0 = add-if-false cond, r12, r13, implicit r0 (2)
// ... = r0 (3)
// Before (1), r0 is not intended to be live, and the use of r0 in (3) is
// not meant to be reached by any def preceding (1). However, since the

View File

@ -480,7 +480,7 @@ MipsInstrInfo::genInstrWithNewOpc(unsigned NewOpc,
MIB = BuildMI(*I->getParent(), I, I->getDebugLoc(), get(NewOpc));
// For MIPSR6 JI*C requires an immediate 0 as an operand, JIALC(64) an
// immediate 0 as an operand and requires the removal of it's %ra<imp-def>
// immediate 0 as an operand and requires the removal of it's implicit-def %ra
// implicit operand as copying the implicit operations of the instructio we're
// looking at will give us the correct flags.
if (NewOpc == Mips::JIC || NewOpc == Mips::JIALC || NewOpc == Mips::JIC64 ||

View File

@ -22,11 +22,11 @@
// This peephole pass optimizes these cases, for example
//
// It will transform the following pattern
// %0<def> = LEA_ADDRi64 %VRFrame, 4
// %1<def> = cvta_to_local_yes_64 %0
// %0 = LEA_ADDRi64 %VRFrame, 4
// %1 = cvta_to_local_yes_64 %0
//
// into
// %1<def> = LEA_ADDRi64 %VRFrameLocal, 4
// %1 = LEA_ADDRi64 %VRFrameLocal, 4
//
// %VRFrameLocal is the virtual register name of %SPL
//

View File

@ -62,9 +62,9 @@ namespace llvm {
/// %bb.0: derived from LLVM BB %entry
/// Live Ins: %f1 %f3 %x6
/// <SNIP1>
/// %0<def> = COPY %f1; F8RC:%0
/// %5<def> = CMPLWI %4<kill>, 0; CRRC:%5 GPRC:%4
/// %8<def> = LXSDX %zero8, %7<kill>, %rm<imp-use>;
/// %0 = COPY %f1; F8RC:%0
/// %5 = CMPLWI killed %4, 0; CRRC:%5 GPRC:%4
/// %8 = LXSDX %zero8, killed %7, implicit %rm;
/// mem:LD8[ConstantPool] F8RC:%8 G8RC:%7
/// BCC 76, %5, <%bb.2>; CRRC:%5
/// Successors according to CFG: %bb.1(?%) %bb.2(?%)
@ -75,7 +75,7 @@ namespace llvm {
///
/// %bb.2: derived from LLVM BB %entry
/// Predecessors according to CFG: %bb.0 %bb.1
/// %9<def> = PHI %8, <%bb.1>, %0, <%bb.0>;
/// %9 = PHI %8, <%bb.1>, %0, <%bb.0>;
/// F8RC:%9,%8,%0
/// <SNIP2>
/// BCC 76, %5, <%bb.4>; CRRC:%5
@ -87,10 +87,10 @@ namespace llvm {
///
/// %bb.4: derived from LLVM BB %entry
/// Predecessors according to CFG: %bb.2 %bb.3
/// %13<def> = PHI %12, <%bb.3>, %2, <%bb.2>;
/// %13 = PHI %12, <%bb.3>, %2, <%bb.2>;
/// F8RC:%13,%12,%2
/// <SNIP3>
/// BLR8 %lr8<imp-use>, %rm<imp-use>, %f1<imp-use>
/// BLR8 implicit %lr8, implicit %rm, implicit %f1
///
/// When this pattern is detected, branch coalescing will try to collapse
/// it by moving code in %bb.2 to %bb.0 and/or %bb.4 and removing %bb.3.
@ -100,9 +100,9 @@ namespace llvm {
/// %bb.0: derived from LLVM BB %entry
/// Live Ins: %f1 %f3 %x6
/// <SNIP1>
/// %0<def> = COPY %f1; F8RC:%0
/// %5<def> = CMPLWI %4<kill>, 0; CRRC:%5 GPRC:%4
/// %8<def> = LXSDX %zero8, %7<kill>, %rm<imp-use>;
/// %0 = COPY %f1; F8RC:%0
/// %5 = CMPLWI killed %4, 0; CRRC:%5 GPRC:%4
/// %8 = LXSDX %zero8, killed %7, implicit %rm;
/// mem:LD8[ConstantPool] F8RC:%8 G8RC:%7
/// <SNIP2>
/// BCC 76, %5, <%bb.4>; CRRC:%5
@ -115,12 +115,12 @@ namespace llvm {
///
/// %bb.4: derived from LLVM BB %entry
/// Predecessors according to CFG: %bb.0 %bb.1
/// %9<def> = PHI %8, <%bb.1>, %0, <%bb.0>;
/// %9 = PHI %8, <%bb.1>, %0, <%bb.0>;
/// F8RC:%9,%8,%0
/// %13<def> = PHI %12, <%bb.1>, %2, <%bb.0>;
/// %13 = PHI %12, <%bb.1>, %2, <%bb.0>;
/// F8RC:%13,%12,%2
/// <SNIP3>
/// BLR8 %lr8<imp-use>, %rm<imp-use>, %f1<imp-use>
/// BLR8 implicit %lr8, implicit %rm, implicit %f1
///
/// Branch Coalescing does not split blocks, it moves everything in the same
/// direction ensuring it does not break use/definition semantics.

View File

@ -2315,10 +2315,10 @@ PPCInstrInfo::isSignOrZeroExtended(const MachineInstr &MI, bool SignExt,
// For a method return value, we check the ZExt/SExt flags in attribute.
// We assume the following code sequence for method call.
// ADJCALLSTACKDOWN 32, %r1<imp-def,dead>, %r1<imp-use>
// ADJCALLSTACKDOWN 32, implicit dead %r1, implicit %r1
// BL8_NOP <ga:@func>,...
// ADJCALLSTACKUP 32, 0, %r1<imp-def,dead>, %r1<imp-use>
// %5<def> = COPY %x3; G8RC:%5
// ADJCALLSTACKUP 32, 0, implicit dead %r1, implicit %r1
// %5 = COPY %x3; G8RC:%5
if (SrcReg == PPC::X3) {
const MachineBasicBlock *MBB = MI.getParent();
MachineBasicBlock::const_instr_iterator II =

View File

@ -585,8 +585,8 @@ bool PPCMIPeephole::simplifyCode(void) {
// We can eliminate RLDICL (e.g. for zero-extension)
// if all bits to clear are already zero in the input.
// This code assume following code sequence for zero-extension.
// %6<def> = COPY %5:sub_32; (optional)
// %8<def> = IMPLICIT_DEF;
// %6 = COPY %5:sub_32; (optional)
// %8 = IMPLICIT_DEF;
// %7<def,tied1> = INSERT_SUBREG %8<tied0>, %6, sub_32;
if (!EnableZExtElimination) break;
@ -685,7 +685,7 @@ bool PPCMIPeephole::simplifyCode(void) {
DEBUG(dbgs() << "Optimizing LI to ADDI: ");
DEBUG(LiMI->dump());
// There could be repeated registers in the PHI, e.g: %1<def> =
// There could be repeated registers in the PHI, e.g: %1 =
// PHI %6, <%bb.2>, %8, <%bb.3>, %8, <%bb.6>; So if we've
// already replaced the def instruction, skip.
if (LiMI->getOpcode() == PPC::ADDI || LiMI->getOpcode() == PPC::ADDI8)

View File

@ -79,8 +79,8 @@ bool PPCQPXLoadSplat::runOnMachineFunction(MachineFunction &MF) {
}
// We're looking for a sequence like this:
// %f0<def> = LFD 0, %x3<kill>, %qf0<imp-def>; mem:LD8[%a](tbaa=!2)
// %qf1<def> = QVESPLATI %qf0<kill>, 0, %rm<imp-use>
// %f0 = LFD 0, killed %x3, implicit-def %qf0; mem:LD8[%a](tbaa=!2)
// %qf1 = QVESPLATI killed %qf0, 0, implicit %rm
for (auto SI = Splats.begin(); SI != Splats.end();) {
MachineInstr *SMI = *SI;

View File

@ -90,21 +90,21 @@ protected:
// This pass is run after register coalescing, and so we're looking for
// a situation like this:
// ...
// %5<def> = COPY %9; VSLRC:%5,%9
// %5 = COPY %9; VSLRC:%5,%9
// %5<def,tied1> = XSMADDADP %5<tied0>, %17, %16,
// %rm<imp-use>; VSLRC:%5,%17,%16
// implicit %rm; VSLRC:%5,%17,%16
// ...
// %9<def,tied1> = XSMADDADP %9<tied0>, %17, %19,
// %rm<imp-use>; VSLRC:%9,%17,%19
// implicit %rm; VSLRC:%9,%17,%19
// ...
// Where we can eliminate the copy by changing from the A-type to the
// M-type instruction. Specifically, for this example, this means:
// %5<def,tied1> = XSMADDADP %5<tied0>, %17, %16,
// %rm<imp-use>; VSLRC:%5,%17,%16
// implicit %rm; VSLRC:%5,%17,%16
// is replaced by:
// %16<def,tied1> = XSMADDMDP %16<tied0>, %18, %9,
// %rm<imp-use>; VSLRC:%16,%18,%9
// and we remove: %5<def> = COPY %9; VSLRC:%5,%9
// implicit %rm; VSLRC:%16,%18,%9
// and we remove: %5 = COPY %9; VSLRC:%5,%9
SlotIndex FMAIdx = LIS->getInstructionIndex(MI);
@ -150,10 +150,10 @@ protected:
// walking the MIs we may as well test liveness here.
//
// FIXME: There is a case that occurs in practice, like this:
// %9<def> = COPY %f1; VSSRC:%9
// %9 = COPY %f1; VSSRC:%9
// ...
// %6<def> = COPY %9; VSSRC:%6,%9
// %7<def> = COPY %9; VSSRC:%7,%9
// %6 = COPY %9; VSSRC:%6,%9
// %7 = COPY %9; VSSRC:%7,%9
// %9<def,tied1> = XSMADDASP %9<tied0>, %1, %4; VSSRC:
// %6<def,tied1> = XSMADDASP %6<tied0>, %1, %2; VSSRC:
// %7<def,tied1> = XSMADDASP %7<tied0>, %1, %3; VSSRC:

View File

@ -436,8 +436,8 @@ bool SystemZElimCompare::optimizeCompareZero(
// Also do a forward search to handle cases where an instruction after the
// compare can be converted like
//
// LTEBRCompare %f0s, %f0s, %cc<imp-def> LTEBRCompare %f0s, %f0s, %cc<imp-def>
// %f2s<def> = LER %f0s
// LTEBRCompare %f0s, %f0s, implicit-def %cc LTEBRCompare %f0s, %f0s,
// implicit-def %cc %f2s = LER %f0s
//
MBBI = Compare, MBBE = MBB.end();
while (++MBBI != MBBE) {

View File

@ -103,20 +103,20 @@ LBB1_3: ## bb
Before regalloc, we have:
%reg1025<def> = IMUL32rri8 %reg1024, 45, %eflags<imp-def>
%reg1025 = IMUL32rri8 %reg1024, 45, implicit-def %eflags
JMP mbb<bb2,0x203afb0>
Successors according to CFG: 0x203afb0 (#3)
bb1: 0x203af60, LLVM BB @0x1e02310, ID#2:
Predecessors according to CFG: 0x203aec0 (#0)
%reg1026<def> = IMUL32rri8 %reg1024, 78, %eflags<imp-def>
%reg1026 = IMUL32rri8 %reg1024, 78, implicit-def %eflags
Successors according to CFG: 0x203afb0 (#3)
bb2: 0x203afb0, LLVM BB @0x1e02340, ID#3:
Predecessors according to CFG: 0x203af10 (#1) 0x203af60 (#2)
%reg1027<def> = PHI %reg1025, mbb<bb,0x203af10>,
%reg1027 = PHI %reg1025, mbb<bb,0x203af10>,
%reg1026, mbb<bb1,0x203af60>
%reg1029<def> = MOVZX64rr32 %reg1027
%reg1029 = MOVZX64rr32 %reg1027
so we'd have to know that IMUL32rri8 leaves the high word zero extended and to
be able to recognize the zero extend. This could also presumably be implemented

View File

@ -191,15 +191,15 @@ bool FixupBWInstPass::runOnMachineFunction(MachineFunction &MF) {
/// %bb.2: derived from LLVM BB %if.then
/// Live Ins: %rdi
/// Predecessors according to CFG: %bb.0
/// %ax<def> = MOV16rm %rdi<kill>, 1, %noreg, 0, %noreg, %eax<imp-def>;
/// %ax = MOV16rm killed %rdi, 1, %noreg, 0, %noreg, implicit-def %eax;
/// mem:LD2[%p]
/// No %eax<imp-use>
/// No implicit %eax
/// Successors according to CFG: %bb.3(?%)
///
/// %bb.3: derived from LLVM BB %if.end
/// Live Ins: %eax Only %ax is actually live
/// Predecessors according to CFG: %bb.2 %bb.1
/// %ax<def> = KILL %ax, %eax<imp-use,kill>
/// %ax = KILL %ax, implicit killed %eax
/// RET 0, %ax
static bool isLive(const MachineInstr &MI,
const LivePhysRegs &LiveRegs,

View File

@ -4469,7 +4469,7 @@ MachineInstr *X86InstrInfo::convertToThreeAddressWithLEA(
unsigned leaInReg2 = 0;
MachineInstr *InsMI2 = nullptr;
if (Src == Src2) {
// ADD16rr %reg1028<kill>, %reg1028
// ADD16rr killed %reg1028, %reg1028
// just a single insert_subreg.
addRegReg(MIB, leaInReg, true, leaInReg, false);
} else {
@ -7633,7 +7633,7 @@ MachineInstr *X86InstrInfo::optimizeLoadInstr(MachineInstr &MI,
/// This is used for mapping:
/// %xmm4 = V_SET0
/// to:
/// %xmm4 = PXORrr %xmm4<undef>, %xmm4<undef>
/// %xmm4 = PXORrr undef %xmm4, undef %xmm4
///
static bool Expand2AddrUndef(MachineInstrBuilder &MIB,
const MCInstrDesc &Desc) {
@ -8197,12 +8197,12 @@ static bool hasUndefRegUpdate(unsigned Opcode) {
///
/// This catches the VCVTSI2SD family of instructions:
///
/// vcvtsi2sdq %rax, %xmm0<undef>, %xmm14
/// vcvtsi2sdq %rax, undef %xmm0, %xmm14
///
/// We should to be careful *not* to catch VXOR idioms which are presumably
/// handled specially in the pipeline:
///
/// vxorps %xmm1<undef>, %xmm1<undef>, %xmm1
/// vxorps undef %xmm1, undef %xmm1, %xmm1
///
/// Like getPartialRegUpdateClearance, this makes a strong assumption that the
/// high bits that are passed-through are not live.
@ -10895,7 +10895,7 @@ X86InstrInfo::getOutliningType(MachineInstr &MI) const {
// FIXME: There are instructions which are being manually built without
// explicit uses/defs so we also have to check the MCInstrDesc. We should be
// able to remove the extra checks once those are fixed up. For example,
// sometimes we might get something like %rax<def> = POP64r 1. This won't be
// sometimes we might get something like %rax = POP64r 1. This won't be
// caught by modifiesRegister or readsRegister even though the instruction
// really ought to be formed so that modifiesRegister/readsRegister would
// catch it.

View File

@ -235,7 +235,7 @@ void VZeroUpperInserter::processBasicBlock(MachineBasicBlock &MBB) {
// If the call has no RegMask, skip it as well. It usually happens on
// helper function calls (such as '_chkstk', '_ftol2') where standard
// calling convention is not used (RegMask is not used to mark register
// clobbered and register usage (def/imp-def/use) is well-defined and
// clobbered and register usage (def/implicit-def/use) is well-defined and
// explicitly specified.
if (IsCall && !callHasRegMask(MI))
continue;

View File

@ -43,7 +43,7 @@ define [1 x double] @constant() {
; The key problem here is that we may fail to create an MBB referenced by a
; PHI. If so, we cannot complete the G_PHI and mustn't try or bad things
; happen.
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: cannot select: G_STORE %6, %2; mem:ST4[%addr] GPR:%6,%2 (in function: pending_phis)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: cannot select: G_STORE %6(s32), %2(p0); mem:ST4[%addr] GPR:%6,%2 (in function: pending_phis)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for pending_phis
; FALLBACK-WITH-REPORT-OUT-LABEL: pending_phis:
define i32 @pending_phis(i1 %tst, i32 %val, i32* %addr) {
@ -63,7 +63,7 @@ false:
}
; General legalizer inability to handle types whose size wasn't a power of 2.
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %1, %0; mem:ST6[%addr](align=8) (in function: odd_type)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %1(s42), %0(p0); mem:ST6[%addr](align=8) (in function: odd_type)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for odd_type
; FALLBACK-WITH-REPORT-OUT-LABEL: odd_type:
define void @odd_type(i42* %addr) {
@ -72,7 +72,7 @@ define void @odd_type(i42* %addr) {
ret void
}
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %1, %0; mem:ST28[%addr](align=32) (in function: odd_vector)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %1(<7 x s32>), %0(p0); mem:ST28[%addr](align=32) (in function: odd_vector)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for odd_vector
; FALLBACK-WITH-REPORT-OUT-LABEL: odd_vector:
define void @odd_vector(<7 x i32>* %addr) {
@ -91,7 +91,7 @@ define i128 @sequence_sizes([8 x i8] %in) {
}
; Just to make sure we don't accidentally emit a normal load/store.
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: cannot select: %2<def>(s64) = G_LOAD %0; mem:LD8[%addr] GPR:%2,%0 (in function: atomic_ops)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: cannot select: %2:gpr(s64) = G_LOAD %0(p0); mem:LD8[%addr] GPR:%2,%0 (in function: atomic_ops)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for atomic_ops
; FALLBACK-WITH-REPORT-LABEL: atomic_ops:
define i64 @atomic_ops(i64* %addr) {
@ -132,14 +132,14 @@ continue:
}
; Check that we fallback on invoke translation failures.
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: %0<def>(s128) = G_FCONSTANT quad 2
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: %0:_(s128) = G_FCONSTANT quad 2
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for test_quad_dump
; FALLBACK-WITH-REPORT-OUT-LABEL: test_quad_dump:
define fp128 @test_quad_dump() {
ret fp128 0xL00000000000000004000000000000000
}
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: %0<def>(p0) = G_EXTRACT_VECTOR_ELT %1, %2; (in function: vector_of_pointers_extractelement)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: %0:_(p0) = G_EXTRACT_VECTOR_ELT %1(<2 x p0>), %2(s32); (in function: vector_of_pointers_extractelement)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for vector_of_pointers_extractelement
; FALLBACK-WITH-REPORT-OUT-LABEL: vector_of_pointers_extractelement:
@var = global <2 x i16*> zeroinitializer
@ -156,7 +156,7 @@ end:
br label %block
}
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %0, %4; mem:ST16[undef] (in function: vector_of_pointers_insertelement)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %0(<2 x p0>), %4(p0); mem:ST16[undef] (in function: vector_of_pointers_insertelement)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for vector_of_pointers_insertelement
; FALLBACK-WITH-REPORT-OUT-LABEL: vector_of_pointers_insertelement:
define void @vector_of_pointers_insertelement() {
@ -172,7 +172,7 @@ end:
br label %block
}
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %1, %3; mem:ST12[undef](align=4) (in function: nonpow2_insertvalue_narrowing)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %1(s96), %3(p0); mem:ST12[undef](align=4) (in function: nonpow2_insertvalue_narrowing)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for nonpow2_insertvalue_narrowing
; FALLBACK-WITH-REPORT-OUT-LABEL: nonpow2_insertvalue_narrowing:
%struct96 = type { float, float, float }
@ -213,7 +213,7 @@ define void @nonpow2_load_narrowing() {
ret void
}
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %3, %0; mem:ST12[%c](align=16) (in function: nonpow2_store_narrowing
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %3(s96), %0(p0); mem:ST12[%c](align=16) (in function: nonpow2_store_narrowing
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for nonpow2_store_narrowing
; FALLBACK-WITH-REPORT-OUT-LABEL: nonpow2_store_narrowing:
define void @nonpow2_store_narrowing(i96* %c) {
@ -223,7 +223,7 @@ define void @nonpow2_store_narrowing(i96* %c) {
ret void
}
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %0, %1; mem:ST12[undef](align=16) (in function: nonpow2_constant_narrowing)
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: G_STORE %0(s96), %1(p0); mem:ST12[undef](align=16) (in function: nonpow2_constant_narrowing)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for nonpow2_constant_narrowing
; FALLBACK-WITH-REPORT-OUT-LABEL: nonpow2_constant_narrowing:
define void @nonpow2_constant_narrowing() {
@ -233,8 +233,8 @@ define void @nonpow2_constant_narrowing() {
; Currently can't handle vector lengths that aren't an exact multiple of
; natively supported vector lengths. Test that the fall-back works for those.
; FALLBACK-WITH-REPORT-ERR-G_IMPLICIT_DEF-LEGALIZABLE: (FIXME: this is what is expected once we can legalize non-pow-of-2 G_IMPLICIT_DEF) remark: <unknown>:0:0: unable to legalize instruction: %1<def>(<7 x s64>) = G_ADD %0, %0; (in function: nonpow2_vector_add_fewerelements
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: %2<def>(s64) = G_EXTRACT_VECTOR_ELT %1, %3; (in function: nonpow2_vector_add_fewerelements)
; FALLBACK-WITH-REPORT-ERR-G_IMPLICIT_DEF-LEGALIZABLE: (FIXME: this is what is expected once we can legalize non-pow-of-2 G_IMPLICIT_DEF) remark: <unknown>:0:0: unable to legalize instruction: %1(<7 x s64>) = G_ADD %0, %0; (in function: nonpow2_vector_add_fewerelements
; FALLBACK-WITH-REPORT-ERR: remark: <unknown>:0:0: unable to legalize instruction: %2:_(s64) = G_EXTRACT_VECTOR_ELT %1(<7 x s64>), %3(s64); (in function: nonpow2_vector_add_fewerelements)
; FALLBACK-WITH-REPORT-ERR: warning: Instruction selection used fallback path for nonpow2_vector_add_fewerelements
; FALLBACK-WITH-REPORT-OUT-LABEL: nonpow2_vector_add_fewerelements:
define void @nonpow2_vector_add_fewerelements() {

View File

@ -9,8 +9,8 @@
...
---
# CHECK: *** Bad machine code: Generic virtual register must have a bank in a RegBankSelected function ***
# CHECK: instruction: %0<def>(s64) = COPY
# CHECK: operand 0: %0<def>
# CHECK: instruction: %0:_(s64) = COPY
# CHECK: operand 0: %0
name: test
regBankSelected: true
registers:

View File

@ -22,11 +22,11 @@ body: |
%0 = COPY %x0
; CHECK: *** Bad machine code: Unexpected generic instruction in a Selected function ***
; CHECK: instruction: %1<def> = G_ADD
; CHECK: instruction: %1:gpr64 = G_ADD
%1 = G_ADD %0, %0
; CHECK: *** Bad machine code: Generic virtual register invalid in a Selected function ***
; CHECK: instruction: %2<def>(s64) = COPY
; CHECK: operand 0: %2<def>
; CHECK: instruction: %2:gpr(s64) = COPY
; CHECK: operand 0: %2
%2(s64) = COPY %x0
...

View File

@ -296,7 +296,7 @@ declare double @hh(double) #1
; Check that we correctly deal with repeated operands.
; The following testcase creates:
; %d1<def> = FADDDrr %d0<kill>, %d0
; %d1 = FADDDrr killed %d0, %d0
; We'll get a crash if we naively look at the first operand, remove it
; from the substitution list then look at the second operand.

View File

@ -1,7 +1,7 @@
; RUN: llc < %s -mtriple=arm64-apple-ios -verify-machineinstrs | FileCheck %s
; LdStOpt bug created illegal instruction:
; %d1<def>, %d2<def> = LDPSi %x0, 1
; %d1, %d2 = LDPSi %x0, 1
; rdar://11512047
%0 = type opaque

View File

@ -11,7 +11,7 @@
; CHECK: Before post-MI-sched:
; CHECK-LABEL: # Machine code for function test1:
; CHECK: SU(2): STRWui %wzr
; CHECK: SU(3): %x21<def>, %x20<def> = LDPXi %sp
; CHECK: SU(3): %x21, %x20 = LDPXi %sp
; CHECK: Predecessors:
; CHECK-NEXT: SU(0): Out
; CHECK-NEXT: SU(0): Out

View File

@ -3,7 +3,7 @@
; Check that the dead register definition pass is considering implicit defs.
; When rematerializing through truncates, the coalescer may produce instructions
; with dead defs, but live implicit-defs of subregs:
; E.g. %x1<def, dead> = MOVi64imm 2, %w1<imp-def>; %x1:GPR64, %w1:GPR32
; E.g. dead %x1 = MOVi64imm 2, implicit-def %w1; %x1:GPR64, %w1:GPR32
; These instructions are live, and their definitions should not be rewritten.
;
; <rdar://problem/16492408>

View File

@ -4,9 +4,9 @@
; CHECK-SSA-LABEL: Machine code for function t1
; CHECK-SSA: [[QUOTREG:%[0-9]+]]<def> = SDIVWr
; CHECK-SSA-NOT: [[QUOTREG]]<def> =
; CHECK-SSA: {{%[0-9]+}}<def> = MSUBWrrr [[QUOTREG]]
; CHECK-SSA: [[QUOTREG:%[0-9]+]]:gpr32 = SDIVWr
; CHECK-SSA-NOT: [[QUOTREG]] =
; CHECK-SSA: {{%[0-9]+}}:gpr32 = MSUBWrrr killed [[QUOTREG]]
; CHECK-SSA-LABEL: Machine code for function t2

View File

@ -6,13 +6,13 @@
; CHECK: ********** MI Scheduling **********
; CHECK-LABEL: ldr_int:%bb.0
; CHECK: Cluster ld/st SU(1) - SU(2)
; CHECK: SU(1): %{{[0-9]+}}<def> = LDRWui
; CHECK: SU(2): %{{[0-9]+}}<def> = LDRWui
; CHECK: SU(1): %{{[0-9]+}}:gpr32 = LDRWui
; CHECK: SU(2): %{{[0-9]+}}:gpr32 = LDRWui
; EXYNOS: ********** MI Scheduling **********
; EXYNOS-LABEL: ldr_int:%bb.0
; EXYNOS: Cluster ld/st SU(1) - SU(2)
; EXYNOS: SU(1): %{{[0-9]+}}<def> = LDRWui
; EXYNOS: SU(2): %{{[0-9]+}}<def> = LDRWui
; EXYNOS: SU(1): %{{[0-9]+}}:gpr32 = LDRWui
; EXYNOS: SU(2): %{{[0-9]+}}:gpr32 = LDRWui
define i32 @ldr_int(i32* %a) nounwind {
%p1 = getelementptr inbounds i32, i32* %a, i32 1
%tmp1 = load i32, i32* %p1, align 2
@ -26,13 +26,13 @@ define i32 @ldr_int(i32* %a) nounwind {
; CHECK: ********** MI Scheduling **********
; CHECK-LABEL: ldp_sext_int:%bb.0
; CHECK: Cluster ld/st SU(1) - SU(2)
; CHECK: SU(1): %{{[0-9]+}}<def> = LDRSWui
; CHECK: SU(2): %{{[0-9]+}}<def> = LDRSWui
; CHECK: SU(1): %{{[0-9]+}}:gpr64 = LDRSWui
; CHECK: SU(2): %{{[0-9]+}}:gpr64 = LDRSWui
; EXYNOS: ********** MI Scheduling **********
; EXYNOS-LABEL: ldp_sext_int:%bb.0
; EXYNOS: Cluster ld/st SU(1) - SU(2)
; EXYNOS: SU(1): %{{[0-9]+}}<def> = LDRSWui
; EXYNOS: SU(2): %{{[0-9]+}}<def> = LDRSWui
; EXYNOS: SU(1): %{{[0-9]+}}:gpr64 = LDRSWui
; EXYNOS: SU(2): %{{[0-9]+}}:gpr64 = LDRSWui
define i64 @ldp_sext_int(i32* %p) nounwind {
%tmp = load i32, i32* %p, align 4
%add.ptr = getelementptr inbounds i32, i32* %p, i64 1
@ -47,13 +47,13 @@ define i64 @ldp_sext_int(i32* %p) nounwind {
; CHECK: ********** MI Scheduling **********
; CHECK-LABEL: ldur_int:%bb.0
; CHECK: Cluster ld/st SU(2) - SU(1)
; CHECK: SU(1): %{{[0-9]+}}<def> = LDURWi
; CHECK: SU(2): %{{[0-9]+}}<def> = LDURWi
; CHECK: SU(1): %{{[0-9]+}}:gpr32 = LDURWi
; CHECK: SU(2): %{{[0-9]+}}:gpr32 = LDURWi
; EXYNOS: ********** MI Scheduling **********
; EXYNOS-LABEL: ldur_int:%bb.0
; EXYNOS: Cluster ld/st SU(2) - SU(1)
; EXYNOS: SU(1): %{{[0-9]+}}<def> = LDURWi
; EXYNOS: SU(2): %{{[0-9]+}}<def> = LDURWi
; EXYNOS: SU(1): %{{[0-9]+}}:gpr32 = LDURWi
; EXYNOS: SU(2): %{{[0-9]+}}:gpr32 = LDURWi
define i32 @ldur_int(i32* %a) nounwind {
%p1 = getelementptr inbounds i32, i32* %a, i32 -1
%tmp1 = load i32, i32* %p1, align 2
@ -67,13 +67,13 @@ define i32 @ldur_int(i32* %a) nounwind {
; CHECK: ********** MI Scheduling **********
; CHECK-LABEL: ldp_half_sext_zext_int:%bb.0
; CHECK: Cluster ld/st SU(3) - SU(4)
; CHECK: SU(3): %{{[0-9]+}}<def> = LDRSWui
; CHECK: SU(4): %{{[0-9]+}}:sub_32<def,read-undef> = LDRWui
; CHECK: SU(3): %{{[0-9]+}}:gpr64 = LDRSWui
; CHECK: SU(4): undef %{{[0-9]+}}.sub_32:gpr64 = LDRWui
; EXYNOS: ********** MI Scheduling **********
; EXYNOS-LABEL: ldp_half_sext_zext_int:%bb.0
; EXYNOS: Cluster ld/st SU(3) - SU(4)
; EXYNOS: SU(3): %{{[0-9]+}}<def> = LDRSWui
; EXYNOS: SU(4): %{{[0-9]+}}:sub_32<def,read-undef> = LDRWui
; EXYNOS: SU(3): %{{[0-9]+}}:gpr64 = LDRSWui
; EXYNOS: SU(4): undef %{{[0-9]+}}.sub_32:gpr64 = LDRWui
define i64 @ldp_half_sext_zext_int(i64* %q, i32* %p) nounwind {
%tmp0 = load i64, i64* %q, align 4
%tmp = load i32, i32* %p, align 4
@ -90,13 +90,13 @@ define i64 @ldp_half_sext_zext_int(i64* %q, i32* %p) nounwind {
; CHECK: ********** MI Scheduling **********
; CHECK-LABEL: ldp_half_zext_sext_int:%bb.0
; CHECK: Cluster ld/st SU(3) - SU(4)
; CHECK: SU(3): %{{[0-9]+}}:sub_32<def,read-undef> = LDRWui
; CHECK: SU(4): %{{[0-9]+}}<def> = LDRSWui
; CHECK: SU(3): undef %{{[0-9]+}}.sub_32:gpr64 = LDRWui
; CHECK: SU(4): %{{[0-9]+}}:gpr64 = LDRSWui
; EXYNOS: ********** MI Scheduling **********
; EXYNOS-LABEL: ldp_half_zext_sext_int:%bb.0
; EXYNOS: Cluster ld/st SU(3) - SU(4)
; EXYNOS: SU(3): %{{[0-9]+}}:sub_32<def,read-undef> = LDRWui
; EXYNOS: SU(4): %{{[0-9]+}}<def> = LDRSWui
; EXYNOS: SU(3): undef %{{[0-9]+}}.sub_32:gpr64 = LDRWui
; EXYNOS: SU(4): %{{[0-9]+}}:gpr64 = LDRSWui
define i64 @ldp_half_zext_sext_int(i64* %q, i32* %p) nounwind {
%tmp0 = load i64, i64* %q, align 4
%tmp = load i32, i32* %p, align 4
@ -113,13 +113,13 @@ define i64 @ldp_half_zext_sext_int(i64* %q, i32* %p) nounwind {
; CHECK: ********** MI Scheduling **********
; CHECK-LABEL: ldr_int_volatile:%bb.0
; CHECK-NOT: Cluster ld/st
; CHECK: SU(1): %{{[0-9]+}}<def> = LDRWui
; CHECK: SU(2): %{{[0-9]+}}<def> = LDRWui
; CHECK: SU(1): %{{[0-9]+}}:gpr32 = LDRWui
; CHECK: SU(2): %{{[0-9]+}}:gpr32 = LDRWui
; EXYNOS: ********** MI Scheduling **********
; EXYNOS-LABEL: ldr_int_volatile:%bb.0
; EXYNOS-NOT: Cluster ld/st
; EXYNOS: SU(1): %{{[0-9]+}}<def> = LDRWui
; EXYNOS: SU(2): %{{[0-9]+}}<def> = LDRWui
; EXYNOS: SU(1): %{{[0-9]+}}:gpr32 = LDRWui
; EXYNOS: SU(2): %{{[0-9]+}}:gpr32 = LDRWui
define i32 @ldr_int_volatile(i32* %a) nounwind {
%p1 = getelementptr inbounds i32, i32* %a, i32 1
%tmp1 = load volatile i32, i32* %p1, align 2
@ -133,8 +133,8 @@ define i32 @ldr_int_volatile(i32* %a) nounwind {
; CHECK: ********** MI Scheduling **********
; CHECK-LABEL: ldq_cluster:%bb.0
; CHECK: Cluster ld/st SU(1) - SU(3)
; CHECK: SU(1): %{{[0-9]+}}<def> = LDRQui
; CHECK: SU(3): %{{[0-9]+}}<def> = LDRQui
; CHECK: SU(1): %{{[0-9]+}}:fpr128 = LDRQui
; CHECK: SU(3): %{{[0-9]+}}:fpr128 = LDRQui
; EXYNOS: ********** MI Scheduling **********
; EXYNOS-LABEL: ldq_cluster:%bb.0
; EXYNOS-NOT: Cluster ld/st

View File

@ -6,7 +6,7 @@
;
; CHECK: ********** MI Scheduling **********
; CHECK: shiftable
; CHECK: SU(2): %2<def> = SUBXri %1, 20, 0
; CHECK: SU(2): %2:gpr64common = SUBXri %1, 20, 0
; CHECK: Successors:
; CHECK-NEXT: SU(4): Data Latency=1 Reg=%2
; CHECK-NEXT: SU(3): Data Latency=2 Reg=%2

View File

@ -5,7 +5,7 @@
;
; CHECK: ********** MI Scheduling **********
; CHECK: misched_bug:%bb.0 entry
; CHECK: SU(2): %2<def> = LDRWui %0, 1; mem:LD4[%ptr1_plus1] GPR32:%2 GPR64common:%0
; CHECK: SU(2): %2:gpr32 = LDRWui %0, 1; mem:LD4[%ptr1_plus1] GPR32:%2 GPR64common:%0
; CHECK: Successors:
; CHECK-NEXT: SU(5): Data Latency=4 Reg=%2
; CHECK-NEXT: SU(4): Ord Latency=0
@ -13,7 +13,7 @@
; CHECK: Successors:
; CHECK: SU(4): Ord Latency=0
; CHECK: SU(4): STRWui %wzr, %1, 0; mem:ST4[%ptr2] GPR64common:%1
; CHECK: SU(5): %w0<def> = COPY %2; GPR32:%2
; CHECK: SU(5): %w0 = COPY %2; GPR32:%2
; CHECK: ** ScheduleDAGMI::schedule picking next node
define i32 @misched_bug(i32* %ptr1, i32* %ptr2) {
entry:

View File

@ -8,7 +8,7 @@
; Check that no scheduling dependencies are created between the paired loads and the store during post-RA MI scheduling.
;
; CHECK-LABEL: # Machine code for function foo:
; CHECK: SU(2): %w{{[0-9]+}}<def>, %w{{[0-9]+}}<def> = LDPWi
; CHECK: SU(2): %w{{[0-9]+}}, %w{{[0-9]+}} = LDPWi
; CHECK: Successors:
; CHECK-NOT: ch SU(4)
; CHECK: SU(3)

View File

@ -22,14 +22,14 @@ tracksRegLiveness: true
body: |
bb.0:
; CHECK: Adding MCLOH_AdrpAdrp:
; CHECK-NEXT: %x1<def> = ADRP <ga:@g3>
; CHECK-NEXT: %x1<def> = ADRP <ga:@g4>
; CHECK-NEXT: %x1 = ADRP <ga:@g3>
; CHECK-NEXT: %x1 = ADRP <ga:@g4>
; CHECK-NEXT: Adding MCLOH_AdrpAdrp:
; CHECK-NEXT: %x1<def> = ADRP <ga:@g2>
; CHECK-NEXT: %x1<def> = ADRP <ga:@g3>
; CHECK-NEXT: %x1 = ADRP <ga:@g2>
; CHECK-NEXT: %x1 = ADRP <ga:@g3>
; CHECK-NEXT: Adding MCLOH_AdrpAdrp:
; CHECK-NEXT: %x0<def> = ADRP <ga:@g0>
; CHECK-NEXT: %x0<def> = ADRP <ga:@g1>
; CHECK-NEXT: %x0 = ADRP <ga:@g0>
; CHECK-NEXT: %x0 = ADRP <ga:@g1>
%x0 = ADRP target-flags(aarch64-page) @g0
%x0 = ADRP target-flags(aarch64-page) @g1
%x1 = ADRP target-flags(aarch64-page) @g2
@ -38,11 +38,11 @@ body: |
bb.1:
; CHECK-NEXT: Adding MCLOH_AdrpAdd:
; CHECK-NEXT: %x20<def> = ADRP <ga:@g0>
; CHECK-NEXT: %x3<def> = ADDXri %x20, <ga:@g0>
; CHECK-NEXT: %x20 = ADRP <ga:@g0>
; CHECK-NEXT: %x3 = ADDXri %x20, <ga:@g0>
; CHECK-NEXT: Adding MCLOH_AdrpAdd:
; CHECK-NEXT: %x1<def> = ADRP <ga:@g0>
; CHECK-NEXT: %x1<def> = ADDXri %x1, <ga:@g0>
; CHECK-NEXT: %x1 = ADRP <ga:@g0>
; CHECK-NEXT: %x1 = ADDXri %x1, <ga:@g0>
%x1 = ADRP target-flags(aarch64-page) @g0
%x9 = SUBXri undef %x11, 5, 0 ; should not affect MCLOH formation
%x1 = ADDXri %x1, target-flags(aarch64-pageoff) @g0, 0
@ -73,11 +73,11 @@ body: |
bb.5:
; CHECK-NEXT: Adding MCLOH_AdrpLdr:
; CHECK-NEXT: %x5<def> = ADRP <ga:@g2>
; CHECK-NEXT: %s6<def> = LDRSui %x5, <ga:@g2>
; CHECK-NEXT: %x5 = ADRP <ga:@g2>
; CHECK-NEXT: %s6 = LDRSui %x5, <ga:@g2>
; CHECK-NEXT: Adding MCLOH_AdrpLdr:
; CHECK-NEXT: %x4<def> = ADRP <ga:@g2>
; CHECK-NEXT: %x4<def> = LDRXui %x4, <ga:@g2>
; CHECK-NEXT: %x4 = ADRP <ga:@g2>
; CHECK-NEXT: %x4 = LDRXui %x4, <ga:@g2>
%x4 = ADRP target-flags(aarch64-page) @g2
%x4 = LDRXui %x4, target-flags(aarch64-pageoff) @g2
%x5 = ADRP target-flags(aarch64-page) @g2
@ -85,11 +85,11 @@ body: |
bb.6:
; CHECK-NEXT: Adding MCLOH_AdrpLdrGot:
; CHECK-NEXT: %x5<def> = ADRP <ga:@g2>
; CHECK-NEXT: %x6<def> = LDRXui %x5, <ga:@g2>
; CHECK-NEXT: %x5 = ADRP <ga:@g2>
; CHECK-NEXT: %x6 = LDRXui %x5, <ga:@g2>
; CHECK-NEXT: Adding MCLOH_AdrpLdrGot:
; CHECK-NEXT: %x4<def> = ADRP <ga:@g2>
; CHECK-NEXT: %x4<def> = LDRXui %x4, <ga:@g2>
; CHECK-NEXT: %x4 = ADRP <ga:@g2>
; CHECK-NEXT: %x4 = LDRXui %x4, <ga:@g2>
%x4 = ADRP target-flags(aarch64-page, aarch64-got) @g2
%x4 = LDRXui %x4, target-flags(aarch64-pageoff, aarch64-got) @g2
%x5 = ADRP target-flags(aarch64-page, aarch64-got) @g2
@ -104,23 +104,23 @@ body: |
bb.8:
; CHECK-NEXT: Adding MCLOH_AdrpAddLdr:
; CHECK-NEXT: %x7<def> = ADRP <ga:@g3>[TF=1]
; CHECK-NEXT: %x8<def> = ADDXri %x7, <ga:@g3>
; CHECK-NEXT: %d1<def> = LDRDui %x8, 8
; CHECK-NEXT: %x7 = ADRP <ga:@g3>[TF=1]
; CHECK-NEXT: %x8 = ADDXri %x7, <ga:@g3>
; CHECK-NEXT: %d1 = LDRDui %x8, 8
%x7 = ADRP target-flags(aarch64-page) @g3
%x8 = ADDXri %x7, target-flags(aarch64-pageoff) @g3, 0
%d1 = LDRDui %x8, 8
bb.9:
; CHECK-NEXT: Adding MCLOH_AdrpAdd:
; CHECK-NEXT: %x3<def> = ADRP <ga:@g3>
; CHECK-NEXT: %x3<def> = ADDXri %x3, <ga:@g3>
; CHECK-NEXT: %x3 = ADRP <ga:@g3>
; CHECK-NEXT: %x3 = ADDXri %x3, <ga:@g3>
; CHECK-NEXT: Adding MCLOH_AdrpAdd:
; CHECK-NEXT: %x5<def> = ADRP <ga:@g3>
; CHECK-NEXT: %x2<def> = ADDXri %x5, <ga:@g3>
; CHECK-NEXT: %x5 = ADRP <ga:@g3>
; CHECK-NEXT: %x2 = ADDXri %x5, <ga:@g3>
; CHECK-NEXT: Adding MCLOH_AdrpAddStr:
; CHECK-NEXT: %x1<def> = ADRP <ga:@g3>
; CHECK-NEXT: %x1<def> = ADDXri %x1, <ga:@g3>
; CHECK-NEXT: %x1 = ADRP <ga:@g3>
; CHECK-NEXT: %x1 = ADDXri %x1, <ga:@g3>
; CHECK-NEXT: STRXui %xzr, %x1, 16
%x1 = ADRP target-flags(aarch64-page) @g3
%x1 = ADDXri %x1, target-flags(aarch64-pageoff) @g3, 0
@ -138,12 +138,12 @@ body: |
bb.10:
; CHECK-NEXT: Adding MCLOH_AdrpLdr:
; CHECK-NEXT: %x2<def> = ADRP <ga:@g3>
; CHECK-NEXT: %x2<def> = LDRXui %x2, <ga:@g3>
; CHECK-NEXT: %x2 = ADRP <ga:@g3>
; CHECK-NEXT: %x2 = LDRXui %x2, <ga:@g3>
; CHECK-NEXT: Adding MCLOH_AdrpLdrGotLdr:
; CHECK-NEXT: %x1<def> = ADRP <ga:@g4>
; CHECK-NEXT: %x1<def> = LDRXui %x1, <ga:@g4>
; CHECK-NEXT: %x1<def> = LDRXui %x1, 24
; CHECK-NEXT: %x1 = ADRP <ga:@g4>
; CHECK-NEXT: %x1 = LDRXui %x1, <ga:@g4>
; CHECK-NEXT: %x1 = LDRXui %x1, 24
%x1 = ADRP target-flags(aarch64-page, aarch64-got) @g4
%x1 = LDRXui %x1, target-flags(aarch64-pageoff, aarch64-got) @g4
%x1 = LDRXui %x1, 24
@ -154,11 +154,11 @@ body: |
bb.11:
; CHECK-NEXT: Adding MCLOH_AdrpLdr
; CHECK-NEXT: %x5<def> = ADRP <ga:@g1>
; CHECK-NEXT: %x5<def> = LDRXui %x5, <ga:@g1>
; CHECK-NEXT: %x5 = ADRP <ga:@g1>
; CHECK-NEXT: %x5 = LDRXui %x5, <ga:@g1>
; CHECK-NEXT: Adding MCLOH_AdrpLdrGotStr:
; CHECK-NEXT: %x1<def> = ADRP <ga:@g4>
; CHECK-NEXT: %x1<def> = LDRXui %x1, <ga:@g4>
; CHECK-NEXT: %x1 = ADRP <ga:@g4>
; CHECK-NEXT: %x1 = LDRXui %x1, <ga:@g4>
; CHECK-NEXT: STRXui %xzr, %x1, 32
%x1 = ADRP target-flags(aarch64-page, aarch64-got) @g4
%x1 = LDRXui %x1, target-flags(aarch64-pageoff, aarch64-got) @g4
@ -171,9 +171,9 @@ body: |
bb.12:
; CHECK-NOT: MCLOH_AdrpAdrp
; CHECK: Adding MCLOH_AdrpAddLdr
; %x9<def> = ADRP <ga:@g4>
; %x9<def> = ADDXri %x9, <ga:@g4>
; %x5<def> = LDRXui %x9, 0
; %x9 = ADRP <ga:@g4>
; %x9 = ADDXri %x9, <ga:@g4>
; %x5 = LDRXui %x9, 0
%x9 = ADRP target-flags(aarch64-page, aarch64-got) @g4
%x9 = ADDXri %x9, target-flags(aarch64-pageoff, aarch64-got) @g4, 0
%x5 = LDRXui %x9, 0

View File

@ -2,18 +2,18 @@
; This file check a bug in MachineCopyPropagation pass. The last COPY will be
; incorrectly removed if the machine instructions are as follows:
; %q5_q6<def> = COPY %q2_q3
; %d5<def> =
; %d3<def> =
; %d3<def> = COPY %d6
; %q5_q6 = COPY %q2_q3
; %d5 =
; %d3 =
; %d3 = COPY %d6
; This is caused by a bug in function SourceNoLongerAvailable(), which fails to
; remove the relationship of D6 and "%q5_q6<def> = COPY %q2_q3".
; remove the relationship of D6 and "%q5_q6 = COPY %q2_q3".
@failed = internal unnamed_addr global i1 false
; CHECK-LABEL: foo:
; CHECK: ld2
; CHECK-NOT: // kill: D{{[0-9]+}}<def> D{{[0-9]+}}<kill>
; CHECK-NOT: // kill: def D{{[0-9]+}} killed D{{[0-9]+}}
define void @foo(<2 x i32> %shuffle251, <8 x i8> %vtbl1.i, i8* %t2, <2 x i32> %vrsubhn_v2.i1364) {
entry:
%val0 = alloca [2 x i64], align 8

View File

@ -7,16 +7,16 @@
# Check that the instructions are not dependent on each other, even though
# they all read/write to the zero register.
# CHECK-LABEL: MI Scheduling
# CHECK: SU(0): %wzr<def,dead> = SUBSWri %w1, 0, 0, %nzcv<imp-def,dead>
# CHECK: SU(0): dead %wzr = SUBSWri %w1, 0, 0, implicit-def dead %nzcv
# CHECK: # succs left : 0
# CHECK-NOT: Successors:
# CHECK: SU(1): %w2<def> = COPY %wzr
# CHECK: SU(1): %w2 = COPY %wzr
# CHECK: # succs left : 0
# CHECK-NOT: Successors:
# CHECK: SU(2): %wzr<def,dead> = SUBSWri %w3, 0, 0, %nzcv<imp-def,dead>
# CHECK: SU(2): dead %wzr = SUBSWri %w3, 0, 0, implicit-def dead %nzcv
# CHECK: # succs left : 0
# CHECK-NOT: Successors:
# CHECK: SU(3): %w4<def> = COPY %wzr
# CHECK: SU(3): %w4 = COPY %wzr
# CHECK: # succs left : 0
# CHECK-NOT: Successors:
name: func

View File

@ -26,15 +26,15 @@ declare void @callee2(i8*, i8*, i8*, i8*, i8*,
; CHECK: fi#-2: {{.*}} fixed, at location [SP+8]
; CHECK: fi#-1: {{.*}} fixed, at location [SP]
; CHECK: [[VRA:%.*]]<def> = LDRXui <fi#-1>
; CHECK: [[VRB:%.*]]<def> = LDRXui <fi#-2>
; CHECK: [[VRA:%.*]]:gpr64 = LDRXui <fi#-1>
; CHECK: [[VRB:%.*]]:gpr64 = LDRXui <fi#-2>
; CHECK: STRXui %{{.*}}, <fi#-4>
; CHECK: STRXui [[VRB]], <fi#-3>
; Make sure that there is an dependence edge between fi#-2 and fi#-4.
; Without this edge the scheduler would be free to move the store accross the load.
; CHECK: SU({{.*}}): [[VRB]]<def> = LDRXui <fi#-2>
; CHECK: SU({{.*}}): [[VRB]]:gpr64 = LDRXui <fi#-2>
; CHECK-NOT: SU
; CHECK: Successors:
; CHECK: SU([[DEPSTOREB:.*]]): Ord Latency=0

View File

@ -5,7 +5,7 @@
; NOOPT: s_load_dwordx2 s[4:5]
; FIXME: Why is the SGPR4_SGPR5 reference being removed from DBG_VALUE?
; NOOPT: ; kill: %sgpr8_sgpr9<def> %sgpr4_sgpr5<kill>
; NOOPT: ; kill: def %sgpr8_sgpr9 killed %sgpr4_sgpr5
; NOOPT-NEXT: ;DEBUG_VALUE: test_debug_value:globalptr_arg <- undef
; GCN: flat_store_dword

View File

@ -4,7 +4,7 @@
# Check there is no SReg_32 pressure created by DS_* instructions because of M0 use
# CHECK: ScheduleDAGMILive::schedule starting
# CHECK: SU({{.*}} = DS_READ_B32 {{.*}} %m0<imp-use>, %exec<imp-use>
# CHECK: SU({{.*}} = DS_READ_B32 {{.*}} implicit %m0, implicit %exec
# CHECK: Pressure Diff : {{$}}
# CHECK: SU({{.*}} DS_WRITE_B32

View File

@ -4,8 +4,8 @@ target triple = "thumbv7-apple-darwin10"
; This tests the fast register allocator's handling of partial redefines:
;
; %reg1028:dsub_0<def>, %reg1028:dsub_1<def> = VLD1q64 %reg1025...
; %reg1030:dsub_1<def> = COPY %reg1028:dsub_0<kill>
; %reg1028:dsub_0, %reg1028:dsub_1 = VLD1q64 %reg1025...
; %reg1030:dsub_1 = COPY killed %reg1028:dsub_0
;
; %reg1028 gets allocated %Q0, and if %reg1030 is reloaded for the partial
; redef, it cannot also get %Q0.

View File

@ -9,7 +9,7 @@ target triple = "thumbv7-apple-ios"
;
; The early-clobber instruction is an str:
;
; %12<earlyclobber,def> = t2STR_PRE %6, %12, 32, pred:14, pred:%noreg
; early-clobber %12 = t2STR_PRE %6, %12, 32, pred:14, pred:%noreg
;
; This tests that shrinkToUses handles the EC redef correctly.

View File

@ -4,7 +4,7 @@
define void @vst(i8* %m, [4 x i64] %v) {
entry:
; CHECK: vst:
; CHECK: VST1d64Q %r{{[0-9]+}}<kill>, 8, %d{{[0-9]+}}, pred:14, pred:%noreg, %q{{[0-9]+}}_q{{[0-9]+}}<imp-use,kill>
; CHECK: VST1d64Q killed %r{{[0-9]+}}, 8, %d{{[0-9]+}}, pred:14, pred:%noreg, implicit killed %q{{[0-9]+}}_q{{[0-9]+}}
%v0 = extractvalue [4 x i64] %v, 0
%v1 = extractvalue [4 x i64] %v, 1
@ -37,7 +37,7 @@ entry:
%struct.__neon_int8x8x4_t = type { <8 x i8>, <8 x i8>, <8 x i8>, <8 x i8> }
define <8 x i8> @vtbx4(<8 x i8>* %A, %struct.__neon_int8x8x4_t* %B, <8 x i8>* %C) nounwind {
; CHECK: vtbx4:
; CHECK: VTBX4 {{.*}}, pred:14, pred:%noreg, %q{{[0-9]+}}_q{{[0-9]+}}<imp-use>
; CHECK: VTBX4 {{.*}}, pred:14, pred:%noreg, implicit %q{{[0-9]+}}_q{{[0-9]+}}
%tmp1 = load <8 x i8>, <8 x i8>* %A
%tmp2 = load %struct.__neon_int8x8x4_t, %struct.__neon_int8x8x4_t* %B
%tmp3 = extractvalue %struct.__neon_int8x8x4_t %tmp2, 0

View File

@ -9,5 +9,5 @@ entry:
ret void
}
; CHECK: tBL pred:14, pred:%noreg, <es:__chkstk>, %lr<imp-def>, %sp<imp-use>, %r4<imp-use,kill>, %r4<imp-def>, %r12<imp-def,dead>, %cpsr<imp-def,dead>
; CHECK: tBL pred:14, pred:%noreg, <es:__chkstk>, implicit-def %lr, implicit %sp, implicit killed %r4, implicit-def %r4, implicit-def dead %r12, implicit-def dead %cpsr

View File

@ -61,7 +61,7 @@ for.end: ; preds = %cond.end
; CHECK: insert_elem
; This test has a sub-register copy with a kill flag:
; %6:ssub_3<def> = COPY %6:ssub_2<kill>; QPR_VFP2:%6
; %6:ssub_3 = COPY killed %6:ssub_2; QPR_VFP2:%6
; The rewriter must do something sensible with that, or the scavenger crashes.
define void @insert_elem() nounwind {
entry:

View File

@ -8,7 +8,7 @@ target triple = "thumbv7-unknown-unknown"
%struct.gs_color_s = type { i16, i16, i16, i16, i8, i8 }
; In this case, the if converter was cloning the return instruction so that we had
; r2<def> = ...
; r2 = ...
; return [pred] r2<dead,def>
; ldr <r2, kill>
; return

View File

@ -33,9 +33,9 @@ for.end: ; preds = %for.body, %entry
; This case was a crasher in constrainLocalCopy.
; The problem was the t2LDR_PRE defining both the global and local lrg.
; CHECK-LABEL: *** Final schedule for %bb.5 ***
; CHECK: %[[R4:[0-9]+]]<def>, %[[R1:[0-9]+]]<def,tied2> = t2LDR_PRE %[[R1]]<tied1>
; CHECK: %{{[0-9]+}}<def> = COPY %[[R1]]
; CHECK: %{{[0-9]+}}<def> = COPY %[[R4]]
; CHECK: %[[R4:[0-9]+]]:gpr, %[[R1:[0-9]+]]:gpr = t2LDR_PRE %[[R1]]
; CHECK: %{{[0-9]+}}:gpr = COPY %[[R1]]
; CHECK: %{{[0-9]+}}:gpr = COPY %[[R4]]
; CHECK-LABEL: MACHINEINSTRS
%struct.rtx_def = type { [4 x i8], [1 x %union.rtunion_def] }
%union.rtunion_def = type { i64 }

View File

@ -37,22 +37,22 @@
}
#
# CHECK: ********** MI Scheduling **********
# CHECK: SU(2): %2<def> = t2MOVi32imm <ga:@g1>; rGPR:%2
# CHECK: SU(2): %2:rgpr = t2MOVi32imm <ga:@g1>; rGPR:%2
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 2
# CHECK_R52: Latency : 2
#
# CHECK: SU(3): %3<def> = t2LDRi12 %2, 0, pred:14, pred:%noreg; mem:LD4[@g1](dereferenceable) rGPR:%3,%2
# CHECK: SU(3): %3:rgpr = t2LDRi12 %2, 0, pred:14, pred:%noreg; mem:LD4[@g1](dereferenceable) rGPR:%3,%2
# CHECK_A9: Latency : 1
# CHECK_SWIFT: Latency : 3
# CHECK_R52: Latency : 4
#
# CHECK : SU(6): %6<def> = t2ADDrr %3, %3, pred:14, pred:%noreg, opt:%noreg; rGPR:%6,%3,%3
# CHECK : SU(6): %6 = t2ADDrr %3, %3, pred:14, pred:%noreg, opt:%noreg; rGPR:%6,%3,%3
# CHECK_A9: Latency : 1
# CHECK_SWIFT: Latency : 1
# CHECK_R52: Latency : 3
# CHECK: SU(7): %7<def> = t2SDIV %6, %5, pred:14, pred:%noreg; rGPR:%7,%6,%5
# CHECK: SU(7): %7:rgpr = t2SDIV %6, %5, pred:14, pred:%noreg; rGPR:%7,%6,%5
# CHECK_A9: Latency : 0
# CHECK_SWIFT: Latency : 14
# CHECK_R52: Latency : 8
@ -62,37 +62,37 @@
# CHECK_SWIFT: Latency : 0
# CHECK_R52: Latency : 4
#
# CHECK: SU(9): %8<def> = t2SMULBB %1, %1, pred:14, pred:%noreg; rGPR:%8,%1,%1
# CHECK: SU(9): %8:rgpr = t2SMULBB %1, %1, pred:14, pred:%noreg; rGPR:%8,%1,%1
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(10): %9<def> = t2SMLABB %0, %0, %8, pred:14, pred:%noreg; rGPR:%9,%0,%0,%8
# CHECK: SU(10): %9:rgpr = t2SMLABB %0, %0, %8, pred:14, pred:%noreg; rGPR:%9,%0,%0,%8
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(11): %10<def> = t2UXTH %9, 0, pred:14, pred:%noreg; rGPR:%10,%9
# CHECK: SU(11): %10:rgpr = t2UXTH %9, 0, pred:14, pred:%noreg; rGPR:%10,%9
# CHECK_A9: Latency : 1
# CHECK_SWIFT: Latency : 1
# CHECK_R52: Latency : 3
#
# CHECK: SU(12): %11<def> = t2MUL %10, %7, pred:14, pred:%noreg; rGPR:%11,%10,%7
# CHECK: SU(12): %11:rgpr = t2MUL %10, %7, pred:14, pred:%noreg; rGPR:%11,%10,%7
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(13): %12<def> = t2MLA %11, %11, %11, pred:14, pred:%noreg; rGPR:%12,%11,%11,%11
# CHECK: SU(13): %12:rgpr = t2MLA %11, %11, %11, pred:14, pred:%noreg; rGPR:%12,%11,%11,%11
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(14): %13<def>, %14<def> = t2UMULL %12, %12, pred:14, pred:%noreg; rGPR:%13,%14,%12,%12
# CHECK: SU(14): %13:rgpr, %14:rgpr = t2UMULL %12, %12, pred:14, pred:%noreg; rGPR:%13,%14,%12,%12
# CHECK_A9: Latency : 3
# CHECK_SWIFT: Latency : 5
# CHECK_R52: Latency : 4
#
# CHECK: SU(18): %19<def,tied4>, %20<def,tied5> = t2UMLAL %12, %12, %19<tied0>, %20<tied1>, pred:14, pred:%noreg; rGPR:%19,%20,%12,%12,%20
# CHECK: SU(18): %19:rgpr, %20:rgpr = t2UMLAL %12, %12, %19, %20, pred:14, pred:%noreg; rGPR:%19,%20,%12,%12,%20
# CHECK_A9: Latency : 3
# CHECK_SWIFT: Latency : 7
# CHECK_R52: Latency : 4

View File

@ -28,37 +28,37 @@
}
# CHECK: ********** MI Scheduling **********
# CHECK: SU(2): %2<def> = SMULBB %1, %1, pred:14, pred:%noreg; GPR:%2,%1,%1
# CHECK: SU(2): %2:gpr = SMULBB %1, %1, pred:14, pred:%noreg; GPR:%2,%1,%1
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(3): %3<def> = SMLABB %0, %0, %2, pred:14, pred:%noreg; GPRnopc:%3,%0,%0 GPR:%2
# CHECK: SU(3): %3:gprnopc = SMLABB %0, %0, %2, pred:14, pred:%noreg; GPRnopc:%3,%0,%0 GPR:%2
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(4): %4<def> = UXTH %3, 0, pred:14, pred:%noreg; GPRnopc:%4,%3
# CHECK: SU(4): %4:gprnopc = UXTH %3, 0, pred:14, pred:%noreg; GPRnopc:%4,%3
# CHECK_A9: Latency : 1
# CHECK_SWIFT: Latency : 1
# CHECK_R52: Latency : 3
#
# CHECK: SU(5): %5<def> = MUL %4, %4, pred:14, pred:%noreg, opt:%noreg; GPRnopc:%5,%4,%4
# CHECK: SU(5): %5:gprnopc = MUL %4, %4, pred:14, pred:%noreg, opt:%noreg; GPRnopc:%5,%4,%4
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(6): %6<def> = MLA %5, %5, %5, pred:14, pred:%noreg, opt:%noreg; GPRnopc:%6,%5,%5,%5
# CHECK: SU(6): %6:gprnopc = MLA %5, %5, %5, pred:14, pred:%noreg, opt:%noreg; GPRnopc:%6,%5,%5,%5
# CHECK_A9: Latency : 2
# CHECK_SWIFT: Latency : 4
# CHECK_R52: Latency : 4
#
# CHECK: SU(7): %7<def>, %8<def> = UMULL %6, %6, pred:14, pred:%noreg, opt:%noreg; GPRnopc:%7,%8,%6,%6
# CHECK: SU(7): %7:gprnopc, %8:gprnopc = UMULL %6, %6, pred:14, pred:%noreg, opt:%noreg; GPRnopc:%7,%8,%6,%6
# CHECK_A9: Latency : 3
# CHECK_SWIFT: Latency : 5
# CHECK_R52: Latency : 4
#
# CHECK: SU(11): %13<def,tied4>, %14<def,tied5> = UMLAL %6, %6, %13<tied0>, %14<tied1>, pred:14, pred:%noreg, opt:%noreg; GPR:%13 GPRnopc:%14,%6,%6
# CHECK: SU(11): %13:gpr, %14:gprnopc = UMLAL %6, %6, %13, %14, pred:14, pred:%noreg, opt:%noreg; GPR:%13 GPRnopc:%14,%6,%6
# CHECK_SWIFT: Latency : 7
# CHECK_A9: Latency : 3
# CHECK_R52: Latency : 4

View File

@ -32,9 +32,9 @@
; debug value as KILL'ed, resulting in a DEBUG_VALUE node changing codegen! (or
; hopefully, triggering an assert).
; CHECK: BUNDLE %itstate<imp-def,dead>
; CHECK: * DBG_VALUE %r1, %noreg, !"u"
; CHECK-NOT: * DBG_VALUE %r1<kill>, %noreg, !"u"
; CHECK: BUNDLE implicit-def dead %itstate
; CHECK: * DBG_VALUE debug-use %r1, debug-use %noreg, !"u"
; CHECK-NOT: * DBG_VALUE killed %r1, %noreg, !"u"
declare arm_aapcscc void @g(%struct.s*, i8*, i32) #1

View File

@ -20,22 +20,22 @@
# CHECK: ********** MI Scheduling **********
# CHECK: ScheduleDAGMILive::schedule starting
# CHECK: SU(1): %1<def> = VLD4d8Pseudo %0, 8, pred:14, pred:%noreg; mem:LD32[%A](align=8) QQPR:%1 GPR:%0
# CHECK: SU(1): %1:qqpr = VLD4d8Pseudo %0, 8, pred:14, pred:%noreg; mem:LD32[%A](align=8) QQPR:%1 GPR:%0
# CHECK: Latency : 8
# CHECK: Single Issue : true;
# CHECK: SU(2): %4<def> = VADDv8i8 %1:dsub_0, %1:dsub_1, pred:14, pred:%noreg; DPR:%4 QQPR:%1
# CHECK: SU(2): %4:dpr = VADDv8i8 %1.dsub_0, %1.dsub_1, pred:14, pred:%noreg; DPR:%4 QQPR:%1
# CHECK: Latency : 5
# CHECK: Single Issue : false;
# CHECK: SU(3): %5<def>, %6<def> = VMOVRRD %4, pred:14, pred:%noreg; GPR:%5,%6 DPR:%4
# CHECK: SU(3): %5:gpr, %6:gpr = VMOVRRD %4, pred:14, pred:%noreg; GPR:%5,%6 DPR:%4
# CHECK: Latency : 4
# CHECK: Single Issue : false;
# TOPDOWN: Scheduling SU(1) %1<def> = VLD4d8Pseudo
# TOPDOWN: Scheduling SU(1) %1:qqpr = VLD4d8Pseudo
# TOPDOWN: Bump cycle to end group
# TOPDOWN: Scheduling SU(2) %4<def> = VADDv8i8
# TOPDOWN: Scheduling SU(2) %4:dpr = VADDv8i8
# BOTTOMUP: Scheduling SU(2) %4<def> = VADDv8i8
# BOTTOMUP: Scheduling SU(1) %1<def> = VLD4d8Pseudo
# BOTTOMUP: Scheduling SU(2) %4:dpr = VADDv8i8
# BOTTOMUP: Scheduling SU(1) %1:qqpr = VLD4d8Pseudo
# BOTTOMUP: Bump cycle to begin group
...

Some files were not shown because too many files have changed in this diff Show More