LLVM 20.0.0git
Macros | Functions | Variables
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...

#include "SIFixSGPRCopies.h"
#include "AMDGPU.h"
#include "GCNSubtarget.h"
#include "MCTargetDesc/AMDGPUMCTargetDesc.h"
#include "llvm/CodeGen/MachineDominators.h"
#include "llvm/InitializePasses.h"
#include "llvm/Target/TargetMachine.h"

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()

static bool foldVGPRCopyIntoRegSequence ( MachineInstr MI,
const SIRegisterInfo TRI,
const SIInstrInfo TII,
MachineRegisterInfo MRI 
)
static

◆ getCopyRegClasses()

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

Definition at line 201 of file SIFixSGPRCopies.cpp.

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

Referenced by foldVGPRCopyIntoRegSequence().

◆ getFirstNonPrologue()

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

◆ hoistAndMergeSGPRInits()

static bool hoistAndMergeSGPRInits ( unsigned  Reg,
const MachineRegisterInfo MRI,
const TargetRegisterInfo TRI,
MachineDominatorTree MDT,
const TargetInstrInfo TII 
)
static

◆ INITIALIZE_PASS_BEGIN()

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

◆ isReachable()

static bool isReachable ( const MachineInstr From,
const MachineInstr To,
const MachineBasicBlock CutOff,
MachineDominatorTree MDT 
)
static

◆ isSafeToFoldImmIntoCopy()

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

◆ isSGPRToVGPRCopy()

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

Definition at line 228 of file SIFixSGPRCopies.cpp.

References TRI.

Referenced by foldVGPRCopyIntoRegSequence().

◆ isVGPRToSGPRCopy()

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

Definition at line 221 of file SIFixSGPRCopies.cpp.

References TRI.

◆ searchPredecessors()

template<class UnaryPredicate >
bool searchPredecessors ( const MachineBasicBlock MBB,
const MachineBasicBlock CutOff,
UnaryPredicate  Predicate 
)

◆ tryChangeVGPRtoSGPRinCopy()

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

Variable Documentation

◆ copies

SI Fix SGPR copies

Definition at line 189 of file SIFixSGPRCopies.cpp.

◆ DEBUG_TYPE

DEBUG_TYPE

Definition at line 189 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 190 of file SIFixSGPRCopies.cpp.