diff --git a/llvm/lib/Transforms/Instrumentation/SPIRITTAnnotations.cpp b/llvm/lib/Transforms/Instrumentation/SPIRITTAnnotations.cpp index 87fd86922ebe6..f42ae8baa87bb 100644 --- a/llvm/lib/Transforms/Instrumentation/SPIRITTAnnotations.cpp +++ b/llvm/lib/Transforms/Instrumentation/SPIRITTAnnotations.cpp @@ -157,15 +157,17 @@ Instruction *emitCall(Module &M, Type *RetTy, StringRef FunctionName, // Insert instrumental annotation calls, that has no arguments (for example // work items start/finish/resume and barrier annotation. void insertSimpleInstrumentationCall(Module &M, StringRef Name, - Instruction *Position) { + Instruction *Position, + const DebugLoc &DL) { Type *VoidTy = Type::getVoidTy(M.getContext()); ArrayRef Args; Instruction *InstrumentationCall = emitCall(M, VoidTy, Name, Args, Position); assert(InstrumentationCall && "Instrumentation call creation failed"); + InstrumentationCall->setDebugLoc(DL); } // Insert instrumental annotation calls for SPIR-V atomics. -void insertAtomicInstrumentationCall(Module &M, StringRef Name, +bool insertAtomicInstrumentationCall(Module &M, StringRef Name, CallInst *AtomicFun, Instruction *Position, StringRef AtomicName) { LLVMContext &Ctx = M.getContext(); @@ -208,7 +210,7 @@ void insertAtomicInstrumentationCall(Module &M, StringRef Name, auto *MemFlag = dyn_cast(AtomicFun->getArgOperand(2)); // TODO: add non-constant memory order processing if (!MemFlag) - return; + return false; uint64_t IntMemFlag = MemFlag->getValue().getZExtValue(); uint64_t Order; if (IntMemFlag & 0x2) @@ -219,10 +221,15 @@ void insertAtomicInstrumentationCall(Module &M, StringRef Name, Order = 3; else Order = 0; + PointerType *Int8PtrAS4Ty = PointerType::get(IntegerType::get(Ctx, 8), 4); + Ptr = CastInst::CreatePointerBitCastOrAddrSpaceCast(Ptr, Int8PtrAS4Ty, "", + Position); Value *MemOrder = ConstantInt::get(Int32Ty, Order); Value *Args[] = {Ptr, AtomicOp, MemOrder}; Instruction *InstrumentationCall = emitCall(M, VoidTy, Name, Args, Position); assert(InstrumentationCall && "Instrumentation call creation failed"); + InstrumentationCall->setDebugLoc(AtomicFun->getDebugLoc()); + return true; } } // namespace @@ -245,15 +252,24 @@ PreservedAnalyses SPIRITTAnnotationsPass::run(Module &M, // At the beggining of a kernel insert work item start annotation // instruction. - if (IsSPIRKernel) - insertSimpleInstrumentationCall(M, ITT_ANNOTATION_WI_START, - &*inst_begin(F)); + if (IsSPIRKernel) { + Instruction *InsertPt = &*inst_begin(F); + if (InsertPt->isDebugOrPseudoInst()) + InsertPt = InsertPt->getNextNonDebugInstruction(); + assert(InsertPt && "Function does not have any real instructions."); + insertSimpleInstrumentationCall(M, ITT_ANNOTATION_WI_START, InsertPt, + InsertPt->getDebugLoc()); + IRModified = true; + } for (BasicBlock &BB : F) { // Insert Finish instruction before return instruction if (IsSPIRKernel) - if (ReturnInst *RI = dyn_cast(BB.getTerminator())) - insertSimpleInstrumentationCall(M, ITT_ANNOTATION_WI_FINISH, RI); + if (ReturnInst *RI = dyn_cast(BB.getTerminator())) { + insertSimpleInstrumentationCall(M, ITT_ANNOTATION_WI_FINISH, RI, + RI->getDebugLoc()); + IRModified = true; + } for (Instruction &I : BB) { CallInst *CI = dyn_cast(&I); if (!CI) @@ -275,15 +291,17 @@ PreservedAnalyses SPIRITTAnnotationsPass::run(Module &M, return CalleeName.startswith(Name); })) { Instruction *InstAfterBarrier = CI->getNextNode(); - insertSimpleInstrumentationCall(M, ITT_ANNOTATION_WG_BARRIER, CI); + const DebugLoc &DL = CI->getDebugLoc(); + insertSimpleInstrumentationCall(M, ITT_ANNOTATION_WG_BARRIER, CI, DL); insertSimpleInstrumentationCall(M, ITT_ANNOTATION_WI_RESUME, - InstAfterBarrier); + InstAfterBarrier, DL); + IRModified = true; } else if (CalleeName.startswith(SPIRV_ATOMIC_INST)) { Instruction *InstAfterAtomic = CI->getNextNode(); - insertAtomicInstrumentationCall(M, ITT_ANNOTATION_ATOMIC_START, CI, - CI, CalleeName); - insertAtomicInstrumentationCall(M, ITT_ANNOTATION_ATOMIC_FINISH, CI, - InstAfterAtomic, CalleeName); + IRModified |= insertAtomicInstrumentationCall( + M, ITT_ANNOTATION_ATOMIC_START, CI, CI, CalleeName); + IRModified |= insertAtomicInstrumentationCall( + M, ITT_ANNOTATION_ATOMIC_FINISH, CI, InstAfterAtomic, CalleeName); } } } diff --git a/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_load.ll b/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_load.ll index 409b7c1f7c1d1..45028d1f38c6d 100644 --- a/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_load.ll +++ b/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_load.ll @@ -46,9 +46,11 @@ if.end.i: ; preds = %entry %9 = addrspacecast i64* %8 to i64 addrspace(4)* %10 = load i64, i64 addrspace(4)* %9, align 8 %add.ptr.i34 = getelementptr inbounds i32, i32 addrspace(1)* %_arg_1, i64 %10 -; CHECK: call void @__itt_offload_atomic_op_start(i32 addrspace(1)* %[[ATOMIC_ARG_1:[0-9a-zA-Z._]+]], i32 0, i32 0) +; CHECK: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_1:[0-9a-zA-Z._]+]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_start(i8 addrspace(4)* [[ARG_ASCAST]], i32 0, i32 0) ; CHECK-NEXT: {{.*}}__spirv_AtomicLoad{{.*}}(i32 addrspace(1)* %[[ATOMIC_ARG_1]],{{.*}}, i32 896 -; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i32 addrspace(1)* %[[ATOMIC_ARG_1]], i32 0, i32 0) +; CHECK-NEXT: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_1]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i8 addrspace(4)* [[ARG_ASCAST]], i32 0, i32 0) %call3.i.i.i.i = tail call spir_func i32 @_Z18__spirv_AtomicLoadPU3AS1KiN5__spv5Scope4FlagENS1_19MemorySemanticsMask4FlagE(i32 addrspace(1)* %add.ptr.i34, i32 1, i32 896) #2 call spir_func void @__synthetic_spir_fun_call(i32 addrspace(1)* %add.ptr.i34) %ptridx.i.i.i = getelementptr inbounds i32, i32 addrspace(1)* %add.ptr.i, i64 %4 @@ -66,9 +68,11 @@ define weak_odr dso_local spir_func void @__synthetic_spir_fun_call(i32 addrspac entry: ; CHECK-LABEL: spir_func void @__synthetic_spir_fun_call(i32 addrspace(1)* %{{.*}}) { ; CHECK-NEXT: entry: -; CHECK-NEXT: call void @__itt_offload_atomic_op_start(i32 addrspace(1)* %[[ATOMIC_ARG_S:[0-9a-zA-Z._]+]], i32 0, i32 0) +; CHECK-NEXT: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_S:[0-9a-zA-Z._]+]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_start(i8 addrspace(4)* [[ARG_ASCAST]], i32 0, i32 0) ; CHECK-NEXT: {{.*}}__spirv_AtomicLoad{{.*}}(i32 addrspace(1)* %[[ATOMIC_ARG_S]],{{.*}}, i32 896 -; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i32 addrspace(1)* %[[ATOMIC_ARG_S]], i32 0, i32 0) +; CHECK-NEXT: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_S]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i8 addrspace(4)* [[ARG_ASCAST]], i32 0, i32 0) call spir_func i32 @_Z18__spirv_AtomicLoadPU3AS1KiN5__spv5Scope4FlagENS1_19MemorySemanticsMask4FlagE(i32 addrspace(1)* %ptr, i32 1, i32 896) #2 ; CHECK-NOT: call void @__itt_offload_wi_finish_wrapper() ret void @@ -93,9 +97,11 @@ entry: %add.ptr.i = getelementptr inbounds i32, i32 addrspace(1)* %_arg_4, i64 %5 %6 = load <3 x i64>, <3 x i64> addrspace(4)* addrspacecast (<3 x i64> addrspace(1)* @__spirv_BuiltInGlobalInvocationId to <3 x i64> addrspace(4)*), align 32, !noalias !19 %7 = extractelement <3 x i64> %6, i64 0 -; CHECK: call void @__itt_offload_atomic_op_start(i32 addrspace(1)* %[[ATOMIC_ARG_2:[0-9a-zA-Z._]+]], i32 0, i32 0) +; CHECK: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_2:[0-9a-zA-Z._]+]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_start(i8 addrspace(4)* [[ARG_ASCAST]], i32 0, i32 0) ; CHECK-NEXT: {{.*}}__spirv_AtomicLoad{{.*}}(i32 addrspace(1)* %[[ATOMIC_ARG_2]],{{.*}}, i32 896) -; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i32 addrspace(1)* %[[ATOMIC_ARG_2]], i32 0, i32 0) +; CHECK-NEXT: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_2]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i8 addrspace(4)* [[ARG_ASCAST]], i32 0, i32 0) %call3.i.i.i = tail call spir_func i32 @_Z18__spirv_AtomicLoadPU3AS1KiN5__spv5Scope4FlagENS1_19MemorySemanticsMask4FlagE(i32 addrspace(1)* %add.ptr.i32, i32 1, i32 896) #2 %ptridx.i.i = getelementptr inbounds i32, i32 addrspace(1)* %add.ptr.i, i64 %7 %ptridx.ascast.i.i = addrspacecast i32 addrspace(1)* %ptridx.i.i to i32 addrspace(4)* @@ -106,8 +112,8 @@ entry: } ; CHECK: declare void @__itt_offload_wi_start_wrapper() -; CHECK: declare void @__itt_offload_atomic_op_start(i32 addrspace(1)*, i32, i32) -; CHECK: declare void @__itt_offload_atomic_op_finish(i32 addrspace(1)*, i32, i32) +; CHECK: declare void @__itt_offload_atomic_op_start(i8 addrspace(4)*, i32, i32) +; CHECK: declare void @__itt_offload_atomic_op_finish(i8 addrspace(4)*, i32, i32) ; CHECK: declare void @__itt_offload_wi_finish_wrapper() attributes #0 = { convergent norecurse "disable-tail-calls"="false" "frame-pointer"="all" "less-precise-fpmad"="false" "min-legal-vector-width"="0" "no-infs-fp-math"="false" "no-jump-tables"="false" "no-nans-fp-math"="false" "no-signed-zeros-fp-math"="false" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "sycl-module-id"="llvm-test-suite/SYCL/AtomicRef/load.cpp" "uniform-work-group-size"="true" "unsafe-fp-math"="false" "use-soft-float"="false" } diff --git a/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_store.ll b/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_store.ll index a469be93d7a24..f843c541e3562 100644 --- a/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_store.ll +++ b/llvm/test/Transforms/SPIRITTAnnotations/itt_atomic_store.ll @@ -43,9 +43,11 @@ if.end.i: ; preds = %entry %7 = load i64, i64 addrspace(4)* %6, align 8 %add.ptr.i = getelementptr inbounds i32, i32 addrspace(1)* %_arg_1, i64 %7 %conv.i.i = trunc i64 %4 to i32 -; CHECK: call void @__itt_offload_atomic_op_start(i32 addrspace(1)* %[[ATOMIC_ARG_1:[0-9a-zA-Z._]+]], i32 1, i32 0 +; CHECK: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_1:[0-9a-zA-Z._]+]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_start(i8 addrspace(4)* [[ARG_ASCAST]], i32 1, i32 0 ; CHECK-NEXT: {{.*}}__spirv_AtomicStore{{.*}}(i32 addrspace(1)* %[[ATOMIC_ARG_1]],{{.*}}, i32 896 -; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i32 addrspace(1)* %[[ATOMIC_ARG_1]], i32 1, i32 0 +; CHECK-NEXT: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_1]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i8 addrspace(4)* [[ARG_ASCAST]], i32 1, i32 0 tail call spir_func void @_Z19__spirv_AtomicStorePU3AS1iN5__spv5Scope4FlagENS1_19MemorySemanticsMask4FlagEi(i32 addrspace(1)* %add.ptr.i, i32 1, i32 896, i32 %conv.i.i) #2 tail call spir_func void @__synthetic_spir_fun_call(i32 addrspace(1)* %add.ptr.i) br label %_ZZN2cl4sycl7handler24parallel_for_lambda_implI12store_kernelIiEZZ10store_testIiEvNS0_5queueEmENKUlRS1_E_clES7_EUlNS0_4itemILi1ELb1EEEE_Li1EEEvNS0_5rangeIXT1_EEET0_ENKUlSA_E_clESA_.exit @@ -59,9 +61,11 @@ _ZZN2cl4sycl7handler24parallel_for_lambda_implI12store_kernelIiEZZ10store_testIi define weak_odr dso_local spir_func void @__synthetic_spir_fun_call(i32 addrspace(1)* %ptr) { entry: ; CHECK-LABEL: spir_func void @__synthetic_spir_fun_call(i32 addrspace(1)* %{{.*}}) { -; CHECK: call void @__itt_offload_atomic_op_start(i32 addrspace(1)* %[[ATOMIC_ARG_S:[0-9a-zA-Z._]+]], i32 1, i32 0) +; CHECK: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_S:[0-9a-zA-Z._]+]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_start(i8 addrspace(4)* [[ARG_ASCAST]], i32 1, i32 0) ; CHECK-NEXT: {{.*}}__spirv_AtomicStore{{.*}}(i32 addrspace(1)* %[[ATOMIC_ARG_S]],{{.*}}, i32 896 -; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i32 addrspace(1)* %[[ATOMIC_ARG_S]], i32 1, i32 0) +; CHECK-NEXT: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_S]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i8 addrspace(4)* [[ARG_ASCAST]], i32 1, i32 0) %0 = load <3 x i64>, <3 x i64> addrspace(4)* addrspacecast (<3 x i64> addrspace(1)* @__spirv_BuiltInGlobalInvocationId to <3 x i64> addrspace(4)*), align 32, !noalias !15 %1 = extractelement <3 x i64> %0, i64 0 %conv = trunc i64 %1 to i32 @@ -86,9 +90,11 @@ entry: %3 = load <3 x i64>, <3 x i64> addrspace(4)* addrspacecast (<3 x i64> addrspace(1)* @__spirv_BuiltInGlobalInvocationId to <3 x i64> addrspace(4)*), align 32, !noalias !15 %4 = extractelement <3 x i64> %3, i64 0 %conv.i = trunc i64 %4 to i32 -; CHECK: call void @__itt_offload_atomic_op_start(i32 addrspace(1)* %[[ATOMIC_ARG_2:[0-9a-zA-Z._]+]], i32 1, i32 0) +; CHECK: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_2:[0-9a-zA-Z._]+]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_start(i8 addrspace(4)* [[ARG_ASCAST]], i32 1, i32 0) ; CHECK-NEXT: {{.*}}__spirv_AtomicStore{{.*}}(i32 addrspace(1)* %[[ATOMIC_ARG_2]],{{.*}}, i32 896 -; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i32 addrspace(1)* %[[ATOMIC_ARG_2]], i32 1, i32 0) +; CHECK-NEXT: [[ARG_ASCAST:%[0-9a-zA-Z._]+]] = addrspacecast i32 addrspace(1)* %[[ATOMIC_ARG_2]] to i8 addrspace(4)* +; CHECK-NEXT: call void @__itt_offload_atomic_op_finish(i8 addrspace(4)* [[ARG_ASCAST]], i32 1, i32 0) tail call spir_func void @_Z19__spirv_AtomicStorePU3AS1iN5__spv5Scope4FlagENS1_19MemorySemanticsMask4FlagEi(i32 addrspace(1)* %add.ptr.i, i32 1, i32 896, i32 %conv.i) #2 ; CHECK: call void @__itt_offload_wi_finish_wrapper() ; CHECK-NEXT: ret void @@ -96,8 +102,8 @@ entry: } ; CHECK: declare void @__itt_offload_wi_start_wrapper() -; CHECK: declare void @__itt_offload_atomic_op_start(i32 addrspace(1)*, i32, i32) -; CHECK: declare void @__itt_offload_atomic_op_finish(i32 addrspace(1)*, i32, i32) +; CHECK: declare void @__itt_offload_atomic_op_start(i8 addrspace(4)*, i32, i32) +; CHECK: declare void @__itt_offload_atomic_op_finish(i8 addrspace(4)*, i32, i32) ; CHECK: declare void @__itt_offload_wi_finish_wrapper() attributes #0 = { convergent norecurse "disable-tail-calls"="false" "frame-pointer"="all" "less-precise-fpmad"="false" "min-legal-vector-width"="0" "no-infs-fp-math"="false" "no-jump-tables"="false" "no-nans-fp-math"="false" "no-signed-zeros-fp-math"="false" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "sycl-module-id"="llvm-test-suite/SYCL/AtomicRef/store.cpp" "uniform-work-group-size"="true" "unsafe-fp-math"="false" "use-soft-float"="false" } diff --git a/llvm/test/Transforms/SPIRITTAnnotations/itt_instrumentation_debug.ll b/llvm/test/Transforms/SPIRITTAnnotations/itt_instrumentation_debug.ll new file mode 100644 index 0000000000000..09857a72464aa --- /dev/null +++ b/llvm/test/Transforms/SPIRITTAnnotations/itt_instrumentation_debug.ll @@ -0,0 +1,105 @@ +; RUN: opt < %s -SPIRITTAnnotations -S | FileCheck %s + +; Verify that SPIRITTAnnotations pass inherits the debug information +; from the insertion points: +; CHECK: call void @__itt_offload_wi_start_wrapper(), !dbg ![[D1:[0-9]+]] +; CHECK: call spir_func void @foo(){{.*}}!dbg ![[D1]] +; CHECK: call void @__itt_offload_wg_barrier_wrapper(), !dbg ![[D2:[0-9]+]] +; CHECK: call spir_func void @_Z22__spirv_ControlBarrieriii(i32 2, i32 2, i32 528){{.*}}!dbg ![[D2]] +; CHECK: call void @__itt_offload_wi_resume_wrapper(), !dbg ![[D2]] +; CHECK: [[LD:%[A-Za-z0-9._]+]] = load i32 addrspace(1)*, i32 addrspace(1)* addrspace(1)* @res +; CHECK: [[AC1:%[A-Za-z0-9._]+]] = addrspacecast i32 addrspace(1)* [[LD]] to i8 addrspace(4)* +; CHECK: call void @__itt_offload_atomic_op_start(i8 addrspace(4)* [[AC1]], i32 2, i32 0), !dbg ![[D3:[0-9]+]] +; CHECK: %call4 = call spir_func i32 @_Z18__spirv_AtomicIAddPU3AS1iiii(i32 addrspace(1)* [[LD]], i32 2, i32 0, i32 1){{.*}}!dbg ![[D3]] +; CHECK: [[AC2:%[A-Za-z0-9._]+]] = addrspacecast i32 addrspace(1)* [[LD]] to i8 addrspace(4)* +; CHECK: call void @__itt_offload_atomic_op_finish(i8 addrspace(4)* [[AC2]], i32 2, i32 0), !dbg ![[D3]] +; CHECK: call void @__itt_offload_wi_finish_wrapper(), !dbg ![[D4:[0-9]+]] +; CHECK: ret void, !dbg ![[D4]] +; CHECK: ![[D2]] = !DILocation(line: 8, column: 3 +; CHECK: ![[D3]] = !DILocation(line: 11, column: 3 +; CHECK: ![[D4]] = !DILocation(line: 14, column: 1 + +target datalayout = "e-i64:64-v16:16-v24:32-v32:32-v48:64-v96:128-v192:256-v256:256-v512:512-v1024:1024-n8:16:32:64" +target triple = "spir64-unknown-unknown" + +@.str = private unnamed_addr addrspace(2) constant [7 x i8] c"enter\0A\00", align 1 +@.str.1 = private unnamed_addr addrspace(2) constant [16 x i8] c"before barrier\0A\00", align 1 +@.str.2 = private unnamed_addr addrspace(2) constant [15 x i8] c"after barrier\0A\00", align 1 +@.str.3 = private unnamed_addr addrspace(2) constant [15 x i8] c"before atomic\0A\00", align 1 +@res = dso_local addrspace(1) global i32 addrspace(1)* null, align 8, !dbg !0 +@.str.4 = private unnamed_addr addrspace(2) constant [14 x i8] c"after atomic\0A\00", align 1 +@.str.5 = private unnamed_addr addrspace(2) constant [6 x i8] c"exit\0A\00", align 1 + +; Function Attrs: convergent noinline norecurse nounwind optnone +define dso_local spir_kernel void @test() #0 !dbg !13 !kernel_arg_addr_space !4 !kernel_arg_access_qual !4 !kernel_arg_type !4 !kernel_arg_base_type !4 !kernel_arg_type_qual !4 !kernel_arg_host_accessible !4 !kernel_arg_pipe_depth !4 !kernel_arg_pipe_io !4 !kernel_arg_buffer_location !4 { +entry: + call spir_func void @foo() #2, !dbg !16 + %0 = getelementptr inbounds [7 x i8], [7 x i8] addrspace(2)* @.str, i64 0, i64 0 + %call = call spir_func i32 @_Z18__spirv_ocl_printfPU3AS2c(i8 addrspace(2)* %0) #1, !dbg !17 + %1 = getelementptr inbounds [16 x i8], [16 x i8] addrspace(2)* @.str.1, i64 0, i64 0 + %call1 = call spir_func i32 @_Z18__spirv_ocl_printfPU3AS2c(i8 addrspace(2)* %1) #1, !dbg !18 + call spir_func void @_Z22__spirv_ControlBarrieriii(i32 2, i32 2, i32 528) #1, !dbg !19 + %2 = getelementptr inbounds [15 x i8], [15 x i8] addrspace(2)* @.str.2, i64 0, i64 0 + %call2 = call spir_func i32 @_Z18__spirv_ocl_printfPU3AS2c(i8 addrspace(2)* %2) #1, !dbg !20 + %3 = getelementptr inbounds [15 x i8], [15 x i8] addrspace(2)* @.str.3, i64 0, i64 0 + %call3 = call spir_func i32 @_Z18__spirv_ocl_printfPU3AS2c(i8 addrspace(2)* %3) #1, !dbg !21 + %4 = load i32 addrspace(1)*, i32 addrspace(1)* addrspace(1)* @res, align 8, !dbg !22 + %call4 = call spir_func i32 @_Z18__spirv_AtomicIAddPU3AS1iiii(i32 addrspace(1)* %4, i32 2, i32 0, i32 1) #1, !dbg !23 + %5 = getelementptr inbounds [14 x i8], [14 x i8] addrspace(2)* @.str.4, i64 0, i64 0 + %call5 = call spir_func i32 @_Z18__spirv_ocl_printfPU3AS2c(i8 addrspace(2)* %5) #1, !dbg !24 + %6 = getelementptr inbounds [6 x i8], [6 x i8] addrspace(2)* @.str.5, i64 0, i64 0 + %call6 = call spir_func i32 @_Z18__spirv_ocl_printfPU3AS2c(i8 addrspace(2)* %6) #1, !dbg !25 + ret void, !dbg !26 +} + +; Function Attrs: convergent +declare spir_func void @foo() #1 + +; Function Attrs: convergent +declare spir_func i32 @_Z18__spirv_ocl_printfPU3AS2c(i8 addrspace(2)*) #1 + +; Function Attrs: convergent +declare spir_func void @_Z22__spirv_ControlBarrieriii(i32, i32, i32) #1 + +; Function Attrs: convergent +declare spir_func i32 @_Z18__spirv_AtomicIAddPU3AS1iiii(i32 addrspace(1)*, i32, i32, i32) #1 + +attributes #0 = { convergent noinline norecurse nounwind optnone "frame-pointer"="none" "min-legal-vector-width"="0" "no-trapping-math"="true" "stack-protector-buffer-size"="8" "uniform-work-group-size"="false" } +attributes #1 = { convergent "frame-pointer"="none" "no-trapping-math"="true" "stack-protector-buffer-size"="8" } +attributes #2 = { convergent } + +!llvm.dbg.cu = !{!2} +!llvm.module.flags = !{!9} +!opencl.compiler.options = !{!4} +!llvm.ident = !{!10} +!spirv.Source = !{!11} +!spirv.MemoryModel = !{!12} +!spirv.ExecutionMode = !{} + +!0 = !DIGlobalVariableExpression(var: !1, expr: !DIExpression()) +!1 = distinct !DIGlobalVariable(name: "res", scope: !2, file: !6, line: 1, type: !7, isLocal: false, isDefinition: true) +!2 = distinct !DICompileUnit(language: DW_LANG_OpenCL, file: !3, producer: "clang 11.0.0", isOptimized: false, runtimeVersion: 0, emissionKind: FullDebug, enums: !4, globals: !5, splitDebugInlining: false, nameTableKind: None) +!3 = !DIFile(filename: "", directory: "/test") +!4 = !{} +!5 = !{!0} +!6 = !DIFile(filename: "itt.c", directory: "/test") +!7 = !DIDerivedType(tag: DW_TAG_pointer_type, baseType: !8, size: 64) +!8 = !DIBasicType(name: "int", size: 32, encoding: DW_ATE_signed) +!9 = !{i32 2, !"Debug Info Version", i32 3} +!10 = !{!"clang 11.0.0"} +!11 = !{i32 3, i32 200000} +!12 = !{i32 2, i32 2} +!13 = distinct !DISubprogram(name: "test", scope: !6, file: !6, line: 4, type: !14, scopeLine: 4, flags: DIFlagPrototyped, spFlags: DISPFlagDefinition, unit: !2, retainedNodes: !4) +!14 = !DISubroutineType(cc: DW_CC_LLVM_OpenCLKernel, types: !15) +!15 = !{null} +!16 = !DILocation(line: 5, column: 3, scope: !13) +!17 = !DILocation(line: 6, column: 3, scope: !13) +!18 = !DILocation(line: 7, column: 3, scope: !13) +!19 = !DILocation(line: 8, column: 3, scope: !13) +!20 = !DILocation(line: 9, column: 3, scope: !13) +!21 = !DILocation(line: 10, column: 3, scope: !13) +!22 = !DILocation(line: 11, column: 12, scope: !13) +!23 = !DILocation(line: 11, column: 3, scope: !13) +!24 = !DILocation(line: 12, column: 3, scope: !13) +!25 = !DILocation(line: 13, column: 3, scope: !13) +!26 = !DILocation(line: 14, column: 1, scope: !13)