[llvm] 2c88996 - [SPIR-V][NewPM] Port SPIRVModuleAnalysis (#227376)
via llvm-commits
llvm-commits at lists.llvm.org
Wed Oct 7 03:49:36 PDT 2026
Author: Arseniy Obolenskiy
Date: 2026-10-07T10:49:21Z
New Revision: 2c8899609919bbc8afd59b69424ea8487f9396db
URL: https://github.com/llvm/llvm-project/commit/2c8899609919bbc8afd59b69424ea8487f9396db
DIFF: https://github.com/llvm/llvm-project/commit/2c8899609919bbc8afd59b69424ea8487f9396db.diff
LOG: [SPIR-V][NewPM] Port SPIRVModuleAnalysis (#227376)
This step enables us with e2e compilation with new pass manager
Added:
Modified:
llvm/lib/Target/SPIRV/SPIRV.h
llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp
llvm/lib/Target/SPIRV/SPIRVCodeGenPassBuilder.cpp
llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp
llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.h
llvm/lib/Target/SPIRV/SPIRVPassRegistry.def
llvm/lib/Target/SPIRV/SPIRVTargetMachine.cpp
llvm/test/CodeGen/SPIRV/llc-pipeline.ll
Removed:
################################################################################
diff --git a/llvm/lib/Target/SPIRV/SPIRV.h b/llvm/lib/Target/SPIRV/SPIRV.h
index ccc7aa52ec52c..1c8e881c307b7 100644
--- a/llvm/lib/Target/SPIRV/SPIRV.h
+++ b/llvm/lib/Target/SPIRV/SPIRV.h
@@ -178,7 +178,7 @@ createSPIRVInstructionSelector(const SPIRVTargetMachine &TM,
const SPIRVSubtarget &Subtarget,
const RegisterBankInfo &RBI);
-void initializeSPIRVModuleAnalysisPass(PassRegistry &);
+void initializeSPIRVModuleAnalysisWrapperPassPass(PassRegistry &);
void initializeSPIRVAsmPrinterPass(PassRegistry &);
void initializeSPIRVConvergenceRegionAnalysisWrapperPassPass(PassRegistry &);
void initializeSPIRVPreLegalizerLegacyPass(PassRegistry &);
diff --git a/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp b/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp
index 11f8674730a2e..685a4f553ca2a 100644
--- a/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp
+++ b/llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp
@@ -74,7 +74,11 @@ class SPIRVAsmPrinter : public AsmPrinter {
explicit SPIRVAsmPrinter(TargetMachine &TM,
std::unique_ptr<MCStreamer> Streamer)
: AsmPrinter(TM, std::move(Streamer), ID), ModuleSectionsEmitted(false),
- ST(nullptr), TII(nullptr), MAI(nullptr) {}
+ ST(nullptr), TII(nullptr), MAI(nullptr) {
+ GetMAI = [this] {
+ return &getAnalysis<SPIRVModuleAnalysisWrapperPass>().MAI;
+ };
+ }
static char ID;
bool ModuleSectionsEmitted;
const SPIRVSubtarget *ST;
@@ -129,6 +133,7 @@ class SPIRVAsmPrinter : public AsmPrinter {
void getAnalysisUsage(AnalysisUsage &AU) const override;
SPIRV::ModuleAnalysisInfo *MAI;
+ std::function<SPIRV::ModuleAnalysisInfo *()> GetMAI;
// Non-owning pointer to the NSDI handler registered via addAsmPrinterHandler.
// The handler's lifetime is managed by AsmPrinter (the base class of this
@@ -143,8 +148,8 @@ class SPIRVAsmPrinter : public AsmPrinter {
} // namespace
void SPIRVAsmPrinter::getAnalysisUsage(AnalysisUsage &AU) const {
- AU.addRequired<SPIRVModuleAnalysis>();
- AU.addPreserved<SPIRVModuleAnalysis>();
+ AU.addRequired<SPIRVModuleAnalysisWrapperPass>();
+ AU.addPreserved<SPIRVModuleAnalysisWrapperPass>();
AsmPrinter::getAnalysisUsage(AU);
}
@@ -890,7 +895,7 @@ void SPIRVAsmPrinter::outputModuleSections() {
// Get the global subtarget to output module-level info.
ST = static_cast<const SPIRVTargetMachine &>(TM).getSubtargetImpl();
TII = ST->getInstrInfo();
- MAI = &getAnalysis<SPIRVModuleAnalysis>().MAI;
+ MAI = GetMAI();
assert(ST && TII && MAI && M && "Module analysis is required");
if (!AuxDataHandler) {
@@ -998,6 +1003,10 @@ SPIRVAsmPrinterPass::run(MachineFunction &MF,
.getCachedResult<AsmPrinterAnalysis>(*MF.getFunction().getParent())
->getPrinter());
setupMachineFunctionAsmPrinter(MFAM, MF, AsmPrinter);
+ AsmPrinter.GetMAI = [&MFAM, &MF] {
+ return MFAM.getResult<ModuleAnalysisManagerMachineFunctionProxy>(MF)
+ .getCachedResult<SPIRVModuleAnalysis>(*MF.getFunction().getParent());
+ };
AsmPrinter.runOnMachineFunction(MF);
return PreservedAnalyses::all();
}
@@ -1007,6 +1016,9 @@ PreservedAnalyses SPIRVAsmPrinterEndPass::run(Module &M,
SPIRVAsmPrinter &AsmPrinter = static_cast<SPIRVAsmPrinter &>(
MAM.getResult<AsmPrinterAnalysis>(M).getPrinter());
setupModuleAsmPrinter(M, MAM, AsmPrinter);
+ AsmPrinter.GetMAI = [&MAM, &M] {
+ return MAM.getCachedResult<SPIRVModuleAnalysis>(M);
+ };
AsmPrinter.doFinalization(M);
return PreservedAnalyses::all();
}
diff --git a/llvm/lib/Target/SPIRV/SPIRVCodeGenPassBuilder.cpp b/llvm/lib/Target/SPIRV/SPIRVCodeGenPassBuilder.cpp
index 4feb8ee2a4699..6481a20217342 100644
--- a/llvm/lib/Target/SPIRV/SPIRVCodeGenPassBuilder.cpp
+++ b/llvm/lib/Target/SPIRV/SPIRVCodeGenPassBuilder.cpp
@@ -9,6 +9,7 @@
#include "Analysis/SPIRVConvergenceRegionAnalysis.h"
#include "SPIRV.h"
#include "SPIRVAsmPrinter.h"
+#include "SPIRVModuleAnalysis.h"
#include "SPIRVTargetMachine.h"
#include "llvm/CodeGen/AtomicExpand.h"
#include "llvm/CodeGen/BranchFoldingPass.h"
@@ -193,6 +194,12 @@ void SPIRVCodeGenPassBuilder::addAsmPrinterBegin(PassManagerWrapper &PMW) {
}
void SPIRVCodeGenPassBuilder::addAsmPrinter(PassManagerWrapper &PMW) {
+ // SPIRVModuleAnalysis needs every MachineFunction before printing starts.
+ if (TargetPassConfig::willCompleteCodeGenPipeline()) {
+ flushFPMsToMPM(PMW);
+ addModulePass(RequireAnalysisPass<SPIRVModuleAnalysis, Module>(), PMW,
+ /*Force=*/true);
+ }
addMachineFunctionPass(SPIRVAsmPrinterPass(), PMW);
}
diff --git a/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp b/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp
index bbf457ea78224..0ba4174615b56 100644
--- a/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp
+++ b/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp
@@ -26,6 +26,7 @@
#include "SPIRVTargetMachine.h"
#include "SPIRVUtils.h"
#include "llvm/ADT/STLExtras.h"
+#include "llvm/CodeGen/MachineFunctionAnalysis.h"
#include "llvm/CodeGen/MachineModuleInfo.h"
#include "llvm/CodeGen/TargetPassConfig.h"
@@ -51,10 +52,10 @@ struct AvoidCapabilitiesSet {
AvoidCapabilitiesSet() { S.insert_range(AvoidCapabilities); }
};
-char llvm::SPIRVModuleAnalysis::ID = 0;
+char llvm::SPIRVModuleAnalysisWrapperPass::ID = 0;
-INITIALIZE_PASS(SPIRVModuleAnalysis, DEBUG_TYPE, "SPIRV module analysis", true,
- true)
+INITIALIZE_PASS(SPIRVModuleAnalysisWrapperPass, DEBUG_TYPE,
+ "SPIRV module analysis", true, true)
static void reportUnsupported(const MachineInstr &MI, const char *Msg) {
const Function &Func = MI.getMF()->getFunction();
@@ -141,7 +142,7 @@ getSymbolicOperandRequirements(SPIRV::OperandCategory::OperandCategory Category,
return {false, {}, {}, VersionTuple(), VersionTuple()};
}
-void SPIRVModuleAnalysis::setBaseInfo(const Module &M) {
+void SPIRVModuleAnalysisImpl::setBaseInfo(const Module &M) {
MAI.MaxID = 0;
for (int i = 0; i < SPIRV::NUM_MODULE_SECTIONS; i++)
MAI.MS[i].clear();
@@ -348,8 +349,8 @@ static unsigned getInvokeOperandIdx(unsigned Opcode) {
}
}
-bool SPIRVModuleAnalysis::isDeclSection(const MachineRegisterInfo &MRI,
- const MachineInstr &MI) {
+bool SPIRVModuleAnalysisImpl::isDeclSection(const MachineRegisterInfo &MRI,
+ const MachineInstr &MI) {
unsigned Opcode = MI.getOpcode();
switch (Opcode) {
case SPIRV::OpTypeForwardPointer:
@@ -402,7 +403,7 @@ bool SPIRVModuleAnalysis::isDeclSection(const MachineRegisterInfo &MRI,
// FunPtrOp is the MachineOperand previously recorded via
// SPIRVGlobalRegistry::recordFunctionPointer, identifying which Function
// this placeholder refers to.
-void SPIRVModuleAnalysis::visitFunPtrUse(
+void SPIRVModuleAnalysisImpl::visitFunPtrUse(
Register OpReg, const MachineOperand *FunPtrOp,
InstrGRegsMap &SignatureToGReg,
std::map<const Value *, unsigned> &GlobalToGReg,
@@ -429,7 +430,7 @@ void SPIRVModuleAnalysis::visitFunPtrUse(
// Depth first recursive traversal of dependencies. Repeated visits are guarded
// by MAI.hasRegisterAlias().
-void SPIRVModuleAnalysis::visitDecl(
+void SPIRVModuleAnalysisImpl::visitDecl(
const MachineRegisterInfo &MRI, InstrGRegsMap &SignatureToGReg,
std::map<const Value *, unsigned> &GlobalToGReg, const MachineFunction *MF,
const MachineInstr &MI) {
@@ -511,7 +512,7 @@ void SPIRVModuleAnalysis::visitDecl(
MAI.setSkipEmission(&MI);
}
-MCRegister SPIRVModuleAnalysis::handleFunctionOrParameter(
+MCRegister SPIRVModuleAnalysisImpl::handleFunctionOrParameter(
const MachineFunction *MF, const MachineInstr &MI,
std::map<const Value *, unsigned> &GlobalToGReg, bool &IsFunDef) {
const Value *GObj = GR->getGlobalObject(MF, MI.getOperand(0).getReg());
@@ -531,9 +532,8 @@ MCRegister SPIRVModuleAnalysis::handleFunctionOrParameter(
return GReg;
}
-MCRegister
-SPIRVModuleAnalysis::handleTypeDeclOrConstant(const MachineInstr &MI,
- InstrGRegsMap &SignatureToGReg) {
+MCRegister SPIRVModuleAnalysisImpl::handleTypeDeclOrConstant(
+ const MachineInstr &MI, InstrGRegsMap &SignatureToGReg) {
InstrSignature MISign = instrToSignature(MI, MAI, false);
auto [It, Inserted] = SignatureToGReg.try_emplace(MISign);
if (!Inserted)
@@ -544,7 +544,7 @@ SPIRVModuleAnalysis::handleTypeDeclOrConstant(const MachineInstr &MI,
return GReg;
}
-MCRegister SPIRVModuleAnalysis::handleVariable(
+MCRegister SPIRVModuleAnalysisImpl::handleVariable(
const MachineFunction *MF, const MachineInstr &MI,
std::map<const Value *, unsigned> &GlobalToGReg) {
MAI.GlobalVarList.push_back(&MI);
@@ -561,11 +561,11 @@ MCRegister SPIRVModuleAnalysis::handleVariable(
return GReg;
}
-void SPIRVModuleAnalysis::collectDeclarations(const Module &M) {
+void SPIRVModuleAnalysisImpl::collectDeclarations(const Module &M) {
InstrGRegsMap SignatureToGReg;
std::map<const Value *, unsigned> GlobalToGReg;
for (const Function &F : M) {
- MachineFunction *MF = MMI->getMachineFunction(F);
+ MachineFunction *MF = GetMF(F);
if (!MF)
continue;
const MachineRegisterInfo &MRI = MF->getRegInfo();
@@ -633,8 +633,8 @@ void SPIRVModuleAnalysis::collectDeclarations(const Module &M) {
// to the register defining that variable (which will usually be the result of
// an OpFunction). This lets us call externally imported functions using
// the correct ID registers.
-void SPIRVModuleAnalysis::collectFuncNames(MachineInstr &MI,
- const Function *F) {
+void SPIRVModuleAnalysisImpl::collectFuncNames(MachineInstr &MI,
+ const Function *F) {
if (MI.getOpcode() == SPIRV::OpDecorate) {
// If it's got Import linkage.
auto Dec = MI.getOperand(1).getImm();
@@ -723,12 +723,12 @@ static void collectOtherInstr(MachineInstr &MI, SPIRV::ModuleAnalysisInfo &MAI,
// Some global instructions make reference to function-local ID regs, so cannot
// be correctly collected until these registers are globally numbered.
-void SPIRVModuleAnalysis::processOtherInstrs(const Module &M) {
+void SPIRVModuleAnalysisImpl::processOtherInstrs(const Module &M) {
InstrTraces IS;
for (const Function &F : M) {
if (F.isDeclaration())
continue;
- MachineFunction *MF = MMI->getMachineFunction(F);
+ MachineFunction *MF = GetMF(F);
assert(MF);
for (MachineBasicBlock &MBB : *MF)
@@ -802,11 +802,11 @@ void SPIRVModuleAnalysis::processOtherInstrs(const Module &M) {
// Number registers in all functions globally from 0 onwards and store
// the result in global register alias table. Some registers are already
// numbered.
-void SPIRVModuleAnalysis::numberRegistersGlobally(const Module &M) {
+void SPIRVModuleAnalysisImpl::numberRegistersGlobally(const Module &M) {
for (const Function &F : M) {
if (F.isDeclaration())
continue;
- MachineFunction *MF = MMI->getMachineFunction(F);
+ MachineFunction *MF = GetMF(F);
assert(MF);
for (MachineBasicBlock &MBB : *MF) {
for (MachineInstr &MI : MBB) {
@@ -2680,10 +2680,10 @@ void addInstrRequirements(const MachineInstr &MI,
}
static void collectReqs(const Module &M, SPIRV::ModuleAnalysisInfo &MAI,
- MachineModuleInfo *MMI, const SPIRVSubtarget &ST) {
+ MachineFunctionGetter GetMF, const SPIRVSubtarget &ST) {
// Collect requirements for existing instructions.
for (const Function &F : M) {
- MachineFunction *MF = MMI->getMachineFunction(F);
+ MachineFunction *MF = GetMF(F);
if (!MF)
continue;
for (const MachineBasicBlock &MBB : *MF)
@@ -2947,11 +2947,12 @@ static void handleMIFlagDecoration(
// Walk all functions and add decorations related to MI flags.
static void addDecorations(const Module &M, const SPIRVInstrInfo &TII,
- MachineModuleInfo *MMI, const SPIRVSubtarget &ST,
+ MachineFunctionGetter GetMF,
+ const SPIRVSubtarget &ST,
SPIRV::ModuleAnalysisInfo &MAI,
const SPIRVGlobalRegistry *GR) {
for (const Function &F : M) {
- MachineFunction *MF = MMI->getMachineFunction(F);
+ MachineFunction *MF = GetMF(F);
if (!MF)
continue;
@@ -2963,10 +2964,10 @@ static void addDecorations(const Module &M, const SPIRVInstrInfo &TII,
}
static void addMBBNames(const Module &M, const SPIRVInstrInfo &TII,
- MachineModuleInfo *MMI, const SPIRVSubtarget &ST,
+ MachineFunctionGetter GetMF, const SPIRVSubtarget &ST,
SPIRV::ModuleAnalysisInfo &MAI) {
for (const Function &F : M) {
- MachineFunction *MF = MMI->getMachineFunction(F);
+ MachineFunction *MF = GetMF(F);
if (!MF)
continue;
if (MF->getFunction()
@@ -2989,9 +2990,9 @@ static void addMBBNames(const Module &M, const SPIRVInstrInfo &TII,
// patching Instruction::PHI to SPIRV::OpPhi
static void patchPhis(const Module &M, SPIRVGlobalRegistry *GR,
- const SPIRVInstrInfo &TII, MachineModuleInfo *MMI) {
+ const SPIRVInstrInfo &TII, MachineFunctionGetter GetMF) {
for (const Function &F : M) {
- MachineFunction *MF = MMI->getMachineFunction(F);
+ MachineFunction *MF = GetMF(F);
if (!MF)
continue;
for (auto &MBB : *MF) {
@@ -3113,29 +3114,22 @@ static void collectFPFastMathDefaults(const Module &M,
}
}
-void SPIRVModuleAnalysis::getAnalysisUsage(AnalysisUsage &AU) const {
- AU.addRequired<TargetPassConfig>();
- AU.addRequired<MachineModuleInfoWrapperPass>();
-}
-
-bool SPIRVModuleAnalysis::runOnModule(Module &M) {
- SPIRVTargetMachine &TM =
- getAnalysis<TargetPassConfig>().getTM<SPIRVTargetMachine>();
- ST = TM.getSubtargetImpl();
- GR = ST->getSPIRVGlobalRegistry();
- TII = ST->getInstrInfo();
-
- MMI = &getAnalysis<MachineModuleInfoWrapperPass>().getMMI();
+SPIRVModuleAnalysisImpl::SPIRVModuleAnalysisImpl(const SPIRVSubtarget &ST,
+ SPIRV::ModuleAnalysisInfo &MAI,
+ MachineFunctionGetter GetMF)
+ : ST(&ST), GR(ST.getSPIRVGlobalRegistry()), TII(ST.getInstrInfo()),
+ MAI(MAI), GetMF(GetMF) {}
+void SPIRVModuleAnalysisImpl::run(const Module &M) {
setBaseInfo(M);
- patchPhis(M, GR, *TII, MMI);
+ patchPhis(M, GR, *TII, GetMF);
- addMBBNames(M, *TII, MMI, *ST, MAI);
+ addMBBNames(M, *TII, GetMF, *ST, MAI);
collectFPFastMathDefaults(M, MAI, *ST);
- addDecorations(M, *TII, MMI, *ST, MAI, GR);
+ addDecorations(M, *TII, GetMF, *ST, MAI, GR);
- collectReqs(M, MAI, MMI, *ST);
+ collectReqs(M, MAI, GetMF, *ST);
// Process type/const/global var/func decl instructions, number their
// destination registers from 0 to N, collect Extensions and Capabilities.
@@ -3153,6 +3147,42 @@ bool SPIRVModuleAnalysis::runOnModule(Module &M) {
// Set maximum ID used.
GR->setBound(MAI.MaxID);
+}
+void SPIRVModuleAnalysisWrapperPass::getAnalysisUsage(AnalysisUsage &AU) const {
+ AU.addRequired<TargetPassConfig>();
+ AU.addRequired<MachineModuleInfoWrapperPass>();
+}
+
+bool SPIRVModuleAnalysisWrapperPass::runOnModule(Module &M) {
+ SPIRVTargetMachine &TM =
+ getAnalysis<TargetPassConfig>().getTM<SPIRVTargetMachine>();
+ MachineModuleInfo &MMI = getAnalysis<MachineModuleInfoWrapperPass>().getMMI();
+ SPIRVModuleAnalysisImpl(
+ *TM.getSubtargetImpl(), MAI,
+ [&MMI](const Function &F) { return MMI.getMachineFunction(F); })
+ .run(M);
return false;
}
+
+AnalysisKey SPIRVModuleAnalysis::Key;
+
+SPIRVModuleAnalysis::Result
+SPIRVModuleAnalysis::run(Module &M, ModuleAnalysisManager &MAM) {
+ const auto &TM = static_cast<const SPIRVTargetMachine &>(
+ MAM.getResult<MachineModuleAnalysis>(M).getMMI().getTarget());
+ FunctionAnalysisManager &FAM =
+ MAM.getResult<FunctionAnalysisManagerModuleProxy>(M).getManager();
+ Result MAI;
+ SPIRVModuleAnalysisImpl(*TM.getSubtargetImpl(), MAI,
+ [&FAM](const Function &F) -> MachineFunction * {
+ MachineFunctionAnalysis::Result *MFA =
+ FAM.getCachedResult<MachineFunctionAnalysis>(
+ const_cast<Function &>(F));
+ assert((MFA || F.isDeclaration()) &&
+ "Missing MachineFunction for definition");
+ return MFA ? &MFA->getMF() : nullptr;
+ })
+ .run(M);
+ return MAI;
+}
diff --git a/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.h b/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.h
index 6559b5cfc7457..6f939894337b0 100644
--- a/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.h
+++ b/llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.h
@@ -20,11 +20,11 @@
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/SmallSet.h"
#include "llvm/ADT/SmallVector.h"
+#include "llvm/IR/PassManager.h"
namespace llvm {
class SPIRVSubtarget;
class MachineFunction;
-class MachineModuleInfo;
namespace SPIRV {
// The enum contains logical module sections for the instruction collection.
@@ -211,23 +211,26 @@ struct ModuleAnalysisInfo {
It->second = getNextIDRegister();
return It->second;
}
+ // Must stay alive until the AsmPrinter consumes it.
+ bool invalidate(Module &, const PreservedAnalyses &,
+ ModuleAnalysisManager::Invalidator &) {
+ return false;
+ }
};
} // namespace SPIRV
using InstrSignature = SmallVector<size_t>;
using InstrTraces = std::set<InstrSignature>;
using InstrGRegsMap = std::map<SmallVector<size_t>, unsigned>;
+using MachineFunctionGetter = function_ref<MachineFunction *(const Function &)>;
-struct SPIRVModuleAnalysis : public ModulePass {
- static char ID;
-
+class SPIRVModuleAnalysisImpl {
public:
- SPIRVModuleAnalysis()
- : ModulePass(ID), ST(nullptr), GR(nullptr), TII(nullptr), MMI(nullptr) {}
+ SPIRVModuleAnalysisImpl(const SPIRVSubtarget &ST,
+ SPIRV::ModuleAnalysisInfo &MAI,
+ MachineFunctionGetter GetMF);
- bool runOnModule(Module &M) override;
- void getAnalysisUsage(AnalysisUsage &AU) const override;
- SPIRV::ModuleAnalysisInfo MAI;
+ void run(const Module &M);
private:
void setBaseInfo(const Module &M);
@@ -257,7 +260,29 @@ struct SPIRVModuleAnalysis : public ModulePass {
const SPIRVSubtarget *ST;
SPIRVGlobalRegistry *GR;
const SPIRVInstrInfo *TII;
- MachineModuleInfo *MMI;
+ SPIRV::ModuleAnalysisInfo &MAI;
+ MachineFunctionGetter GetMF;
+};
+
+struct SPIRVModuleAnalysisWrapperPass : public ModulePass {
+ static char ID;
+
+public:
+ SPIRVModuleAnalysisWrapperPass() : ModulePass(ID) {}
+
+ bool runOnModule(Module &M) override;
+ void getAnalysisUsage(AnalysisUsage &AU) const override;
+ SPIRV::ModuleAnalysisInfo MAI;
+};
+
+class SPIRVModuleAnalysis : public AnalysisInfoMixin<SPIRVModuleAnalysis> {
+ friend AnalysisInfoMixin<SPIRVModuleAnalysis>;
+ static AnalysisKey Key;
+
+public:
+ using Result = SPIRV::ModuleAnalysisInfo;
+
+ Result run(Module &M, ModuleAnalysisManager &MAM);
};
} // namespace llvm
#endif // LLVM_LIB_TARGET_SPIRV_SPIRVMODULEANALYSIS_H
diff --git a/llvm/lib/Target/SPIRV/SPIRVPassRegistry.def b/llvm/lib/Target/SPIRV/SPIRVPassRegistry.def
index 4cd3a94b017b4..6236c03f5cbef 100644
--- a/llvm/lib/Target/SPIRV/SPIRVPassRegistry.def
+++ b/llvm/lib/Target/SPIRV/SPIRVPassRegistry.def
@@ -13,6 +13,12 @@
// NOTE: NO INCLUDE GUARD DESIRED!
+#ifndef MODULE_ANALYSIS
+#define MODULE_ANALYSIS(NAME, CREATE_PASS)
+#endif
+MODULE_ANALYSIS("spirv-module-analysis", SPIRVModuleAnalysis())
+#undef MODULE_ANALYSIS
+
#ifndef MODULE_PASS
#define MODULE_PASS(NAME, CREATE_PASS)
#endif
diff --git a/llvm/lib/Target/SPIRV/SPIRVTargetMachine.cpp b/llvm/lib/Target/SPIRV/SPIRVTargetMachine.cpp
index 7df3f9881fe73..ddf9889c5c521 100644
--- a/llvm/lib/Target/SPIRV/SPIRVTargetMachine.cpp
+++ b/llvm/lib/Target/SPIRV/SPIRVTargetMachine.cpp
@@ -46,7 +46,7 @@ extern "C" LLVM_ABI LLVM_EXTERNAL_VISIBILITY void LLVMInitializeSPIRVTarget() {
PassRegistry &PR = *PassRegistry::getPassRegistry();
initializeGlobalISel(PR);
- initializeSPIRVModuleAnalysisPass(PR);
+ initializeSPIRVModuleAnalysisWrapperPassPass(PR);
initializeSPIRVAsmPrinterPass(PR);
initializeSPIRVConvergenceRegionAnalysisWrapperPassPass(PR);
initializeSPIRVStructurizerPass(PR);
diff --git a/llvm/test/CodeGen/SPIRV/llc-pipeline.ll b/llvm/test/CodeGen/SPIRV/llc-pipeline.ll
index 406641b2aa753..2aa5a18fdab94 100644
--- a/llvm/test/CodeGen/SPIRV/llc-pipeline.ll
+++ b/llvm/test/CodeGen/SPIRV/llc-pipeline.ll
@@ -7,9 +7,9 @@
; RUN: | FileCheck -match-full-lines -strict-whitespace -check-prefix=SPIRV-Opt %s
; RUN:llc -O3 -mtriple=spirv-- -disable-verify -debug-pass=Structure < %s 2>&1 \
; RUN: | FileCheck -match-full-lines -strict-whitespace -check-prefix=SPIRV-Opt %s
-; RUN:llc -O0 -mtriple=spirv-- -enable-new-pm -stop-before=spirv-asm-printer < %s \
+; RUN:llc -O0 -mtriple=spirv-- -enable-new-pm < %s \
; RUN: | FileCheck -check-prefix=SPIRV-NPM %s
-; RUN:llc -O3 -mtriple=spirv-- -enable-new-pm -stop-before=spirv-asm-printer < %s \
+; RUN:llc -O3 -mtriple=spirv-- -enable-new-pm < %s \
; RUN: | FileCheck -check-prefix=SPIRV-NPM %s
; REQUIRES:asserts
@@ -230,13 +230,12 @@
; SPIRV-Opt-NEXT: SPIRV Assembly Printer
; SPIRV-Opt-NEXT: Free MachineFunction
-; SPIR-V NewPM skips RegBankSelect, so instruction selection must not require it.
-; SPIRV-NPM:legalized: true
-; SPIRV-NPM-NEXT:regBankSelected: false
-; SPIRV-NPM-NEXT:selected: true
-; SPIRV-NPM:%[[#VOID:]]:type = OpTypeVoid
-; SPIRV-NPM:%[[#]]:iid = OpFunction %[[#VOID]], 0, %[[#]]
+; SPIRV-NPM:OpCapability Linkage
+; SPIRV-NPM:OpName %[[#FN:]] "empty"
+; SPIRV-NPM:%[[#VOID:]] = OpTypeVoid
+; SPIRV-NPM:%[[#FN]] = OpFunction %[[#VOID]] None %[[#]]
; SPIRV-NPM:OpReturn
+; SPIRV-NPM:OpFunctionEnd
define void @empty() {
ret void
More information about the llvm-commits
mailing list