LLVM 22.0.0git
SIFixSGPRCopies.cpp File Reference

Copies from VGPR to SGPR registers are illegal and the register coalescer will sometimes generate these illegal copies in situations like this: More...

Go to the source code of this file.

Macros

#define DEBUG_TYPE   "si-fix-sgpr-copies"

Functions

 INITIALIZE_PASS_BEGIN (SIFixSGPRCopiesLegacy, DEBUG_TYPE, "SI Fix SGPR copies", false, false) INITIALIZE_PASS_END(SIFixSGPRCopiesLegacy
static std::pair< const TargetRegisterClass *, const TargetRegisterClass * > getCopyRegClasses (const MachineInstr &Copy, const SIRegisterInfo &TRI, const MachineRegisterInfo &MRI)
static bool isVGPRToSGPRCopy (const TargetRegisterClass *SrcRC, const TargetRegisterClass *DstRC, const SIRegisterInfo &TRI)
static bool isSGPRToVGPRCopy (const TargetRegisterClass *SrcRC, const TargetRegisterClass *DstRC, const SIRegisterInfo &TRI)
static bool tryChangeVGPRtoSGPRinCopy (MachineInstr &MI, const SIRegisterInfo *TRI, const SIInstrInfo *TII)
static bool foldVGPRCopyIntoRegSequence (MachineInstr &MI, const SIRegisterInfo *TRI, const SIInstrInfo *TII, MachineRegisterInfo &MRI)
static bool isSafeToFoldImmIntoCopy (const MachineInstr *Copy, const MachineInstr *MoveImm, const SIInstrInfo *TII, unsigned &SMovOp, int64_t &Imm)
template<class UnaryPredicate>
bool searchPredecessors (const MachineBasicBlock *MBB, const MachineBasicBlock *CutOff, UnaryPredicate Predicate)
static bool isReachable (const MachineInstr *From, const MachineInstr *To, const MachineBasicBlock *CutOff, MachineDominatorTree &MDT)
static MachineBasicBlock::iterator getFirstNonPrologue (MachineBasicBlock *MBB, const TargetInstrInfo *TII)
static bool hoistAndMergeSGPRInits (unsigned Reg, const MachineRegisterInfo &MRI, const TargetRegisterInfo *TRI, MachineDominatorTree &MDT, const TargetInstrInfo *TII)

Variables

static cl::opt< boolEnableM0Merge ("amdgpu-enable-merge-m0", cl::desc("Merge and hoist M0 initializations"), cl::init(true))
 DEBUG_TYPE
SI Fix SGPR copies
SI Fix SGPR false

Detailed Description

Copies from VGPR to SGPR registers are illegal and the register coalescer will sometimes generate these illegal copies in situations like this:

Register Class <vsrc> is the union of <vgpr> and <sgpr>

BB0: %0 <sgpr> = SCALAR_INST %1 <vsrc> = COPY %0 <sgpr> ... BRANCH cond BB1, BB2 BB1: %2 <vgpr> = VECTOR_INST %3 <vsrc> = COPY %2 <vgpr> BB2: %4 <vsrc> = PHI %1 <vsrc>, <bb.0>, %3 <vrsc>, <bb.1> %5 <vgpr> = VECTOR_INST %4 <vsrc>

The coalescer will begin at BB0 and eliminate its copy, then the resulting code will look like this:

BB0: %0 <sgpr> = SCALAR_INST ... BRANCH cond BB1, BB2 BB1: %2 <vgpr> = VECTOR_INST %3 <vsrc> = COPY %2 <vgpr> BB2: %4 <sgpr> = PHI %0 <sgpr>, <bb.0>, %3 <vsrc>, <bb.1> %5 <vgpr> = VECTOR_INST %4 <sgpr>

Now that the result of the PHI instruction is an SGPR, the register allocator is now forced to constrain the register class of %3 to <sgpr> so we end up with final code like this:

BB0: %0 <sgpr> = SCALAR_INST ... BRANCH cond BB1, BB2 BB1: %2 <vgpr> = VECTOR_INST %3 <sgpr> = COPY %2 <vgpr> BB2: %4 <sgpr> = PHI %0 <sgpr>, <bb.0>, %3 <sgpr>, <bb.1> %5 <vgpr> = VECTOR_INST %4 <sgpr>

Now this code contains an illegal copy from a VGPR to an SGPR.

In order to avoid this problem, this pass searches for PHI instructions which define a <vsrc> register and constrains its definition class to <vgpr> if the user of the PHI's definition register is a vector instruction. If the PHI's definition class is constrained to <vgpr> then the coalescer will be unable to perform the COPY removal from the above example which ultimately led to the creation of an illegal COPY.

Definition in file SIFixSGPRCopies.cpp.

Macro Definition Documentation

◆ DEBUG_TYPE

#define DEBUG_TYPE   "si-fix-sgpr-copies"

Definition at line 77 of file SIFixSGPRCopies.cpp.

Function Documentation

◆ foldVGPRCopyIntoRegSequence()

◆ getCopyRegClasses()

std::pair< const TargetRegisterClass *, const TargetRegisterClass * > getCopyRegClasses ( const MachineInstr & Copy,
const SIRegisterInfo & TRI,
const MachineRegisterInfo & MRI )
static

Definition at line 203 of file SIFixSGPRCopies.cpp.

References llvm::Register::isVirtual(), MRI, and TRI.

Referenced by foldVGPRCopyIntoRegSequence().

◆ getFirstNonPrologue()

MachineBasicBlock::iterator getFirstNonPrologue ( MachineBasicBlock * MBB,
const TargetInstrInfo * TII )
static

Definition at line 440 of file SIFixSGPRCopies.cpp.

References I, MBB, and TII.

Referenced by hoistAndMergeSGPRInits().

◆ hoistAndMergeSGPRInits()

◆ INITIALIZE_PASS_BEGIN()

INITIALIZE_PASS_BEGIN ( SIFixSGPRCopiesLegacy ,
DEBUG_TYPE ,
"SI Fix SGPR copies" ,
false ,
false  )

◆ isReachable()

◆ isSafeToFoldImmIntoCopy()

bool isSafeToFoldImmIntoCopy ( const MachineInstr * Copy,
const MachineInstr * MoveImm,
const SIInstrInfo * TII,
unsigned & SMovOp,
int64_t & Imm )
static

◆ isSGPRToVGPRCopy()

bool isSGPRToVGPRCopy ( const TargetRegisterClass * SrcRC,
const TargetRegisterClass * DstRC,
const SIRegisterInfo & TRI )
static

Definition at line 230 of file SIFixSGPRCopies.cpp.

References TRI.

Referenced by foldVGPRCopyIntoRegSequence().

◆ isVGPRToSGPRCopy()

bool isVGPRToSGPRCopy ( const TargetRegisterClass * SrcRC,
const TargetRegisterClass * DstRC,
const SIRegisterInfo & TRI )
static

Definition at line 223 of file SIFixSGPRCopies.cpp.

References TRI.

◆ searchPredecessors()

◆ tryChangeVGPRtoSGPRinCopy()

bool tryChangeVGPRtoSGPRinCopy ( MachineInstr & MI,
const SIRegisterInfo * TRI,
const SIInstrInfo * TII )
static

Definition at line 237 of file SIFixSGPRCopies.cpp.

References llvm::Register::isVirtual(), MI, MRI, OpIdx, TII, TRI, and UseMI.

Referenced by foldVGPRCopyIntoRegSequence().

Variable Documentation

◆ copies

SI Fix SGPR copies

Definition at line 191 of file SIFixSGPRCopies.cpp.

◆ DEBUG_TYPE

DEBUG_TYPE

Definition at line 191 of file SIFixSGPRCopies.cpp.

◆ EnableM0Merge

cl::opt< bool > EnableM0Merge("amdgpu-enable-merge-m0", cl::desc("Merge and hoist M0 initializations"), cl::init(true)) ( "amdgpu-enable-merge-m0" ,
cl::desc("Merge and hoist M0 initializations") ,
cl::init(true)  )
static

◆ false

SI Fix SGPR false

Definition at line 192 of file SIFixSGPRCopies.cpp.