Skip to content

Commit 8ddf584

Browse files
committed
[SYCL] Mark calls to barrier and work-item functions as convergent
Calls to work-item functions and barrier function must be convergent to preserve semantics of these functions during llvm optimizations. Signed-off-by: Artur Gainullin <[email protected]>
1 parent a038480 commit 8ddf584

File tree

2 files changed

+58
-4
lines changed

2 files changed

+58
-4
lines changed

llvm/lib/SYCLLowerIR/LowerWGScope.cpp

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -874,10 +874,15 @@ Value *spirv::genLinearLocalID(Instruction &Before, const Triple &TT) {
874874
IRBuilder<> Bld(Ctx);
875875
Bld.SetInsertPoint(&Before);
876876

877+
AttributeList Attr;
878+
Attr = Attr.addAttribute(Ctx, AttributeList::FunctionIndex,
879+
Attribute::Convergent);
880+
877881
#define CREATE_CALLEE(NAME, FN_NAME) \
878-
FunctionCallee FnCallee##NAME = M.getOrInsertFunction(FN_NAME, RetTy); \
882+
FunctionCallee FnCallee##NAME = M.getOrInsertFunction(FN_NAME, Attr, RetTy); \
879883
assert(FnCallee##NAME && "spirv intrinsic creation failed"); \
880-
auto NAME = Bld.CreateCall(FnCallee##NAME, {});
884+
auto NAME = Bld.CreateCall(FnCallee##NAME, {}); \
885+
NAME->addAttribute(AttributeList::FunctionIndex, Attribute::Convergent);
881886

882887
CREATE_CALLEE(LocalInvocationId_X, "_Z27__spirv_LocalInvocationId_xv");
883888
CREATE_CALLEE(LocalInvocationId_Y, "_Z27__spirv_LocalInvocationId_yv");
@@ -937,8 +942,11 @@ Instruction *spirv::genWGBarrier(Instruction &Before, const Triple &TT) {
937942
Type *SemanticsTy = Type::getInt32Ty(Ctx);
938943
Type *RetTy = Type::getVoidTy(Ctx);
939944

945+
AttributeList Attr;
946+
Attr = Attr.addAttribute(Ctx, AttributeList::FunctionIndex,
947+
Attribute::Convergent);
940948
FunctionCallee FC =
941-
M.getOrInsertFunction(Name, RetTy, ScopeTy, ScopeTy, SemanticsTy);
949+
M.getOrInsertFunction(Name, Attr, RetTy, ScopeTy, ScopeTy, SemanticsTy);
942950
assert(FC.getCallee() && "spirv intrinsic creation failed");
943951

944952
IRBuilder<> Bld(Ctx);
@@ -948,5 +956,8 @@ Instruction *spirv::genWGBarrier(Instruction &Before, const Triple &TT) {
948956
auto ArgSema = ConstantInt::get(
949957
ScopeTy, asUInt(spirv::MemorySemantics::SequentiallyConsistent) |
950958
asUInt(spirv::MemorySemantics::WorkgroupMemory));
951-
return Bld.CreateCall(FC, {ArgExec, ArgMem, ArgSema});
959+
auto BarrierCall = Bld.CreateCall(FC, {ArgExec, ArgMem, ArgSema});
960+
BarrierCall->addAttribute(llvm::AttributeList::FunctionIndex,
961+
llvm::Attribute::Convergent);
962+
return BarrierCall;
952963
}

llvm/test/SYCLLowerIR/convergent.ll

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
; RUN: opt < %s -LowerWGScope -S | FileCheck %s
2+
; RUN: opt < %s -LowerWGScope --mtriple=nvptx -S | FileCheck %s -check-prefix=CHECK-PTX
3+
4+
5+
%struct.baz = type { i64 }
6+
7+
define internal spir_func void @wibble(%struct.baz* byval(%struct.baz) %arg1) !work_group_scope !0 {
8+
; CHECK-PTX: %1 = call i64 @_Z27__spirv_LocalInvocationId_xv() #0
9+
; CHECK-PTX: %2 = call i64 @_Z27__spirv_LocalInvocationId_yv() #0
10+
; CHECK-PTX: %3 = call i64 @_Z27__spirv_LocalInvocationId_zv() #0
11+
; CHECK-PTX: %4 = call i64 @_Z23__spirv_WorkgroupSize_yv() #0
12+
; CHECK-PTX: %5 = call i64 @_Z23__spirv_WorkgroupSize_zv() #0
13+
; CHECK-PTX: call void @_Z22__spirv_ControlBarrierN5__spv5ScopeES0_j(i32 2, i32 2, i32 272) #0
14+
; CHECK: call void @__spirv_ControlBarrier(i32 2, i32 2, i32 272) #1
15+
ret void
16+
}
17+
18+
; CHECK-PTX: ; Function Attrs: convergent
19+
; CHECK-PTX: declare i64 @_Z27__spirv_LocalInvocationId_xv() #0
20+
21+
; CHECK-PTX: ; Function Attrs: convergent
22+
; CHECK-PTX: declare i64 @_Z27__spirv_LocalInvocationId_yv() #0
23+
24+
; CHECK-PTX: ; Function Attrs: convergent
25+
; CHECK-PTX: declare i64 @_Z27__spirv_LocalInvocationId_zv() #0
26+
27+
; CHECK-PTX: ; Function Attrs: convergent
28+
; CHECK-PTX: declare i64 @_Z23__spirv_WorkgroupSize_yv() #0
29+
30+
; CHECK-PTX: ; Function Attrs: convergent
31+
; CHECK-PTX: declare i64 @_Z23__spirv_WorkgroupSize_zv() #0
32+
33+
; CHECK-PTX: ; Function Attrs: convergent
34+
; CHECK-PTX: declare void @_Z22__spirv_ControlBarrierN5__spv5ScopeES0_j(i32, i32, i32) #0
35+
36+
; CHECK-PTX: attributes #0 = { convergent }
37+
38+
; CHECK: ; Function Attrs: convergent
39+
; CHECK: declare void @__spirv_ControlBarrier(i32, i32, i32) #1
40+
41+
; CHECK: attributes #1 = { convergent }
42+
43+
!0 = !{}

0 commit comments

Comments
 (0)