@@ -132,7 +132,7 @@ INITIALIZE_PASS(SPIRITTAnnotationsLegacyPass, "SPIRITTAnnotations",
132
132
" Insert ITT annotations in SPIR code" , false , false )
133
133
134
134
// Public interface to the SPIRITTAnnotationsPass.
135
- ModulePass *llvm::createSPIRITTAnnotationsPass () {
135
+ ModulePass *llvm::createSPIRITTAnnotationsLegacyPass () {
136
136
return new SPIRITTAnnotationsLegacyPass ();
137
137
}
138
138
@@ -151,35 +151,32 @@ Instruction *emitCall(Module &M, Type *RetTy, StringRef FunctionName,
151
151
auto *FT = FunctionType::get (RetTy, ArgTys, false /* isVarArg*/ );
152
152
FunctionCallee FC = M.getOrInsertFunction (FunctionName, FT);
153
153
assert (FC.getCallee () && " Instruction creation failed" );
154
- auto *Call = CallInst::Create (FT, FC.getCallee (), Args, " " , InsertBefore);
155
- return Call;
154
+ return CallInst::Create (FT, FC.getCallee (), Args, " " , InsertBefore);
156
155
}
157
156
158
157
// Insert instrumental annotation calls, that has no arguments (for example
159
158
// work items start/finish/resume and barrier annotation.
160
- bool insertSimpleInstrumentationCall (Module &M, StringRef Name,
159
+ void insertSimpleInstrumentationCall (Module &M, StringRef Name,
161
160
Instruction *Position) {
162
161
Type *VoidTy = Type::getVoidTy (M.getContext ());
163
162
ArrayRef<Value *> Args;
164
163
Instruction *InstrumentationCall = emitCall (M, VoidTy, Name, Args, Position);
165
164
assert (InstrumentationCall && " Instrumentation call creation failed" );
166
- return true ;
167
165
}
168
166
169
167
// Insert instrumental annotation calls for SPIR-V atomics.
170
- bool insertAtomicInstrumentationCall (Module &M, StringRef Name,
171
- CallInst *AtomicFun,
172
- Instruction *Position ) {
168
+ void insertAtomicInstrumentationCall (Module &M, StringRef Name,
169
+ CallInst *AtomicFun, Instruction *Position,
170
+ StringRef AtomicName ) {
173
171
LLVMContext &Ctx = M.getContext ();
174
172
Type *VoidTy = Type::getVoidTy (Ctx);
175
- Type *Int32Ty = Type::getInt32Ty (Ctx);
173
+ IntegerType *Int32Ty = IntegerType::get (Ctx, 32 );
176
174
// __spirv_Atomic... instructions have following arguments:
177
175
// Pointer, Memory Scope, Memory Semantics and others. To construct Atomic
178
176
// annotation instructions we need Pointer and Memory Semantic arguments
179
177
// taken from the original Atomic instruction.
180
178
Value *Ptr = dyn_cast<Value>(AtomicFun->getArgOperand (0 ));
181
- StringRef AtomicName = AtomicFun->getCalledFunction ()->getName ();
182
- Value *AtomicOp;
179
+ assert (Ptr && " Failed to get a pointer argument of atomic instruction" );
183
180
// Second parameter of Atomic Start/Finish annotation is an Op code of
184
181
// the instruction, encoded into a value of enum, defined like this on user's/
185
182
// profiler's side:
@@ -189,12 +186,11 @@ bool insertAtomicInstrumentationCall(Module &M, StringRef Name,
189
186
// __itt_mem_store = 1,
190
187
// __itt_mem_update = 2
191
188
// }
192
- if (AtomicName.contains (SPIRV_ATOMIC_LOAD))
193
- AtomicOp = ConstantInt::get (Int32Ty, 0 );
194
- else if (AtomicName.contains (SPIRV_ATOMIC_STORE))
195
- AtomicOp = ConstantInt::get (Int32Ty, 1 );
196
- else
197
- AtomicOp = ConstantInt::get (Int32Ty, 2 );
189
+ ConstantInt *AtomicOp =
190
+ StringSwitch<ConstantInt *>(AtomicName)
191
+ .StartsWith (SPIRV_ATOMIC_LOAD, ConstantInt::get (Int32Ty, 0 ))
192
+ .StartsWith (SPIRV_ATOMIC_STORE, ConstantInt::get (Int32Ty, 1 ))
193
+ .Default (ConstantInt::get (Int32Ty, 2 ));
198
194
// Third parameter of Atomic Start/Finish annotation is an ordering
199
195
// semantic of the instruction, encoded into a value of enum, defined like
200
196
// this on user's/profiler's side:
@@ -209,23 +205,24 @@ bool insertAtomicInstrumentationCall(Module &M, StringRef Name,
209
205
// differencies in values between SYCL mem order and SPIR-V mem order, SYCL RT
210
206
// also applies Memory Semantic mask, like WorkgroupMemory (0x100)), need to
211
207
// align it.
212
- uint64_t MemFlag = dyn_cast<ConstantInt>(AtomicFun->getArgOperand (2 ))
213
- ->getValue ()
214
- .getZExtValue ();
208
+ auto *MemFlag = dyn_cast<ConstantInt>(AtomicFun->getArgOperand (2 ));
209
+ // TODO: add non-constant memory order processing
210
+ if (!MemFlag)
211
+ return ;
212
+ uint64_t IntMemFlag = MemFlag->getValue ().getZExtValue ();
215
213
uint64_t Order;
216
- if (MemFlag & 0x2 )
214
+ if (IntMemFlag & 0x2 )
217
215
Order = 1 ;
218
- else if (MemFlag & 0x4 )
216
+ else if (IntMemFlag & 0x4 )
219
217
Order = 2 ;
220
- else if (MemFlag & 0x8 )
218
+ else if (IntMemFlag & 0x8 )
221
219
Order = 3 ;
222
220
else
223
221
Order = 0 ;
224
222
Value *MemOrder = ConstantInt::get (Int32Ty, Order);
225
223
Value *Args[] = {Ptr, AtomicOp, MemOrder};
226
224
Instruction *InstrumentationCall = emitCall (M, VoidTy, Name, Args, Position);
227
225
assert (InstrumentationCall && " Instrumentation call creation failed" );
228
- return true ;
229
226
}
230
227
231
228
} // namespace
@@ -249,15 +246,14 @@ PreservedAnalyses SPIRITTAnnotationsPass::run(Module &M,
249
246
// At the beggining of a kernel insert work item start annotation
250
247
// instruction.
251
248
if (IsSPIRKernel)
252
- IRModified |= insertSimpleInstrumentationCall (M, ITT_ANNOTATION_WI_START,
253
- &*inst_begin (F));
249
+ insertSimpleInstrumentationCall (M, ITT_ANNOTATION_WI_START,
250
+ &*inst_begin (F));
254
251
255
252
for (BasicBlock &BB : F) {
256
253
// Insert Finish instruction before return instruction
257
254
if (IsSPIRKernel)
258
255
if (ReturnInst *RI = dyn_cast<ReturnInst>(BB.getTerminator ()))
259
- IRModified |=
260
- insertSimpleInstrumentationCall (M, ITT_ANNOTATION_WI_FINISH, RI);
256
+ insertSimpleInstrumentationCall (M, ITT_ANNOTATION_WI_FINISH, RI);
261
257
for (Instruction &I : BB) {
262
258
CallInst *CI = dyn_cast<CallInst>(&I);
263
259
if (!CI)
@@ -279,16 +275,15 @@ PreservedAnalyses SPIRITTAnnotationsPass::run(Module &M,
279
275
return CalleeName.startswith (Name);
280
276
})) {
281
277
Instruction *InstAfterBarrier = CI->getNextNode ();
282
- IRModified |=
283
- insertSimpleInstrumentationCall (M, ITT_ANNOTATION_WG_BARRIER, CI);
284
- IRModified |= insertSimpleInstrumentationCall (
285
- M, ITT_ANNOTATION_WI_RESUME, InstAfterBarrier);
278
+ insertSimpleInstrumentationCall (M, ITT_ANNOTATION_WG_BARRIER, CI);
279
+ insertSimpleInstrumentationCall (M, ITT_ANNOTATION_WI_RESUME,
280
+ InstAfterBarrier);
286
281
} else if (CalleeName.startswith (SPIRV_ATOMIC_INST)) {
287
282
Instruction *InstAfterAtomic = CI->getNextNode ();
288
- IRModified |= insertAtomicInstrumentationCall (
289
- M, ITT_ANNOTATION_ATOMIC_START, CI, CI );
290
- IRModified |= insertAtomicInstrumentationCall (
291
- M, ITT_ANNOTATION_ATOMIC_FINISH, CI, InstAfterAtomic);
283
+ insertAtomicInstrumentationCall (M, ITT_ANNOTATION_ATOMIC_START, CI,
284
+ CI, CalleeName );
285
+ insertAtomicInstrumentationCall (M, ITT_ANNOTATION_ATOMIC_FINISH, CI,
286
+ InstAfterAtomic, CalleeName );
292
287
}
293
288
}
294
289
}
0 commit comments