[llvm] [SPIRV] Split async copy tests and fix invalid tests (PR #178718)
Manuel Carrasco via llvm-commits
llvm-commits at lists.llvm.org
Fri Jan 30 09:32:17 PST 2026
https://github.com/mgcarrasco updated https://github.com/llvm/llvm-project/pull/178718
>From c8132f391c980c3f71a6afdab8b6b26122cf955f Mon Sep 17 00:00:00 2001
From: Manuel Carrasco <Manuel.Carrasco at amd.com>
Date: Thu, 29 Jan 2026 12:13:18 -0600
Subject: [PATCH 1/2] [SPIRV] Split async copy tests and fix invalid tests
After a spirv-val update, tests that mix spirv32 and spirv64 targets with
the same LLVM IR are now correctly flagged as invalid. The SPIR-V
specification requires that NumElements and Stride operands in
OpGroupAsyncCopy must be 32-bit integers when the addressing model is
Physical32, and 64-bit integers for Physical64.
---
.../test/CodeGen/SPIRV/event-zero-const-64.ll | 27 +++++
llvm/test/CodeGen/SPIRV/event-zero-const.ll | 12 +-
.../OpGroupAsyncCopy-strided-64.ll | 37 ++++++
.../transcoding/OpGroupAsyncCopy-strided.ll | 31 ++---
.../SPIRV/transcoding/spirv-event-null-64.ll | 101 +++++++++++++++++
.../SPIRV/transcoding/spirv-event-null.ll | 107 +++++++++---------
6 files changed, 242 insertions(+), 73 deletions(-)
create mode 100644 llvm/test/CodeGen/SPIRV/event-zero-const-64.ll
create mode 100644 llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll
create mode 100644 llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll
diff --git a/llvm/test/CodeGen/SPIRV/event-zero-const-64.ll b/llvm/test/CodeGen/SPIRV/event-zero-const-64.ll
new file mode 100644
index 0000000000000..49cd2cb6bf268
--- /dev/null
+++ b/llvm/test/CodeGen/SPIRV/event-zero-const-64.ll
@@ -0,0 +1,27 @@
+; RUN: llc -verify-machineinstrs -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s
+; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
+
+; CHECK-DAG: %[[#LongTy:]] = OpTypeInt 64 0
+; CHECK-DAG: %[[#IntTy:]] = OpTypeInt 32 0
+; CHECK-DAG: %[[#EventTy:]] = OpTypeEvent
+; CHECK-DAG: %[[#LongNull:]] = OpConstantNull %[[#LongTy]]
+; CHECK-DAG: %[[#EventNull:]] = OpConstantNull %[[#EventTy]]
+; CHECK-DAG: %[[#Scope:]] = OpConstant %[[#IntTy]] 2
+; CHECK-DAG: %[[#One:]] = OpConstant %[[#LongTy]] 1
+; CHECK: OpFunction
+; CHECK: OpINotEqual %[[#]] %[[#]] %[[#LongNull]]
+; CHECK: OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#]] %[[#]] %[[#One]] %[[#One]] %[[#EventNull]]
+
+ at G_r1 = global i1 0
+ at G_e1 = global target("spirv.Event") poison
+
+define weak_odr dso_local spir_kernel void @foo(i64 %_arg_i, ptr addrspace(1) %_arg_ptr, ptr addrspace(3) %_arg_local) {
+entry:
+ %r1 = icmp ne i64 %_arg_i, 0
+ store i1 %r1, ptr @G_r1
+ %e1 = tail call spir_func target("spirv.Event") @__spirv_GroupAsyncCopy(i32 2, ptr addrspace(3) %_arg_local, ptr addrspace(1) %_arg_ptr, i64 1, i64 1, target("spirv.Event") zeroinitializer)
+ store target("spirv.Event") %e1, ptr @G_e1
+ ret void
+}
+
+declare dso_local spir_func target("spirv.Event") @__spirv_GroupAsyncCopy(i32, ptr addrspace(3), ptr addrspace(1), i64, i64, target("spirv.Event"))
diff --git a/llvm/test/CodeGen/SPIRV/event-zero-const.ll b/llvm/test/CodeGen/SPIRV/event-zero-const.ll
index 2bf8259e78785..df8c79519779d 100644
--- a/llvm/test/CodeGen/SPIRV/event-zero-const.ll
+++ b/llvm/test/CodeGen/SPIRV/event-zero-const.ll
@@ -1,16 +1,16 @@
-; RUN: llc -verify-machineinstrs -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s
-; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
-
; RUN: llc -verify-machineinstrs -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %}
; CHECK-DAG: %[[#LongTy:]] = OpTypeInt 64 0
+; CHECK-DAG: %[[#IntTy:]] = OpTypeInt 32 0
; CHECK-DAG: %[[#EventTy:]] = OpTypeEvent
; CHECK-DAG: %[[#LongNull:]] = OpConstantNull %[[#LongTy]]
; CHECK-DAG: %[[#EventNull:]] = OpConstantNull %[[#EventTy]]
+; CHECK-DAG: %[[#Scope:]] = OpConstant %[[#IntTy]] 2
+; CHECK-DAG: %[[#One:]] = OpConstant %[[#IntTy]] 1
; CHECK: OpFunction
; CHECK: OpINotEqual %[[#]] %[[#]] %[[#LongNull]]
-; CHECK: OpGroupAsyncCopy %[[#EventTy]] %[[#]] %[[#]] %[[#]] %[[#]] %[[#]] %[[#EventNull]]
+; CHECK: OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#]] %[[#]] %[[#One]] %[[#One]] %[[#EventNull]]
@G_r1 = global i1 0
@G_e1 = global target("spirv.Event") poison
@@ -19,9 +19,9 @@ define weak_odr dso_local spir_kernel void @foo(i64 %_arg_i, ptr addrspace(1) %_
entry:
%r1 = icmp ne i64 %_arg_i, 0
store i1 %r1, ptr @G_r1
- %e1 = tail call spir_func target("spirv.Event") @__spirv_GroupAsyncCopy(i32 2, ptr addrspace(3) %_arg_local, ptr addrspace(1) %_arg_ptr, i64 1, i64 1, target("spirv.Event") zeroinitializer)
+ %e1 = tail call spir_func target("spirv.Event") @__spirv_GroupAsyncCopy(i32 2, ptr addrspace(3) %_arg_local, ptr addrspace(1) %_arg_ptr, i32 1, i32 1, target("spirv.Event") zeroinitializer)
store target("spirv.Event") %e1, ptr @G_e1
ret void
}
-declare dso_local spir_func target("spirv.Event") @__spirv_GroupAsyncCopy(i32, ptr addrspace(3), ptr addrspace(1), i64, i64, target("spirv.Event"))
+declare dso_local spir_func target("spirv.Event") @__spirv_GroupAsyncCopy(i32, ptr addrspace(3), ptr addrspace(1), i32, i32, target("spirv.Event"))
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll
new file mode 100644
index 0000000000000..b5ba122c71943
--- /dev/null
+++ b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll
@@ -0,0 +1,37 @@
+; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
+; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
+
+; CHECK-SPIRV-DAG: %[[#LongTy:]] = OpTypeInt 64 0
+; CHECK-SPIRV-DAG: %[[#IntTy:]] = OpTypeInt 32 0
+; CHECK-SPIRV-DAG: %[[#Int8Ty:]] = OpTypeInt 8 0
+; CHECK-SPIRV-DAG: %[[#EventTy:]] = OpTypeEvent
+; CHECK-SPIRV-DAG: %[[#WGPtrTy:]] = OpTypePointer Workgroup %[[#Int8Ty]]
+; CHECK-SPIRV-DAG: %[[#CWGPtrTy:]] = OpTypePointer CrossWorkgroup %[[#Int8Ty]]
+; CHECK-SPIRV-DAG: %[[#Scope:]] = OpConstant %[[#IntTy]] 2
+; CHECK-SPIRV-DAG: %[[#NumElem:]] = OpConstant %[[#LongTy]] 123
+; CHECK-SPIRV-DAG: %[[#Stride:]] = OpConstant %[[#LongTy]] 1
+; CHECK-SPIRV-DAG: %[[#DstNull:]] = OpConstantNull %[[#WGPtrTy]]
+; CHECK-SPIRV-DAG: %[[#SrcNull:]] = OpConstantNull %[[#CWGPtrTy]]
+; CHECK-SPIRV-DAG: %[[#EventNull:]] = OpConstantNull %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#GenPtrEventTy:]] = OpTypePointer Generic %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#FunPtrEventTy:]] = OpTypePointer Function %[[#EventTy]]
+; CHECK-SPIRV: OpFunction
+; CHECK-SPIRV: %[[#Var:]] = OpVariable %[[#FunPtrEventTy]] Function
+; CHECK-SPIRV: %[[#ResEvent:]] = OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#DstNull]] %[[#SrcNull]] %[[#NumElem]] %[[#Stride]] %[[#EventNull]]
+; CHECK-SPIRV: OpStore %[[#Var]] %[[#ResEvent]]
+; CHECK-SPIRV: %[[#PtrEventGen:]] = OpPtrCastToGeneric %[[#GenPtrEventTy]] %[[#Var]]
+; CHECK-SPIRV: OpGroupWaitEvents %[[#Scope]] %[[#]] %[[#PtrEventGen]]
+; CHECK-SPIRV: OpFunctionEnd
+
+define spir_kernel void @foo() {
+ %event = alloca target("spirv.Event"), align 8
+ %call = call spir_func target("spirv.Event") @_Z29async_work_group_strided_copyPU3AS3hPU3AS1Khmm9ocl_event(ptr addrspace(3) null, ptr addrspace(1) null, i64 123, i64 1, target("spirv.Event") zeroinitializer)
+ store target("spirv.Event") %call, ptr %event, align 8
+ %event.ascast = addrspacecast ptr %event to ptr addrspace(4)
+ call spir_func void @_Z17wait_group_eventsiPU3AS49ocl_event(i32 1, ptr addrspace(4) %event.ascast)
+ ret void
+}
+
+declare spir_func target("spirv.Event") @_Z29async_work_group_strided_copyPU3AS3hPU3AS1Khmm9ocl_event(ptr addrspace(3), ptr addrspace(1), i64, i64, target("spirv.Event"))
+declare spir_func void @_Z17wait_group_eventsiPU3AS49ocl_event(i32, ptr addrspace(4))
+
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll
index efb99dc19eb99..aa607d25df85e 100644
--- a/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll
+++ b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll
@@ -1,34 +1,35 @@
-; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
-; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
-
; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %}
-; CHECK-SPIRV-DAG: %[[#LongTy:]] = OpTypeInt 64 0
; CHECK-SPIRV-DAG: %[[#IntTy:]] = OpTypeInt 32 0
+; CHECK-SPIRV-DAG: %[[#Int8Ty:]] = OpTypeInt 8 0
; CHECK-SPIRV-DAG: %[[#EventTy:]] = OpTypeEvent
+; CHECK-SPIRV-DAG: %[[#WGPtrTy:]] = OpTypePointer Workgroup %[[#Int8Ty]]
+; CHECK-SPIRV-DAG: %[[#CWGPtrTy:]] = OpTypePointer CrossWorkgroup %[[#Int8Ty]]
; CHECK-SPIRV-DAG: %[[#Scope:]] = OpConstant %[[#IntTy]] 2
-; CHECK-SPIRV-DAG: %[[#Num:]] = OpConstant %[[#LongTy]] 123
-; CHECK-SPIRV-DAG: %[[#Null:]] = OpConstantNull
-; CHECK-SPIRV-DAG: %[[#Stride:]] = OpConstant %[[#LongTy]] 1
+; CHECK-SPIRV-DAG: %[[#NumElem:]] = OpConstant %[[#IntTy]] 123
+; CHECK-SPIRV-DAG: %[[#Stride:]] = OpConstant %[[#IntTy]] 1
+; CHECK-SPIRV-DAG: %[[#DstNull:]] = OpConstantNull %[[#WGPtrTy]]
+; CHECK-SPIRV-DAG: %[[#SrcNull:]] = OpConstantNull %[[#CWGPtrTy]]
+; CHECK-SPIRV-DAG: %[[#EventNull:]] = OpConstantNull %[[#EventTy]]
; CHECK-SPIRV-DAG: %[[#GenPtrEventTy:]] = OpTypePointer Generic %[[#EventTy]]
; CHECK-SPIRV-DAG: %[[#FunPtrEventTy:]] = OpTypePointer Function %[[#EventTy]]
; CHECK-SPIRV: OpFunction
; CHECK-SPIRV: %[[#Var:]] = OpVariable %[[#FunPtrEventTy]] Function
-; CHECK-SPIRV: %[[#ResEvent:]] = OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#Null]] %[[#Null]] %[[#Num]] %[[#Stride]] %[[#Null]]
+; CHECK-SPIRV: %[[#ResEvent:]] = OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#DstNull]] %[[#SrcNull]] %[[#NumElem]] %[[#Stride]] %[[#EventNull]]
; CHECK-SPIRV: OpStore %[[#Var]] %[[#ResEvent]]
; CHECK-SPIRV: %[[#PtrEventGen:]] = OpPtrCastToGeneric %[[#GenPtrEventTy]] %[[#Var]]
-; CHECK-SPIRV: OpGroupWaitEvents %[[#Scope]] %[[#Num]] %[[#PtrEventGen]]
+; CHECK-SPIRV: OpGroupWaitEvents %[[#Scope]] %[[#Stride]] %[[#PtrEventGen]]
; CHECK-SPIRV: OpFunctionEnd
define spir_kernel void @foo() {
- %event = alloca ptr, align 8
- %call = call spir_func ptr @_Z29async_work_group_strided_copyPU3AS3hPU3AS1Khmm9ocl_event(ptr null, ptr null, i64 123, i64 1, ptr null)
- store ptr %call, ptr %event, align 8
+ %event = alloca target("spirv.Event"), align 8
+ %call = call spir_func target("spirv.Event") @_Z29async_work_group_strided_copyPU3AS3hPU3AS1Khjj9ocl_event(ptr addrspace(3) null, ptr addrspace(1) null, i32 123, i32 1, target("spirv.Event") zeroinitializer)
+ store target("spirv.Event") %call, ptr %event, align 8
%event.ascast = addrspacecast ptr %event to ptr addrspace(4)
- call spir_func void @_Z17wait_group_eventsiPU3AS49ocl_event(i64 123, ptr addrspace(4) %event.ascast)
+ call spir_func void @_Z17wait_group_eventsiPU3AS49ocl_event(i32 1, ptr addrspace(4) %event.ascast)
ret void
}
-declare spir_func ptr @_Z29async_work_group_strided_copyPU3AS3hPU3AS1Khmm9ocl_event(ptr, ptr, i64, i64, ptr)
-declare spir_func void @_Z17wait_group_eventsiPU3AS49ocl_event(i64, ptr addrspace(4))
+declare spir_func target("spirv.Event") @_Z29async_work_group_strided_copyPU3AS3hPU3AS1Khjj9ocl_event(ptr addrspace(3), ptr addrspace(1), i32, i32, target("spirv.Event"))
+declare spir_func void @_Z17wait_group_eventsiPU3AS49ocl_event(i32, ptr addrspace(4))
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll
new file mode 100644
index 0000000000000..572069cfba709
--- /dev/null
+++ b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll
@@ -0,0 +1,101 @@
+; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
+; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
+
+; CHECK-SPIRV-DAG: %[[#IntTy:]] = OpTypeInt 32 0
+; CHECK-SPIRV-DAG: %[[#LongTy:]] = OpTypeInt 64 0
+; CHECK-SPIRV-DAG: %[[#EventTy:]] = OpTypeEvent
+; CHECK-SPIRV-DAG: %[[#ConstEvent:]] = OpConstantNull %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyEventPtr:]] = OpTypePointer Function %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyEventPtrGen:]] = OpTypePointer Generic %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyStruct:]] = OpTypeStruct %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyStructPtr:]] = OpTypePointer Function %[[#TyStruct]]
+; CHECK-SPIRV-DAG: %[[#TyChar:]] = OpTypeInt 8 0
+; CHECK-SPIRV-DAG: %[[#TyV4:]] = OpTypeVector %[[#TyChar]] 4
+; CHECK-SPIRV-DAG: %[[#TyStructV4:]] = OpTypeStruct %[[#TyV4]]
+; CHECK-SPIRV-DAG: %[[#TyPtrSV4_CW:]] = OpTypePointer CrossWorkgroup %[[#TyStructV4]]
+; CHECK-SPIRV-DAG: %[[#TyPtrV4_W:]] = OpTypePointer Workgroup %[[#TyV4]]
+; CHECK-SPIRV-DAG: %[[#TyPtrV4_CW:]] = OpTypePointer CrossWorkgroup %[[#TyV4]]
+; CHECK-SPIRV-DAG: %[[#TyHalf:]] = OpTypeFloat 16
+; CHECK-SPIRV-DAG: %[[#TyHalfV2:]] = OpTypeVector %[[#TyHalf]] 2
+; CHECK-SPIRV-DAG: %[[#TyHalfV2_W:]] = OpTypePointer Workgroup %[[#TyHalfV2]]
+; CHECK-SPIRV-DAG: %[[#TyHalfV2_CW:]] = OpTypePointer CrossWorkgroup %[[#TyHalfV2]]
+; CHECK-SPIRV-DAG: %[[#Scope:]] = OpConstant %[[#IntTy]] 2
+; CHECK-SPIRV-DAG: %[[#NumElem:]] = OpConstant %[[#LongTy]] 16
+; CHECK-SPIRV-DAG: %[[#Stride:]] = OpConstant %[[#LongTy]] 10
+; CHECK-SPIRV-DAG: %[[#NumEvents:]] = OpConstant %[[#IntTy]] 1
+
+; Check correct translation of __spirv_GroupAsyncCopy and target("spirv.Event") zeroinitializer
+
+%StructEvent = type { target("spirv.Event") }
+
+ at G_r = global target("spirv.Event") poison
+
+; CHECK-SPIRV: OpFunction
+; CHECK-SPIRV: %[[#HalfA1:]] = OpFunctionParameter %[[#TyHalfV2_W]]
+; CHECK-SPIRV: %[[#HalfA2:]] = OpFunctionParameter %[[#TyHalfV2_CW]]
+; CHECK-SPIRV: OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#HalfA1]] %[[#HalfA2]] %[[#NumElem]] %[[#Stride]] %[[#ConstEvent]]
+; CHECK-SPIRV: OpFunctionEnd
+
+define spir_kernel void @test_half(ptr addrspace(3) %_arg1, ptr addrspace(1) %_arg2) {
+entry:
+ %r = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv2_DF16_PU3AS1KS_mm9ocl_event(i32 2, ptr addrspace(3) %_arg1, ptr addrspace(1) %_arg2, i64 16, i64 10, target("spirv.Event") zeroinitializer)
+ store target("spirv.Event") %r, ptr @G_r
+ ret void
+}
+
+declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv2_DF16_PU3AS1KS_mm9ocl_event(i32 noundef, ptr addrspace(3) noundef, ptr addrspace(1) noundef, i64 noundef, i64 noundef, target("spirv.Event"))
+
+; CHECK-SPIRV: OpFunction
+; CHECK-SPIRV: OpFunctionParameter
+; CHECK-SPIRV: %[[#Src:]] = OpFunctionParameter
+; CHECK-SPIRV: %[[#EventVar:]] = OpVariable %[[#TyEventPtr]] Function
+; CHECK-SPIRV: %[[#Dest:]] = OpInBoundsPtrAccessChain
+; CHECK-SPIRV: %[[#CopyRes:]] = OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#Dest]] %[[#Src]] %[[#NumElem]] %[[#Stride]] %[[#ConstEvent]]
+; CHECK-SPIRV: OpStore %[[#EventVar]] %[[#CopyRes]]
+; CHECK-SPIRV: OpFunctionEnd
+
+define spir_kernel void @foo(ptr addrspace(1) %_arg_out_ptr, ptr addrspace(3) %_arg_local_acc) {
+entry:
+ %var = alloca %StructEvent
+ %dev_event.i.sroa.0 = alloca target("spirv.Event")
+ %add.ptr.i26 = getelementptr inbounds i32, ptr addrspace(1) %_arg_out_ptr, i64 0
+ %call3.i = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kimm9ocl_event(i32 2, ptr addrspace(1) %add.ptr.i26, ptr addrspace(3) %_arg_local_acc, i64 16, i64 10, target("spirv.Event") zeroinitializer)
+ store target("spirv.Event") %call3.i, ptr %dev_event.i.sroa.0
+ ret void
+}
+
+declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kimm9ocl_event(i32, ptr addrspace(1), ptr addrspace(3), i64, i64, target("spirv.Event"))
+
+; Check correct type inference when calling __spirv_GroupAsyncCopy:
+; we expect that the Backend is able to deduce a type of the %_arg_Local
+; given facts that it's possible to deduce a type of the %_arg
+; and %_arg_Local and %_arg are source/destination arguments in OpGroupAsyncCopy
+
+%Vec4 = type { <4 x i8> }
+
+; CHECK-SPIRV: OpFunction
+; CHECK-SPIRV: %[[#BarArg1:]] = OpFunctionParameter %[[#TyPtrV4_W]]
+; CHECK-SPIRV: %[[#BarArg2:]] = OpFunctionParameter %[[#TyPtrSV4_CW]]
+; CHECK-SPIRV: %[[#EventVarBar:]] = OpVariable %[[#TyStructPtr]] Function
+; CHECK-SPIRV: %[[#EventVarBarCasted2:]] = OpBitcast %[[#TyEventPtr]] %[[#EventVarBar]]
+; CHECK-SPIRV: %[[#ResBar:]] = OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#BarArg1]] %[[#]] %[[#NumElem]] %[[#Stride]] %[[#ConstEvent]]
+; CHECK-SPIRV: %[[#EventVarBarCasted:]] = OpBitcast %[[#TyEventPtr]] %[[#EventVarBar]]
+; CHECK-SPIRV: OpStore %[[#EventVarBarCasted]] %[[#ResBar]]
+; CHECK-SPIRV: %[[#EventVarBarGen:]] = OpPtrCastToGeneric %[[#TyEventPtrGen]] %[[#EventVarBarCasted2]]
+; CHECK-SPIRV: OpGroupWaitEvents %[[#Scope]] %[[#NumEvents]] %[[#EventVarBarGen]]
+; CHECK-SPIRV: OpFunctionEnd
+
+define spir_kernel void @bar(ptr addrspace(3) %_arg_Local, ptr addrspace(1) readonly %_arg) {
+entry:
+ %E1 = alloca %StructEvent
+ %srcptr = getelementptr inbounds %Vec4, ptr addrspace(1) %_arg, i64 0
+ %r1 = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv4_aPU3AS1KS_mm9ocl_event(i32 2, ptr addrspace(3) %_arg_Local, ptr addrspace(1) %srcptr, i64 16, i64 10, target("spirv.Event") zeroinitializer)
+ store target("spirv.Event") %r1, ptr %E1
+ %E.ascast.i = addrspacecast ptr %E1 to ptr addrspace(4)
+ call spir_func void @_Z23__spirv_GroupWaitEventsjiP9ocl_event(i32 2, i32 1, ptr addrspace(4) %E.ascast.i)
+ ret void
+}
+
+declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv4_aPU3AS1KS_mm9ocl_event(i32, ptr addrspace(3), ptr addrspace(1), i64, i64, target("spirv.Event"))
+declare dso_local spir_func void @_Z23__spirv_GroupWaitEventsjiP9ocl_event(i32, i32, ptr addrspace(4))
+
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll
index 7658362773218..311c7c934c4bd 100644
--- a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll
+++ b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll
@@ -1,97 +1,100 @@
-; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s
+; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %}
-; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s
-; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
-
-; CHECK-DAG: %[[#TyEvent:]] = OpTypeEvent
-; CHECK-DAG: %[[#TyStruct:]] = OpTypeStruct %[[#TyEvent]]
-; CHECK-DAG: %[[#ConstEvent:]] = OpConstantNull %[[#TyEvent]]
-; CHECK-DAG: %[[#TyEventPtr:]] = OpTypePointer Function %[[#TyEvent]]
-; CHECK-DAG: %[[#TyEventPtrGen:]] = OpTypePointer Generic %[[#TyEvent]]
-; CHECK-DAG: %[[#TyStructPtr:]] = OpTypePointer Function %[[#TyStruct]]
-; CHECK-DAG: %[[#TyChar:]] = OpTypeInt 8 0
-; CHECK-DAG: %[[#TyV4:]] = OpTypeVector %[[#TyChar]] 4
-; CHECK-DAG: %[[#TyStructV4:]] = OpTypeStruct %[[#TyV4]]
-; CHECK-DAG: %[[#TyPtrSV4_CW:]] = OpTypePointer CrossWorkgroup %[[#TyStructV4]]
-; CHECK-DAG: %[[#TyPtrV4_W:]] = OpTypePointer Workgroup %[[#TyV4]]
-; CHECK-DAG: %[[#TyPtrV4_CW:]] = OpTypePointer CrossWorkgroup %[[#TyV4]]
-; CHECK-DAG: %[[#TyHalf:]] = OpTypeFloat 16
-; CHECK-DAG: %[[#TyHalfV2:]] = OpTypeVector %[[#TyHalf]] 2
-; CHECK-DAG: %[[#TyHalfV2_W:]] = OpTypePointer Workgroup %[[#TyHalfV2]]
-; CHECK-DAG: %[[#TyHalfV2_CW:]] = OpTypePointer CrossWorkgroup %[[#TyHalfV2]]
+; CHECK-SPIRV-DAG: %[[#IntTy:]] = OpTypeInt 32 0
+; CHECK-SPIRV-DAG: %[[#EventTy:]] = OpTypeEvent
+; CHECK-SPIRV-DAG: %[[#ConstEvent:]] = OpConstantNull %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyEventPtr:]] = OpTypePointer Function %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyEventPtrGen:]] = OpTypePointer Generic %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyStruct:]] = OpTypeStruct %[[#EventTy]]
+; CHECK-SPIRV-DAG: %[[#TyStructPtr:]] = OpTypePointer Function %[[#TyStruct]]
+; CHECK-SPIRV-DAG: %[[#TyChar:]] = OpTypeInt 8 0
+; CHECK-SPIRV-DAG: %[[#TyV4:]] = OpTypeVector %[[#TyChar]] 4
+; CHECK-SPIRV-DAG: %[[#TyStructV4:]] = OpTypeStruct %[[#TyV4]]
+; CHECK-SPIRV-DAG: %[[#TyPtrSV4_CW:]] = OpTypePointer CrossWorkgroup %[[#TyStructV4]]
+; CHECK-SPIRV-DAG: %[[#TyPtrV4_W:]] = OpTypePointer Workgroup %[[#TyV4]]
+; CHECK-SPIRV-DAG: %[[#TyPtrV4_CW:]] = OpTypePointer CrossWorkgroup %[[#TyV4]]
+; CHECK-SPIRV-DAG: %[[#TyHalf:]] = OpTypeFloat 16
+; CHECK-SPIRV-DAG: %[[#TyHalfV2:]] = OpTypeVector %[[#TyHalf]] 2
+; CHECK-SPIRV-DAG: %[[#TyHalfV2_W:]] = OpTypePointer Workgroup %[[#TyHalfV2]]
+; CHECK-SPIRV-DAG: %[[#TyHalfV2_CW:]] = OpTypePointer CrossWorkgroup %[[#TyHalfV2]]
+; CHECK-SPIRV-DAG: %[[#Scope:]] = OpConstant %[[#IntTy]] 2
+; CHECK-SPIRV-DAG: %[[#NumElem:]] = OpConstant %[[#IntTy]] 16
+; CHECK-SPIRV-DAG: %[[#Stride:]] = OpConstant %[[#IntTy]] 10
+; CHECK-SPIRV-DAG: %[[#NumEvents:]] = OpConstant %[[#IntTy]] 1
; Check correct translation of __spirv_GroupAsyncCopy and target("spirv.Event") zeroinitializer
-; CHECK: OpFunction
-; CHECK: %[[#HalfA1:]] = OpFunctionParameter %[[#TyHalfV2_W:]]
-; CHECK: %[[#HalfA2:]] = OpFunctionParameter %[[#TyHalfV2_CW:]]
-; CHECK: OpGroupAsyncCopy %[[#TyEvent]] %[[#]] %[[#HalfA1]] %[[#HalfA2]] %[[#]] %[[#]] %[[#ConstEvent]]
-; CHECK: OpFunctionEnd
-
%StructEvent = type { target("spirv.Event") }
@G_r = global target("spirv.Event") poison
+; CHECK-SPIRV: OpFunction
+; CHECK-SPIRV: %[[#HalfA1:]] = OpFunctionParameter %[[#TyHalfV2_W]]
+; CHECK-SPIRV: %[[#HalfA2:]] = OpFunctionParameter %[[#TyHalfV2_CW]]
+; CHECK-SPIRV: OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#HalfA1]] %[[#HalfA2]] %[[#NumElem]] %[[#Stride]] %[[#ConstEvent]]
+; CHECK-SPIRV: OpFunctionEnd
+
define spir_kernel void @test_half(ptr addrspace(3) %_arg1, ptr addrspace(1) %_arg2) {
entry:
- %r = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv2_DF16_PU3AS1KS_mm9ocl_event(i32 2, ptr addrspace(3) %_arg1, ptr addrspace(1) %_arg2, i64 16, i64 10, target("spirv.Event") zeroinitializer)
+ %r = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv2_DF16_PU3AS1KS_jj9ocl_event(i32 2, ptr addrspace(3) %_arg1, ptr addrspace(1) %_arg2, i32 16, i32 10, target("spirv.Event") zeroinitializer)
store target("spirv.Event") %r, ptr @G_r
ret void
}
-declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv2_DF16_PU3AS1KS_mm9ocl_event(i32 noundef, ptr addrspace(3) noundef, ptr addrspace(1) noundef, i64 noundef, i64 noundef, target("spirv.Event"))
+declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv2_DF16_PU3AS1KS_jj9ocl_event(i32 noundef, ptr addrspace(3) noundef, ptr addrspace(1) noundef, i32 noundef, i32 noundef, target("spirv.Event"))
-; CHECK: OpFunction
-; CHECK: OpFunctionParameter
-; CHECK: %[[#Src:]] = OpFunctionParameter
-; CHECK: %[[#EventVar:]] = OpVariable %[[#TyEventPtr]] Function
-; CHECK: %[[#Dest:]] = OpInBoundsPtrAccessChain
-; CHECK: %[[#CopyRes:]] = OpGroupAsyncCopy %[[#TyEvent]] %[[#]] %[[#Dest]] %[[#Src]] %[[#]] %[[#]] %[[#ConstEvent]]
-; CHECK: OpStore %[[#EventVar]] %[[#CopyRes]]
-; CHECK: OpFunctionEnd
+; CHECK-SPIRV: OpFunction
+; CHECK-SPIRV: OpFunctionParameter
+; CHECK-SPIRV: %[[#Src:]] = OpFunctionParameter
+; CHECK-SPIRV: %[[#EventVar:]] = OpVariable %[[#TyEventPtr]] Function
+; CHECK-SPIRV: %[[#Dest:]] = OpInBoundsPtrAccessChain
+; CHECK-SPIRV: %[[#CopyRes:]] = OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#Dest]] %[[#Src]] %[[#NumElem]] %[[#Stride]] %[[#ConstEvent]]
+; CHECK-SPIRV: OpStore %[[#EventVar]] %[[#CopyRes]]
+; CHECK-SPIRV: OpFunctionEnd
define spir_kernel void @foo(ptr addrspace(1) %_arg_out_ptr, ptr addrspace(3) %_arg_local_acc) {
entry:
%var = alloca %StructEvent
%dev_event.i.sroa.0 = alloca target("spirv.Event")
%add.ptr.i26 = getelementptr inbounds i32, ptr addrspace(1) %_arg_out_ptr, i64 0
- %call3.i = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kimm9ocl_event(i32 2, ptr addrspace(1) %add.ptr.i26, ptr addrspace(3) %_arg_local_acc, i64 16, i64 10, target("spirv.Event") zeroinitializer)
+ %call3.i = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kijj9ocl_event(i32 2, ptr addrspace(1) %add.ptr.i26, ptr addrspace(3) %_arg_local_acc, i32 16, i32 10, target("spirv.Event") zeroinitializer)
store target("spirv.Event") %call3.i, ptr %dev_event.i.sroa.0
ret void
}
-declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kimm9ocl_event(i32, ptr addrspace(1), ptr addrspace(3), i64, i64, target("spirv.Event"))
+declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS1iPU3AS3Kijj9ocl_event(i32, ptr addrspace(1), ptr addrspace(3), i32, i32, target("spirv.Event"))
; Check correct type inference when calling __spirv_GroupAsyncCopy:
; we expect that the Backend is able to deduce a type of the %_arg_Local
; given facts that it's possible to deduce a type of the %_arg
; and %_arg_Local and %_arg are source/destination arguments in OpGroupAsyncCopy
-; CHECK: OpFunction
-; CHECK: %[[#BarArg1:]] = OpFunctionParameter %[[#TyPtrV4_W]]
-; CHECK: %[[#BarArg2:]] = OpFunctionParameter %[[#TyPtrSV4_CW]]
-; CHECK: %[[#EventVarBar:]] = OpVariable %[[#TyStructPtr]] Function
-; CHECK: %[[#EventVarBarCasted2:]] = OpBitcast %[[#TyEventPtr]] %[[#EventVarBar]]
-; CHECK: %[[#ResBar:]] = OpGroupAsyncCopy %[[#TyEvent]] %[[#]] %[[#BarArg1]] %[[#]] %[[#]] %[[#]] %[[#ConstEvent]]
-; CHECK: %[[#EventVarBarCasted:]] = OpBitcast %[[#TyEventPtr]] %[[#EventVarBar]]
-; CHECK: OpStore %[[#EventVarBarCasted]] %[[#ResBar]]
-; CHECK: %[[#EventVarBarGen:]] = OpPtrCastToGeneric %[[#TyEventPtrGen]] %[[#EventVarBarCasted2]]
-; CHECK: OpGroupWaitEvents %[[#]] %[[#]] %[[#EventVarBarGen]]
-; CHECK: OpFunctionEnd
-
%Vec4 = type { <4 x i8> }
+; CHECK-SPIRV: OpFunction
+; CHECK-SPIRV: %[[#BarArg1:]] = OpFunctionParameter %[[#TyPtrV4_W]]
+; CHECK-SPIRV: %[[#BarArg2:]] = OpFunctionParameter %[[#TyPtrSV4_CW]]
+; CHECK-SPIRV: %[[#EventVarBar:]] = OpVariable %[[#TyStructPtr]] Function
+; CHECK-SPIRV: %[[#EventVarBarCasted2:]] = OpBitcast %[[#TyEventPtr]] %[[#EventVarBar]]
+; CHECK-SPIRV: %[[#ResBar:]] = OpGroupAsyncCopy %[[#EventTy]] %[[#Scope]] %[[#BarArg1]] %[[#]] %[[#NumElem]] %[[#Stride]] %[[#ConstEvent]]
+; CHECK-SPIRV: %[[#EventVarBarCasted:]] = OpBitcast %[[#TyEventPtr]] %[[#EventVarBar]]
+; CHECK-SPIRV: OpStore %[[#EventVarBarCasted]] %[[#ResBar]]
+; CHECK-SPIRV: %[[#EventVarBarGen:]] = OpPtrCastToGeneric %[[#TyEventPtrGen]] %[[#EventVarBarCasted2]]
+; CHECK-SPIRV: OpGroupWaitEvents %[[#Scope]] %[[#NumEvents]] %[[#EventVarBarGen]]
+; CHECK-SPIRV: OpFunctionEnd
+
define spir_kernel void @bar(ptr addrspace(3) %_arg_Local, ptr addrspace(1) readonly %_arg) {
entry:
%E1 = alloca %StructEvent
%srcptr = getelementptr inbounds %Vec4, ptr addrspace(1) %_arg, i64 0
- %r1 = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv4_aPU3AS1KS_mm9ocl_event(i32 2, ptr addrspace(3) %_arg_Local, ptr addrspace(1) %srcptr, i64 16, i64 10, target("spirv.Event") zeroinitializer)
+ %r1 = tail call spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv4_aPU3AS1KS_jj9ocl_event(i32 2, ptr addrspace(3) %_arg_Local, ptr addrspace(1) %srcptr, i32 16, i32 10, target("spirv.Event") zeroinitializer)
store target("spirv.Event") %r1, ptr %E1
%E.ascast.i = addrspacecast ptr %E1 to ptr addrspace(4)
call spir_func void @_Z23__spirv_GroupWaitEventsjiP9ocl_event(i32 2, i32 1, ptr addrspace(4) %E.ascast.i)
ret void
}
-declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv4_aPU3AS1KS_mm9ocl_event(i32, ptr addrspace(3), ptr addrspace(1), i64, i64, target("spirv.Event"))
+declare dso_local spir_func target("spirv.Event") @_Z22__spirv_GroupAsyncCopyjPU3AS3Dv4_aPU3AS1KS_jj9ocl_event(i32, ptr addrspace(3), ptr addrspace(1), i32, i32, target("spirv.Event"))
declare dso_local spir_func void @_Z23__spirv_GroupWaitEventsjiP9ocl_event(i32, i32, ptr addrspace(4))
+
>From 70e3c12ce004b6185465e32d9340a4cc4e7f7e43 Mon Sep 17 00:00:00 2001
From: Manuel Carrasco <Manuel.Carrasco at amd.com>
Date: Fri, 30 Jan 2026 11:31:30 -0600
Subject: [PATCH 2/2] [review] Use default CHECK.
---
.../CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll | 2 +-
llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll | 2 +-
llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll | 2 +-
llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll | 2 +-
4 files changed, 4 insertions(+), 4 deletions(-)
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll
index b5ba122c71943..f4b42290bee4a 100644
--- a/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll
+++ b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided-64.ll
@@ -1,4 +1,4 @@
-; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
+; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
; CHECK-SPIRV-DAG: %[[#LongTy:]] = OpTypeInt 64 0
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll
index aa607d25df85e..b0b961b07ded5 100644
--- a/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll
+++ b/llvm/test/CodeGen/SPIRV/transcoding/OpGroupAsyncCopy-strided.ll
@@ -1,4 +1,4 @@
-; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
+; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %}
; CHECK-SPIRV-DAG: %[[#IntTy:]] = OpTypeInt 32 0
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll
index 572069cfba709..dac672270f970 100644
--- a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll
+++ b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null-64.ll
@@ -1,4 +1,4 @@
-; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
+; RUN: llc -O0 -mtriple=spirv64-unknown-unknown %s -o - | FileCheck %s
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv64-unknown-unknown %s -o - -filetype=obj | spirv-val %}
; CHECK-SPIRV-DAG: %[[#IntTy:]] = OpTypeInt 32 0
diff --git a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll
index 311c7c934c4bd..68d2203de10af 100644
--- a/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll
+++ b/llvm/test/CodeGen/SPIRV/transcoding/spirv-event-null.ll
@@ -1,4 +1,4 @@
-; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s --check-prefix=CHECK-SPIRV
+; RUN: llc -O0 -mtriple=spirv32-unknown-unknown %s -o - | FileCheck %s
; RUN: %if spirv-tools %{ llc -O0 -mtriple=spirv32-unknown-unknown %s -o - -filetype=obj | spirv-val %}
; CHECK-SPIRV-DAG: %[[#IntTy:]] = OpTypeInt 32 0
More information about the llvm-commits
mailing list