Skip to content

Commit 874b4fb

Browse files
[SPIR-V] Fix emission of debug and annotation instructions and add SPV_EXT_optnone SPIR-V extension (#118402)
This PR fixes: * emission of OpNames (added newly inserted internal intrinsics and basic blocks) * emission of function attributes (SRet is added) * implementation of SPV_INTEL_optnone so that it emits OptNoneINTEL Function Control flag, and add implementation of the SPV_EXT_optnone SPIR-V extension.
1 parent 4e6f812 commit 874b4fb

15 files changed

+146
-72
lines changed

llvm/docs/SPIRVUsage.rst

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -141,16 +141,18 @@ list of supported SPIR-V extensions, sorted alphabetically by their extension na
141141

142142
* - Extension Name
143143
- Description
144+
* - ``SPV_EXT_arithmetic_fence``
145+
- Adds an instruction that prevents fast-math optimizations between its argument and the expression that contains it.
146+
* - ``SPV_EXT_demote_to_helper_invocation``
147+
- Adds an instruction that demotes a fragment shader invocation to a helper invocation.
148+
* - ``SPV_EXT_optnone``
149+
- Adds OptNoneEXT value for Function Control mask that indicates a request to not optimize the function.
144150
* - ``SPV_EXT_shader_atomic_float16_add``
145151
- Extends the SPV_EXT_shader_atomic_float_add extension to support atomically adding to 16-bit floating-point numbers in memory.
146152
* - ``SPV_EXT_shader_atomic_float_add``
147153
- Adds atomic add instruction on floating-point numbers.
148154
* - ``SPV_EXT_shader_atomic_float_min_max``
149155
- Adds atomic min and max instruction on floating-point numbers.
150-
* - ``SPV_EXT_arithmetic_fence``
151-
- Adds an instruction that prevents fast-math optimizations between its argument and the expression that contains it.
152-
* - ``SPV_EXT_demote_to_helper_invocation``
153-
- Adds an instruction that demotes a fragment shader invocation to a helper invocation.
154156
* - ``SPV_INTEL_arbitrary_precision_integers``
155157
- Allows generating arbitrary width integer types.
156158
* - ``SPV_INTEL_bfloat16_conversion``

llvm/lib/Target/SPIRV/SPIRVAsmPrinter.cpp

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@ using namespace llvm;
4545
namespace {
4646
class SPIRVAsmPrinter : public AsmPrinter {
4747
unsigned NLabels = 0;
48+
SmallPtrSet<const MachineBasicBlock *, 8> LabeledMBB;
4849

4950
public:
5051
explicit SPIRVAsmPrinter(TargetMachine &TM,
@@ -152,13 +153,9 @@ void SPIRVAsmPrinter::outputOpFunctionEnd() {
152153
outputMCInst(FunctionEndInst);
153154
}
154155

155-
// Emit OpFunctionEnd at the end of MF and clear BBNumToRegMap.
156156
void SPIRVAsmPrinter::emitFunctionBodyEnd() {
157-
// Do not emit anything if it's an internal service function.
158-
if (isHidden())
159-
return;
160-
outputOpFunctionEnd();
161-
MAI->BBNumToRegMap.clear();
157+
if (!isHidden())
158+
outputOpFunctionEnd();
162159
}
163160

164161
void SPIRVAsmPrinter::emitOpLabel(const MachineBasicBlock &MBB) {
@@ -171,6 +168,7 @@ void SPIRVAsmPrinter::emitOpLabel(const MachineBasicBlock &MBB) {
171168
LabelInst.addOperand(MCOperand::createReg(MAI->getOrCreateMBBRegister(MBB)));
172169
outputMCInst(LabelInst);
173170
++NLabels;
171+
LabeledMBB.insert(&MBB);
174172
}
175173

176174
void SPIRVAsmPrinter::emitBasicBlockStart(const MachineBasicBlock &MBB) {
@@ -267,7 +265,7 @@ void SPIRVAsmPrinter::emitInstruction(const MachineInstr *MI) {
267265

268266
// Output OpLabel after OpFunction and OpFunctionParameter in the first MBB.
269267
const MachineInstr *NextMI = MI->getNextNode();
270-
if (!MAI->hasMBBRegister(*MI->getParent()) && isFuncOrHeaderInstr(MI, TII) &&
268+
if (!LabeledMBB.contains(MI->getParent()) && isFuncOrHeaderInstr(MI, TII) &&
271269
(!NextMI || !isFuncOrHeaderInstr(NextMI, TII))) {
272270
assert(MI->getParent()->getNumber() == MF->front().getNumber() &&
273271
"OpFunction is not in the front MBB of MF");

llvm/lib/Target/SPIRV/SPIRVCallLowering.cpp

Lines changed: 15 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -65,7 +65,8 @@ bool SPIRVCallLowering::lowerReturn(MachineIRBuilder &MIRBuilder,
6565
}
6666

6767
// Based on the LLVM function attributes, get a SPIR-V FunctionControl.
68-
static uint32_t getFunctionControl(const Function &F) {
68+
static uint32_t getFunctionControl(const Function &F,
69+
const SPIRVSubtarget *ST) {
6970
MemoryEffects MemEffects = F.getMemoryEffects();
7071

7172
uint32_t FuncControl = static_cast<uint32_t>(SPIRV::FunctionControl::None);
@@ -80,6 +81,11 @@ static uint32_t getFunctionControl(const Function &F) {
8081
else if (MemEffects.onlyReadsMemory())
8182
FuncControl |= static_cast<uint32_t>(SPIRV::FunctionControl::Const);
8283

84+
if (ST->canUseExtension(SPIRV::Extension::SPV_INTEL_optnone) ||
85+
ST->canUseExtension(SPIRV::Extension::SPV_EXT_optnone))
86+
if (F.hasFnAttribute(Attribute::OptimizeNone))
87+
FuncControl |= static_cast<uint32_t>(SPIRV::FunctionControl::OptNoneEXT);
88+
8389
return FuncControl;
8490
}
8591

@@ -346,6 +352,12 @@ bool SPIRVCallLowering::lowerFormalArguments(MachineIRBuilder &MIRBuilder,
346352
buildOpDecorate(VRegs[i][0], MIRBuilder,
347353
SPIRV::Decoration::FuncParamAttr, {Attr});
348354
}
355+
if (Arg.hasAttribute(Attribute::StructRet)) {
356+
auto Attr =
357+
static_cast<unsigned>(SPIRV::FunctionParameterAttribute::Sret);
358+
buildOpDecorate(VRegs[i][0], MIRBuilder,
359+
SPIRV::Decoration::FuncParamAttr, {Attr});
360+
}
349361

350362
if (F.getCallingConv() == CallingConv::SPIR_KERNEL) {
351363
std::vector<SPIRV::Decoration::Decoration> ArgTypeQualDecs =
@@ -397,7 +409,7 @@ bool SPIRVCallLowering::lowerFormalArguments(MachineIRBuilder &MIRBuilder,
397409
FTy = fixFunctionTypeIfPtrArgs(GR, F, FTy, RetTy, ArgTypeVRegs);
398410
SPIRVType *FuncTy = GR->getOrCreateOpTypeFunctionWithArgs(
399411
FTy, RetTy, ArgTypeVRegs, MIRBuilder);
400-
uint32_t FuncControl = getFunctionControl(F);
412+
uint32_t FuncControl = getFunctionControl(F, ST);
401413

402414
// Add OpFunction instruction
403415
MachineInstrBuilder MB = MIRBuilder.buildInstr(SPIRV::OpFunction)
@@ -427,10 +439,8 @@ bool SPIRVCallLowering::lowerFormalArguments(MachineIRBuilder &MIRBuilder,
427439

428440
// Handle entry points and function linkage.
429441
if (isEntryPoint(F)) {
430-
const auto &STI = MIRBuilder.getMF().getSubtarget<SPIRVSubtarget>();
431-
auto executionModel = getExecutionModel(STI, F);
432442
auto MIB = MIRBuilder.buildInstr(SPIRV::OpEntryPoint)
433-
.addImm(static_cast<uint32_t>(executionModel))
443+
.addImm(static_cast<uint32_t>(getExecutionModel(*ST, F)))
434444
.addUse(FuncVReg);
435445
addStringImm(F.getName(), MIB);
436446
} else if (F.getLinkage() != GlobalValue::InternalLinkage &&

llvm/lib/Target/SPIRV/SPIRVCommandLine.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ static const std::map<std::string, SPIRV::Extension::Extension, std::less<>>
4242
{"SPV_INTEL_global_variable_host_access",
4343
SPIRV::Extension::Extension::SPV_INTEL_global_variable_host_access},
4444
{"SPV_INTEL_optnone", SPIRV::Extension::Extension::SPV_INTEL_optnone},
45+
{"SPV_EXT_optnone", SPIRV::Extension::Extension::SPV_EXT_optnone},
4546
{"SPV_INTEL_usm_storage_classes",
4647
SPIRV::Extension::Extension::SPV_INTEL_usm_storage_classes},
4748
{"SPV_INTEL_split_barrier",

llvm/lib/Target/SPIRV/SPIRVEmitIntrinsics.cpp

Lines changed: 33 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -199,6 +199,8 @@ class SPIRVEmitIntrinsics
199199
DenseMap<Function *, CallInst *> Ptrcasts);
200200

201201
void replaceAllUsesWith(Value *Src, Value *Dest, bool DeleteOld = true);
202+
void replaceAllUsesWithAndErase(IRBuilder<> &B, Instruction *Src,
203+
Instruction *Dest, bool DeleteOld = true);
202204

203205
bool runOnFunction(Function &F);
204206
bool postprocessTypes(Module &M);
@@ -322,6 +324,17 @@ static inline void reportFatalOnTokenType(const Instruction *I) {
322324
false);
323325
}
324326

327+
static void emitAssignName(Instruction *I, IRBuilder<> &B) {
328+
if (!I->hasName() || I->getType()->isAggregateType() ||
329+
expectIgnoredInIRTranslation(I))
330+
return;
331+
reportFatalOnTokenType(I);
332+
setInsertPointAfterDef(B, I);
333+
std::vector<Value *> Args = {I};
334+
addStringImm(I->getName(), B, Args);
335+
B.CreateIntrinsic(Intrinsic::spv_assign_name, {I->getType()}, Args);
336+
}
337+
325338
void SPIRVEmitIntrinsics::replaceAllUsesWith(Value *Src, Value *Dest,
326339
bool DeleteOld) {
327340
Src->replaceAllUsesWith(Dest);
@@ -336,6 +349,19 @@ void SPIRVEmitIntrinsics::replaceAllUsesWith(Value *Src, Value *Dest,
336349
}
337350
}
338351

352+
void SPIRVEmitIntrinsics::replaceAllUsesWithAndErase(IRBuilder<> &B,
353+
Instruction *Src,
354+
Instruction *Dest,
355+
bool DeleteOld) {
356+
replaceAllUsesWith(Src, Dest, DeleteOld);
357+
std::string Name = Src->hasName() ? Src->getName().str() : "";
358+
Src->eraseFromParent();
359+
if (!Name.empty()) {
360+
Dest->setName(Name);
361+
emitAssignName(Dest, B);
362+
}
363+
}
364+
339365
static bool IsKernelArgInt8(Function *F, StoreInst *SI) {
340366
return SI && F->getCallingConv() == CallingConv::SPIR_KERNEL &&
341367
isPointerTy(SI->getValueOperand()->getType()) &&
@@ -1308,8 +1334,7 @@ Instruction *SPIRVEmitIntrinsics::visitGetElementPtrInst(GetElementPtrInst &I) {
13081334
for (auto &Op : I.operands())
13091335
Args.push_back(Op);
13101336
auto *NewI = B.CreateIntrinsic(Intrinsic::spv_gep, {Types}, {Args});
1311-
replaceAllUsesWith(&I, NewI);
1312-
I.eraseFromParent();
1337+
replaceAllUsesWithAndErase(B, &I, NewI);
13131338
return NewI;
13141339
}
13151340

@@ -1331,10 +1356,7 @@ Instruction *SPIRVEmitIntrinsics::visitBitCastInst(BitCastInst &I) {
13311356
SmallVector<Type *, 2> Types = {I.getType(), Source->getType()};
13321357
SmallVector<Value *> Args(I.op_begin(), I.op_end());
13331358
auto *NewI = B.CreateIntrinsic(Intrinsic::spv_bitcast, {Types}, {Args});
1334-
std::string InstName = I.hasName() ? I.getName().str() : "";
1335-
replaceAllUsesWith(&I, NewI);
1336-
I.eraseFromParent();
1337-
NewI->setName(InstName);
1359+
replaceAllUsesWithAndErase(B, &I, NewI);
13381360
return NewI;
13391361
}
13401362

@@ -1589,10 +1611,7 @@ Instruction *SPIRVEmitIntrinsics::visitInsertElementInst(InsertElementInst &I) {
15891611
B.SetInsertPoint(&I);
15901612
SmallVector<Value *> Args(I.op_begin(), I.op_end());
15911613
auto *NewI = B.CreateIntrinsic(Intrinsic::spv_insertelt, {Types}, {Args});
1592-
std::string InstName = I.hasName() ? I.getName().str() : "";
1593-
replaceAllUsesWith(&I, NewI);
1594-
I.eraseFromParent();
1595-
NewI->setName(InstName);
1614+
replaceAllUsesWithAndErase(B, &I, NewI);
15961615
return NewI;
15971616
}
15981617

@@ -1604,10 +1623,7 @@ SPIRVEmitIntrinsics::visitExtractElementInst(ExtractElementInst &I) {
16041623
I.getIndexOperand()->getType()};
16051624
SmallVector<Value *, 2> Args = {I.getVectorOperand(), I.getIndexOperand()};
16061625
auto *NewI = B.CreateIntrinsic(Intrinsic::spv_extractelt, {Types}, {Args});
1607-
std::string InstName = I.hasName() ? I.getName().str() : "";
1608-
replaceAllUsesWith(&I, NewI);
1609-
I.eraseFromParent();
1610-
NewI->setName(InstName);
1626+
replaceAllUsesWithAndErase(B, &I, NewI);
16111627
return NewI;
16121628
}
16131629

@@ -1641,8 +1657,7 @@ Instruction *SPIRVEmitIntrinsics::visitExtractValueInst(ExtractValueInst &I) {
16411657
Args.push_back(B.getInt32(Op));
16421658
auto *NewI =
16431659
B.CreateIntrinsic(Intrinsic::spv_extractv, {I.getType()}, {Args});
1644-
replaceAllUsesWith(&I, NewI);
1645-
I.eraseFromParent();
1660+
replaceAllUsesWithAndErase(B, &I, NewI);
16461661
return NewI;
16471662
}
16481663

@@ -1701,10 +1716,7 @@ Instruction *SPIRVEmitIntrinsics::visitAllocaInst(AllocaInst &I) {
17011716
ArraySize ? B.CreateIntrinsic(Intrinsic::spv_alloca_array,
17021717
{PtrTy, ArraySize->getType()}, {ArraySize})
17031718
: B.CreateIntrinsic(Intrinsic::spv_alloca, {PtrTy}, {});
1704-
std::string InstName = I.hasName() ? I.getName().str() : "";
1705-
replaceAllUsesWith(&I, NewI);
1706-
I.eraseFromParent();
1707-
NewI->setName(InstName);
1719+
replaceAllUsesWithAndErase(B, &I, NewI);
17081720
return NewI;
17091721
}
17101722

@@ -1914,14 +1926,7 @@ void SPIRVEmitIntrinsics::processInstrAfterVisit(Instruction *I,
19141926
I->setOperand(OpNo, NewOp);
19151927
}
19161928
}
1917-
if (I->hasName() && !I->getType()->isAggregateType() &&
1918-
!expectIgnoredInIRTranslation(I)) {
1919-
reportFatalOnTokenType(I);
1920-
setInsertPointAfterDef(B, I);
1921-
std::vector<Value *> Args = {I};
1922-
addStringImm(I->getName(), B, Args);
1923-
B.CreateIntrinsic(Intrinsic::spv_assign_name, {I->getType()}, Args);
1924-
}
1929+
emitAssignName(I, B);
19251930
}
19261931

19271932
Type *SPIRVEmitIntrinsics::deduceFunParamElementType(Function *F,

llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.cpp

Lines changed: 31 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -421,6 +421,7 @@ void SPIRVModuleAnalysis::processOtherInstrs(const Module &M) {
421421
continue;
422422
MachineFunction *MF = MMI->getMachineFunction(*F);
423423
assert(MF);
424+
424425
for (MachineBasicBlock &MBB : *MF)
425426
for (MachineInstr &MI : MBB) {
426427
if (MAI.getSkipEmission(&MI))
@@ -1548,11 +1549,14 @@ static void collectReqs(const Module &M, SPIRV::ModuleAnalysisInfo &MAI,
15481549
SPIRV::OperandCategory::ExecutionModeOperand,
15491550
SPIRV::ExecutionMode::VecTypeHint, ST);
15501551

1551-
if (F.hasOptNone() &&
1552-
ST.canUseExtension(SPIRV::Extension::SPV_INTEL_optnone)) {
1553-
// Output OpCapability OptNoneINTEL.
1554-
MAI.Reqs.addExtension(SPIRV::Extension::SPV_INTEL_optnone);
1555-
MAI.Reqs.addCapability(SPIRV::Capability::OptNoneINTEL);
1552+
if (F.hasOptNone()) {
1553+
if (ST.canUseExtension(SPIRV::Extension::SPV_EXT_optnone)) {
1554+
MAI.Reqs.addExtension(SPIRV::Extension::SPV_EXT_optnone);
1555+
MAI.Reqs.addCapability(SPIRV::Capability::OptNoneEXT);
1556+
} else if (ST.canUseExtension(SPIRV::Extension::SPV_INTEL_optnone)) {
1557+
MAI.Reqs.addExtension(SPIRV::Extension::SPV_INTEL_optnone);
1558+
MAI.Reqs.addCapability(SPIRV::Capability::OptNoneINTEL);
1559+
}
15561560
}
15571561
}
15581562
}
@@ -1613,6 +1617,27 @@ static void addDecorations(const Module &M, const SPIRVInstrInfo &TII,
16131617
}
16141618
}
16151619

1620+
static void addMBBNames(const Module &M, const SPIRVInstrInfo &TII,
1621+
MachineModuleInfo *MMI, const SPIRVSubtarget &ST,
1622+
SPIRV::ModuleAnalysisInfo &MAI) {
1623+
for (auto F = M.begin(), E = M.end(); F != E; ++F) {
1624+
MachineFunction *MF = MMI->getMachineFunction(*F);
1625+
if (!MF)
1626+
continue;
1627+
MachineRegisterInfo &MRI = MF->getRegInfo();
1628+
for (auto &MBB : *MF) {
1629+
if (!MBB.hasName() || MBB.empty())
1630+
continue;
1631+
// Emit basic block names.
1632+
Register Reg = MRI.createGenericVirtualRegister(LLT::scalar(64));
1633+
MRI.setRegClass(Reg, &SPIRV::IDRegClass);
1634+
buildOpName(Reg, MBB.getName(), *std::prev(MBB.end()), TII);
1635+
Register GlobalReg = MAI.getOrCreateMBBRegister(MBB);
1636+
MAI.setRegisterAlias(MF, Reg, GlobalReg);
1637+
}
1638+
}
1639+
}
1640+
16161641
struct SPIRV::ModuleAnalysisInfo SPIRVModuleAnalysis::MAI;
16171642

16181643
void SPIRVModuleAnalysis::getAnalysisUsage(AnalysisUsage &AU) const {
@@ -1631,6 +1656,7 @@ bool SPIRVModuleAnalysis::runOnModule(Module &M) {
16311656

16321657
setBaseInfo(M);
16331658

1659+
addMBBNames(M, *TII, MMI, *ST, MAI);
16341660
addDecorations(M, *TII, MMI, *ST, MAI);
16351661

16361662
collectReqs(M, MAI, MMI, *ST);

llvm/lib/Target/SPIRV/SPIRVModuleAnalysis.h

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -157,7 +157,7 @@ struct ModuleAnalysisInfo {
157157
// The array contains lists of MIs for each module section.
158158
InstrList MS[NUM_MODULE_SECTIONS];
159159
// The table maps MBB number to SPIR-V unique ID register.
160-
DenseMap<int, Register> BBNumToRegMap;
160+
DenseMap<std::pair<const MachineFunction *, int>, Register> BBNumToRegMap;
161161

162162
Register getFuncReg(const Function *F) {
163163
assert(F && "Function is null");
@@ -188,15 +188,17 @@ struct ModuleAnalysisInfo {
188188
}
189189
unsigned getNextID() { return MaxID++; }
190190
bool hasMBBRegister(const MachineBasicBlock &MBB) {
191-
return BBNumToRegMap.contains(MBB.getNumber());
191+
auto Key = std::make_pair(MBB.getParent(), MBB.getNumber());
192+
return BBNumToRegMap.contains(Key);
192193
}
193194
// Convert MBB's number to corresponding ID register.
194195
Register getOrCreateMBBRegister(const MachineBasicBlock &MBB) {
195-
auto f = BBNumToRegMap.find(MBB.getNumber());
196-
if (f != BBNumToRegMap.end())
197-
return f->second;
196+
auto Key = std::make_pair(MBB.getParent(), MBB.getNumber());
197+
auto It = BBNumToRegMap.find(Key);
198+
if (It != BBNumToRegMap.end())
199+
return It->second;
198200
Register NewReg = Register::index2VirtReg(getNextID());
199-
BBNumToRegMap[MBB.getNumber()] = NewReg;
201+
BBNumToRegMap[Key] = NewReg;
200202
return NewReg;
201203
}
202204
};

llvm/lib/Target/SPIRV/SPIRVSymbolicOperands.td

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -304,6 +304,7 @@ defm SPV_INTEL_global_variable_host_access : ExtensionOperand<109>;
304304
defm SPV_INTEL_global_variable_fpga_decorations : ExtensionOperand<110>;
305305
defm SPV_KHR_cooperative_matrix : ExtensionOperand<111>;
306306
defm SPV_EXT_arithmetic_fence : ExtensionOperand<112>;
307+
defm SPV_EXT_optnone : ExtensionOperand<113>;
307308

308309
//===----------------------------------------------------------------------===//
309310
// Multiclass used to define Capabilities enum values and at the same time
@@ -463,6 +464,7 @@ defm PhysicalStorageBufferAddressesEXT : CapabilityOperand<5347, 0, 0, [], [Shad
463464
defm CooperativeMatrixNV : CapabilityOperand<5357, 0, 0, [], [Shader]>;
464465
defm ArbitraryPrecisionIntegersINTEL : CapabilityOperand<5844, 0, 0, [SPV_INTEL_arbitrary_precision_integers], [Int8, Int16]>;
465466
defm OptNoneINTEL : CapabilityOperand<6094, 0, 0, [SPV_INTEL_optnone], []>;
467+
defm OptNoneEXT : CapabilityOperand<6094, 0, 0, [SPV_EXT_optnone], []>;
466468
defm BitInstructions : CapabilityOperand<6025, 0, 0, [SPV_KHR_bit_instructions], []>;
467469
defm ExpectAssumeKHR : CapabilityOperand<5629, 0, 0, [SPV_KHR_expect_assume], []>;
468470
defm FunctionPointersINTEL : CapabilityOperand<5603, 0, 0, [SPV_INTEL_function_pointers], []>;
@@ -1433,6 +1435,7 @@ defm Inline : FunctionControlOperand<0x1>;
14331435
defm DontInline : FunctionControlOperand<0x2>;
14341436
defm Pure : FunctionControlOperand<0x4>;
14351437
defm Const : FunctionControlOperand<0x8>;
1438+
defm OptNoneEXT : FunctionControlOperand<0x10000>;
14361439

14371440
//===----------------------------------------------------------------------===//
14381441
// Multiclass used to define MemorySemantics enum values and at the same time

llvm/lib/Target/SPIRV/SPIRVUtils.cpp

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,16 @@ void buildOpName(Register Target, const StringRef &Name,
108108
}
109109
}
110110

111+
void buildOpName(Register Target, const StringRef &Name, MachineInstr &I,
112+
const SPIRVInstrInfo &TII) {
113+
if (!Name.empty()) {
114+
auto MIB =
115+
BuildMI(*I.getParent(), I, I.getDebugLoc(), TII.get(SPIRV::OpName))
116+
.addUse(Target);
117+
addStringImm(Name, MIB);
118+
}
119+
}
120+
111121
static void finishBuildOpDecorate(MachineInstrBuilder &MIB,
112122
const std::vector<uint32_t> &DecArgs,
113123
StringRef StrImm) {

0 commit comments

Comments
 (0)