[llvm] AMDGPU: Initialize Module fields in AMDGPUPromoteAllocaImpl (PR #206052)
Matt Arsenault via llvm-commits
llvm-commits at lists.llvm.org
Fri Jun 26 05:48:41 PDT 2026
https://github.com/arsenm created https://github.com/llvm/llvm-project/pull/206052
None
>From 7232a2f399d8f9ba29b5ef0e8427dac5d0328fbc Mon Sep 17 00:00:00 2001
From: Matt Arsenault <Matthew.Arsenault at amd.com>
Date: Fri, 26 Jun 2026 14:47:25 +0200
Subject: [PATCH] AMDGPU: Initialize Module fields in AMDGPUPromoteAllocaImpl
---
.../lib/Target/AMDGPU/AMDGPUPromoteAlloca.cpp | 70 +++++++++----------
1 file changed, 32 insertions(+), 38 deletions(-)
diff --git a/llvm/lib/Target/AMDGPU/AMDGPUPromoteAlloca.cpp b/llvm/lib/Target/AMDGPU/AMDGPUPromoteAlloca.cpp
index 95e06dc8295d9..2223b9d036fa1 100644
--- a/llvm/lib/Target/AMDGPU/AMDGPUPromoteAlloca.cpp
+++ b/llvm/lib/Target/AMDGPU/AMDGPUPromoteAlloca.cpp
@@ -129,8 +129,8 @@ class AMDGPUPromoteAllocaImpl {
private:
const TargetMachine &TM;
LoopInfo &LI;
- Module *Mod = nullptr;
- const DataLayout *DL = nullptr;
+ Module &Mod;
+ const DataLayout &DL;
// FIXME: This should be per-kernel.
uint32_t LocalMemLimit = 0;
@@ -172,9 +172,9 @@ class AMDGPUPromoteAllocaImpl {
void setFunctionLimits(const Function &F);
public:
- AMDGPUPromoteAllocaImpl(TargetMachine &TM, LoopInfo &LI) : TM(TM), LI(LI) {
-
- const Triple &TT = TM.getTargetTriple();
+ AMDGPUPromoteAllocaImpl(TargetMachine &TM, Module &M, LoopInfo &LI)
+ : TM(TM), LI(LI), Mod(M), DL(M.getDataLayout()) {
+ const Triple &TT = M.getTargetTriple();
IsAMDGCN = TT.isAMDGCN();
IsAMDHSA = TT.getOS() == Triple::AMDHSA;
}
@@ -194,7 +194,7 @@ class AMDGPUPromoteAlloca : public FunctionPass {
return false;
if (auto *TPC = getAnalysisIfAvailable<TargetPassConfig>())
return AMDGPUPromoteAllocaImpl(
- TPC->getTM<TargetMachine>(),
+ TPC->getTM<TargetMachine>(), *F.getParent(),
getAnalysis<LoopInfoWrapperPass>().getLoopInfo())
.run(F, /*PromoteToLDS*/ true);
return false;
@@ -211,9 +211,6 @@ class AMDGPUPromoteAlloca : public FunctionPass {
static unsigned getMaxVGPRs(unsigned LDSBytes, const TargetMachine &TM,
const Function &F) {
- if (!TM.getTargetTriple().isAMDGCN())
- return 128;
-
const GCNSubtarget &ST = TM.getSubtarget<GCNSubtarget>(F);
unsigned DynamicVGPRBlockSize = AMDGPU::getDynamicVGPRBlockSize(F);
@@ -253,7 +250,8 @@ char &llvm::AMDGPUPromoteAllocaID = AMDGPUPromoteAlloca::ID;
PreservedAnalyses AMDGPUPromoteAllocaPass::run(Function &F,
FunctionAnalysisManager &AM) {
auto &LI = AM.getResult<LoopAnalysis>(F);
- bool Changed = AMDGPUPromoteAllocaImpl(TM, LI).run(F, /*PromoteToLDS=*/true);
+ bool Changed = AMDGPUPromoteAllocaImpl(TM, *F.getParent(), LI)
+ .run(F, /*PromoteToLDS=*/true);
if (Changed) {
PreservedAnalyses PA;
PA.preserveSet<CFGAnalyses>();
@@ -265,7 +263,8 @@ PreservedAnalyses AMDGPUPromoteAllocaPass::run(Function &F,
PreservedAnalyses
AMDGPUPromoteAllocaToVectorPass::run(Function &F, FunctionAnalysisManager &AM) {
auto &LI = AM.getResult<LoopAnalysis>(F);
- bool Changed = AMDGPUPromoteAllocaImpl(TM, LI).run(F, /*PromoteToLDS=*/false);
+ bool Changed = AMDGPUPromoteAllocaImpl(TM, *F.getParent(), LI)
+ .run(F, /*PromoteToLDS=*/false);
if (Changed) {
PreservedAnalyses PA;
PA.preserveSet<CFGAnalyses>();
@@ -372,11 +371,8 @@ bool AMDGPUPromoteAllocaImpl::run(Function &F, bool PromoteToLDS) {
if (DisablePromoteAllocaToLDS && DisablePromoteAllocaToVector)
return false;
- Mod = F.getParent();
- DL = &Mod->getDataLayout();
-
bool SufficientLDS = PromoteToLDS && hasSufficientLocalMem(F);
- MaxVGPRs = getMaxVGPRs(CurrentLocalMemUsage, TM, F);
+ MaxVGPRs = IsAMDGCN ? getMaxVGPRs(CurrentLocalMemUsage, TM, F) : 128;
setFunctionLimits(F);
unsigned VectorizationBudget =
@@ -422,7 +418,7 @@ bool AMDGPUPromoteAllocaImpl::run(Function &F, bool PromoteToLDS) {
SetVector<IntrinsicInst *> DeferredIntrs;
for (AllocaAnalysis &AA : Allocas) {
if (AA.Vector.Ty) {
- std::optional<TypeSize> Size = AA.Alloca->getAllocationSize(*DL);
+ std::optional<TypeSize> Size = AA.Alloca->getAllocationSize(DL);
assert(Size); // Expected to succeed on non-array alloca.
const unsigned AllocaCost = Size->getFixedValue() * 8;
// First, check if we have enough budget to vectorize this alloca.
@@ -923,9 +919,9 @@ AMDGPUPromoteAllocaImpl::getVectorTypeForAlloca(Type *AllocaTy) const {
}
if (VectorType::isValidElementType(ElemTy) && NumElems > 0) {
- unsigned ElementSize = DL->getTypeSizeInBits(ElemTy) / 8;
+ unsigned ElementSize = DL.getTypeSizeInBits(ElemTy) / 8;
if (ElementSize > 0) {
- unsigned AllocaSize = DL->getTypeStoreSize(AllocaTy);
+ unsigned AllocaSize = DL.getTypeStoreSize(AllocaTy);
// Expand vector if required to match padding of inner type,
// i.e. odd size subvectors.
// Storage size of new vector must match that of alloca for correct
@@ -943,7 +939,7 @@ AMDGPUPromoteAllocaImpl::getVectorTypeForAlloca(Type *AllocaTy) const {
}
const unsigned MaxElements =
- (MaxVectorRegs * 32) / DL->getTypeSizeInBits(VectorTy->getElementType());
+ (MaxVectorRegs * 32) / DL.getTypeSizeInBits(VectorTy->getElementType());
if (VectorTy->getNumElements() > MaxElements ||
VectorTy->getNumElements() < 2) {
@@ -953,8 +949,8 @@ AMDGPUPromoteAllocaImpl::getVectorTypeForAlloca(Type *AllocaTy) const {
}
Type *VecEltTy = VectorTy->getElementType();
- unsigned ElementSizeInBits = DL->getTypeSizeInBits(VecEltTy);
- if (ElementSizeInBits != DL->getTypeAllocSizeInBits(VecEltTy)) {
+ unsigned ElementSizeInBits = DL.getTypeSizeInBits(VecEltTy);
+ if (ElementSizeInBits != DL.getTypeAllocSizeInBits(VecEltTy)) {
LLVM_DEBUG(dbgs() << " Cannot convert to vector if the allocation size "
"does not match the type's size\n");
return nullptr;
@@ -981,7 +977,7 @@ void AMDGPUPromoteAllocaImpl::analyzePromoteToVector(AllocaAnalysis &AA) const {
};
Type *VecEltTy = AA.Vector.Ty->getElementType();
- unsigned ElementSize = DL->getTypeSizeInBits(VecEltTy) / 8;
+ unsigned ElementSize = DL.getTypeSizeInBits(VecEltTy) / 8;
assert(ElementSize > 0);
for (auto *U : AA.Uses) {
Instruction *Inst = cast<Instruction>(U->getUser());
@@ -1005,13 +1001,13 @@ void AMDGPUPromoteAllocaImpl::analyzePromoteToVector(AllocaAnalysis &AA) const {
// Alloca already accessed as vector.
if (Ptr == AA.Alloca &&
- DL->getTypeStoreSize(AA.Alloca->getAllocatedType()) ==
- DL->getTypeStoreSize(AccessTy)) {
+ DL.getTypeStoreSize(AA.Alloca->getAllocatedType()) ==
+ DL.getTypeStoreSize(AccessTy)) {
AA.Vector.Worklist.push_back(Inst);
continue;
}
- if (!isSupportedAccessType(AA.Vector.Ty, AccessTy, *DL))
+ if (!isSupportedAccessType(AA.Vector.Ty, AccessTy, DL))
return RejectUser(Inst, "not a supported access type");
AA.Vector.Worklist.push_back(Inst);
@@ -1021,7 +1017,7 @@ void AMDGPUPromoteAllocaImpl::analyzePromoteToVector(AllocaAnalysis &AA) const {
if (auto *GEP = dyn_cast<GetElementPtrInst>(Inst)) {
// If we can't compute a vector index from this GEP, then we can't
// promote this alloca to vector.
- auto Index = computeGEPToVectorIndex(GEP, AA.Alloca, VecEltTy, *DL);
+ auto Index = computeGEPToVectorIndex(GEP, AA.Alloca, VecEltTy, DL);
if (!Index)
return RejectUser(Inst, "cannot compute vector index for GEP");
@@ -1031,7 +1027,7 @@ void AMDGPUPromoteAllocaImpl::analyzePromoteToVector(AllocaAnalysis &AA) const {
}
if (MemSetInst *MSI = dyn_cast<MemSetInst>(Inst);
- MSI && isSupportedMemset(MSI, AA.Alloca, *DL)) {
+ MSI && isSupportedMemset(MSI, AA.Alloca, DL)) {
AA.Vector.Worklist.push_back(Inst);
continue;
}
@@ -1117,10 +1113,10 @@ void AMDGPUPromoteAllocaImpl::promoteAllocaToVector(AllocaAnalysis &AA) {
LLVM_DEBUG(dbgs() << "Promoting to vectors: " << *AA.Alloca << '\n');
LLVM_DEBUG(dbgs() << " type conversion: " << *AA.Alloca->getAllocatedType()
<< " -> " << *AA.Vector.Ty << '\n');
- const unsigned VecStoreSize = DL->getTypeStoreSize(AA.Vector.Ty);
+ const unsigned VecStoreSize = DL.getTypeStoreSize(AA.Vector.Ty);
Type *VecEltTy = AA.Vector.Ty->getElementType();
- const unsigned ElementSize = DL->getTypeSizeInBits(VecEltTy) / 8;
+ const unsigned ElementSize = DL.getTypeSizeInBits(VecEltTy) / 8;
// Alloca is uninitialized memory. Imitate that by making the first value
// undef.
@@ -1159,7 +1155,7 @@ void AMDGPUPromoteAllocaImpl::promoteAllocaToVector(AllocaAnalysis &AA) {
return Placeholders.back();
};
- Value *Result = promoteAllocaUserToVector(I, *DL, AA, VecStoreSize,
+ Value *Result = promoteAllocaUserToVector(I, DL, AA, VecStoreSize,
ElementSize, GetCurVal);
// If the returned result is a placeholder, it means the instruction does
// not really modify the alloca. So no need to make it being available value
@@ -1257,7 +1253,7 @@ AMDGPUPromoteAllocaImpl::getLocalSizeYZ(IRBuilder<> &Builder) {
// Size of the dispatch packet struct.
DispatchPtr->addDereferenceableRetAttr(64);
- Type *I32Ty = Type::getInt32Ty(Mod->getContext());
+ Type *I32Ty = Type::getInt32Ty(Mod.getContext());
// We could do a single 64-bit load here, but it's likely that the basic
// 32-bit and extract sequence is already present, and it is probably easier
@@ -1268,7 +1264,7 @@ AMDGPUPromoteAllocaImpl::getLocalSizeYZ(IRBuilder<> &Builder) {
Value *GEPZU = Builder.CreateConstInBoundsGEP1_64(I32Ty, DispatchPtr, 2);
LoadInst *LoadZU = Builder.CreateAlignedLoad(I32Ty, GEPZU, Align(4));
- MDNode *MD = MDNode::get(Mod->getContext(), {});
+ MDNode *MD = MDNode::get(Mod.getContext(), {});
LoadXY->setMetadata(LLVMContext::MD_invariant_load, MD);
LoadZU->setMetadata(LLVMContext::MD_invariant_load, MD);
ST.makeLIDRangeMetadata(LoadZU);
@@ -1307,7 +1303,7 @@ Value *AMDGPUPromoteAllocaImpl::getWorkitemID(IRBuilder<> &Builder,
llvm_unreachable("invalid dimension");
}
- Function *WorkitemIdFn = Intrinsic::getOrInsertDeclaration(Mod, IntrID);
+ Function *WorkitemIdFn = Intrinsic::getOrInsertDeclaration(&Mod, IntrID);
CallInst *CI = Builder.CreateCall(WorkitemIdFn);
ST.makeLIDRangeMetadata(CI);
F->removeFnAttr(AttrName);
@@ -1507,7 +1503,7 @@ bool AMDGPUPromoteAllocaImpl::hasSufficientLocalMem(const Function &F) {
return false;
};
- for (GlobalVariable &GV : Mod->globals()) {
+ for (GlobalVariable &GV : Mod.globals()) {
if (GV.getAddressSpace() != AMDGPUAS::LOCAL_ADDRESS)
continue;
@@ -1529,7 +1525,6 @@ bool AMDGPUPromoteAllocaImpl::hasSufficientLocalMem(const Function &F) {
}
}
- const DataLayout &DL = Mod->getDataLayout();
SmallVector<std::pair<uint64_t, Align>, 16> AllocatedSizes;
AllocatedSizes.reserve(UsedLDS.size());
@@ -1603,7 +1598,6 @@ bool AMDGPUPromoteAllocaImpl::tryPromoteAllocaToLDS(
if (!SufficientLDS)
return false;
- const DataLayout &DL = Mod->getDataLayout();
IRBuilder<> Builder(AA.Alloca);
const Function &ContainingFunction = *AA.Alloca->getParent()->getParent();
@@ -1639,7 +1633,7 @@ bool AMDGPUPromoteAllocaImpl::tryPromoteAllocaToLDS(
Type *GVTy = ArrayType::get(AA.Alloca->getAllocatedType(), WorkGroupSize);
GlobalVariable *GV = new GlobalVariable(
- *Mod, GVTy, false, GlobalValue::InternalLinkage, PoisonValue::get(GVTy),
+ Mod, GVTy, false, GlobalValue::InternalLinkage, PoisonValue::get(GVTy),
Twine(F->getName()) + Twine('.') + AA.Alloca->getName(), nullptr,
GlobalVariable::NotThreadLocal, AMDGPUAS::LOCAL_ADDRESS);
GV->setUnnamedAddr(GlobalValue::UnnamedAddr::Global);
@@ -1658,7 +1652,7 @@ bool AMDGPUPromoteAllocaImpl::tryPromoteAllocaToLDS(
Value *TID = Builder.CreateAdd(Tmp0, Tmp1);
TID = Builder.CreateAdd(TID, TIdZ);
- LLVMContext &Context = Mod->getContext();
+ LLVMContext &Context = Mod.getContext();
Value *Indices[] = {Constant::getNullValue(Type::getInt32Ty(Context)), TID};
Value *Offset = Builder.CreateInBoundsGEP(GVTy, GV, Indices);
More information about the llvm-commits
mailing list