mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
This attribute was introduced in 7eca38ce76d5d1915f4ab7e665964062c0b37697 (llvm-project). Match it using a wildcard regex, since it is not relevant to these tests. This is intended to reduce future conflicts with rebranch.
156 lines
7.9 KiB
Plaintext
156 lines
7.9 KiB
Plaintext
// RUN: %target-swift-frontend -emit-irgen -disable-emit-type-malloc-for-coro-frame %s | %FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-%target-cpu --check-prefix=CHECK-%target-ptrsize -DINT=i%target-ptrsize
|
|
|
|
import Builtin
|
|
|
|
sil @marker : $(Builtin.Int64) -> ()
|
|
|
|
sil @coro_ret : $@yield_once @convention(thin) () -> (@yields Builtin.Int64, Builtin.Int64)
|
|
sil @coro_ret_pair : $@yield_once @convention(thin) () -> (@yields Builtin.Int64, Builtin.Int64, Builtin.Int64)
|
|
|
|
// CHECK-LABEL: define{{( dllexport)?}}{{( protected)?}} swiftcc ptr @test_simple
|
|
// CHECK-32-SAME: ptr noalias dereferenceable([[BUFFER_SIZE:16]]) %0)
|
|
// CHECK-64-SAME: (ptr noalias dereferenceable([[BUFFER_SIZE:32]]) %0)
|
|
// CHECK-SAME: [[CORO_ATTRIBUTES:#[0-9]+]]
|
|
sil @test_simple : $@yield_once () -> (Builtin.Int64) {
|
|
entry:
|
|
// CHECK-32: [[ID:%.*]] = call token (i32, i32, ptr, ptr, ptr, ptr, ...) @llvm.coro.id.retcon.once(i32 [[BUFFER_SIZE]], i32 [[BUFFER_ALIGN:4]], ptr %0, ptr @"$sBi64_IetAd_TC{{(.ptrauth)?}}", ptr @malloc, ptr @free)
|
|
// CHECK-64: [[ID:%.*]] = call token (i32, i32, ptr, ptr, ptr, ptr, ...) @llvm.coro.id.retcon.once(i32 [[BUFFER_SIZE]], i32 [[BUFFER_ALIGN:8]], ptr %0, ptr @"$sBi64_IetAd_TC{{(.ptrauth)?}}", ptr @malloc, ptr @free)
|
|
// CHECK-NEXT: [[BEGIN:%.*]] = call ptr @llvm.coro.begin(token [[ID]], ptr null)
|
|
|
|
// CHECK-NEXT: call swiftcc void @marker(i64 1000)
|
|
%marker = function_ref @marker : $@convention(thin) (Builtin.Int64) -> ()
|
|
%1000 = integer_literal $Builtin.Int64, 1000
|
|
apply %marker(%1000) : $@convention(thin) (Builtin.Int64) -> ()
|
|
|
|
// CHECK-NEXT: [[IS_UNWIND:%.*]] = call i1 (...) @llvm.coro.suspend.retcon.i1()
|
|
// CHECK-NEXT: br i1 [[IS_UNWIND]], label [[UNWIND_BB:%.*]], label [[RESUME_BB:%.*]]
|
|
yield (), resume resume, unwind unwind
|
|
|
|
resume:
|
|
// CHECK: call swiftcc void @marker(i64 2000)
|
|
%2000 = integer_literal $Builtin.Int64, 2000
|
|
apply %marker(%2000) : $@convention(thin) (Builtin.Int64) -> ()
|
|
// CHECK: br label %coro.end
|
|
return %2000 : $Builtin.Int64
|
|
|
|
unwind:
|
|
// CHECK: call swiftcc void @marker(i64 3000)
|
|
%3000 = integer_literal $Builtin.Int64, 3000
|
|
apply %marker(%3000) : $@convention(thin) (Builtin.Int64) -> ()
|
|
// CHECK: br label %coro.end
|
|
unwind
|
|
|
|
// CHECK: coro.end:
|
|
// CHECK: [[RESULT:%.*]] = phi i64 [ 2000, [[RESUME_BB]] ], [ undef, [[UNWIND_BB]] ]
|
|
// CHECK: [[TOKEN:%.*]] = call token (...) @llvm.coro.end.results(i64 [[RESULT]])
|
|
// CHECK: call i1 @llvm.coro.end(ptr [[BEGIN]], i1 false, token [[TOKEN]])
|
|
// CHECK-NEXT: unreachable
|
|
}
|
|
|
|
// CHECK-LABEL: declare{{( dllimport)?}}{{( protected)?}} swiftcc i64 @"$sBi64_IetAd_TC{{(.ptrauth)?}}"
|
|
// CHECK-SAME: (ptr noalias dereferenceable([[BUFFER_SIZE]]), i1)
|
|
|
|
// CHECK-LABEL: test_coro_ret
|
|
sil @test_coro_ret : $() -> (Builtin.Int64, Builtin.Int64, Builtin.Int64) {
|
|
entry:
|
|
%marker = function_ref @marker : $@convention(thin) (Builtin.Int64) -> ()
|
|
|
|
%coro1 = function_ref @coro_ret : $@yield_once @convention(thin) () -> (@yields Builtin.Int64, Builtin.Int64)
|
|
(%first, %token1) = begin_apply %coro1() : $@yield_once @convention(thin) () -> (@yields Builtin.Int64, Builtin.Int64)
|
|
|
|
// CHECK: [[T0:%.*]] = alloca {{\[}}[[BUFFER_SIZE1:.*]] x i8
|
|
// CHECK: [[T1:%.*]] = alloca {{\[}}[[BUFFER_SIZE2:.*]] x i8
|
|
// CHECK: [[BUFFER1:%.*]] = getelementptr inbounds{{.*}} {{\[}}[[BUFFER_SIZE1]] x i8], ptr [[T0]], i32 0, i32 0
|
|
// CHECK: [[CORO1:%.*]] = call ptr @llvm.coro.prepare.retcon(ptr @coro_ret)
|
|
// CHECK: [[FRAME1:%.*]] = call swiftcc { ptr, i64 } [[CORO1]](ptr noalias dereferenceable([[BUFFER_SIZE1]]) [[BUFFER1]]
|
|
// CHECK: [[CONT1:%.*]] = extractvalue { ptr, i64 } [[FRAME1]], 0
|
|
|
|
apply %marker(%first) : $@convention(thin) (Builtin.Int64) -> ()
|
|
|
|
%ret = end_apply %token1 as $Builtin.Int64
|
|
|
|
// CHECK: call swiftcc i64 [[CONT1]](ptr noalias dereferenceable([[BUFFER_SIZE1]]) [[BUFFER1]], i1 false)
|
|
|
|
apply %marker(%ret) : $@convention(thin) (Builtin.Int64) -> ()
|
|
|
|
%coro2 = function_ref @coro_ret_pair : $@yield_once @convention(thin) () -> (@yields Builtin.Int64, Builtin.Int64, Builtin.Int64)
|
|
(%second, %token2) = begin_apply %coro2() : $@yield_once @convention(thin) () -> (@yields Builtin.Int64, Builtin.Int64, Builtin.Int64)
|
|
|
|
// CHECK: [[BUFFER2:%.*]] = getelementptr inbounds{{.*}} {{\[}}[[BUFFER_SIZE2]] x i8], ptr [[T1]], i32 0, i32 0
|
|
// CHECK: [[CORO2:%.*]] = call ptr @llvm.coro.prepare.retcon(ptr @coro_ret_pair)
|
|
// CHECK: [[FRAME2:%.*]] = call swiftcc { ptr, i64 } [[CORO2]](ptr noalias dereferenceable([[BUFFER_SIZE2]]) [[BUFFER2]]
|
|
// CHECK: [[CONT2:%.*]] = extractvalue { ptr, i64 } [[FRAME2]], 0
|
|
|
|
%ret2 = end_apply %token2 as $(Builtin.Int64, Builtin.Int64)
|
|
|
|
// CHECK: call swiftcc { i64, i64 } [[CONT2]](ptr noalias dereferenceable([[BUFFER_SIZE2]]) [[BUFFER2]], i1 false)
|
|
|
|
%ret2_1 = tuple_extract %ret2 : $(Builtin.Int64, Builtin.Int64), 0
|
|
%ret2_2 = tuple_extract %ret2 : $(Builtin.Int64, Builtin.Int64), 1
|
|
|
|
apply %marker(%second) : $@convention(thin) (Builtin.Int64) -> ()
|
|
|
|
%retf = tuple (%ret : $Builtin.Int64, %ret2_1 : $Builtin.Int64, %ret2_2 : $Builtin.Int64)
|
|
return %retf : $(Builtin.Int64, Builtin.Int64, Builtin.Int64)
|
|
}
|
|
|
|
// CHECK-LABEL: coro_ret_indirect
|
|
// CHECK-SAME: ptr{{.*}} [[CTX:%.*]], ptr{{.*}} [[INDIRECT_RET:%.*]], ptr{{.*}} [[ARG:%.*]], ptr{{.*}} [[TYPE:%.*]])
|
|
sil @coro_ret_indirect : $@yield_once @convention(thin) <T> (@in T) -> (@yields @in T, @out T) {
|
|
bb0(%outt : $*T, %t : $*T):
|
|
// CHECK-32: [[ID:%.*]] = call token (i32, i32, ptr, ptr, ptr, ptr, ...) @llvm.coro.id.retcon.once(i32 [[BUFFER_SIZE]], i32 [[BUFFER_ALIGN:4]], ptr [[CTX]], ptr @"$sxxxlIetAirYi_TC{{(.ptrauth)?}}", ptr @malloc, ptr @free)
|
|
// CHECK-64: [[ID:%.*]] = call token (i32, i32, ptr, ptr, ptr, ptr, ...) @llvm.coro.id.retcon.once(i32 [[BUFFER_SIZE]], i32 [[BUFFER_ALIGN:8]], ptr [[CTX]], ptr @"$sxxxlIetAirYi_TC{{(.ptrauth)?}}", ptr @malloc, ptr @free)
|
|
|
|
// CHECK: [[IS_UNWIND:%.*]] = call i1 (...) @llvm.coro.suspend.retcon.i1(ptr [[ARG]])
|
|
// CHECK: br i1 [[IS_UNWIND]], label %[[UNWIND_BB:.*]], label %[[RESUME_BB:.*]]
|
|
|
|
// CHECK:[[RESUME_BB]]:
|
|
// CHECK: [[VW_PTR:%.*]] = getelementptr inbounds ptr, ptr [[TYPE]], [[INT]] -1
|
|
// CHECK: [[VW:%.*]] = load ptr, ptr [[VW_PTR]]
|
|
// CHECK-arm64e-NEXT: ptrtoint ptr [[VW_PTR]] to i64
|
|
// CHECK-arm64e-NEXT: call i64 @llvm.ptrauth.blend
|
|
// CHECK-arm64e: [[VW:%.*]] = inttoptr i64 {{%.*}} to ptr
|
|
// CHECK: [[ASSIGN_PTR:%.*]] = getelementptr inbounds ptr, ptr [[VW]], i32 3
|
|
// CHECK: [[ASSIGN:%.*]] = load ptr, ptr [[ASSIGN_PTR]]
|
|
// CHECK: call ptr [[ASSIGN]](ptr [[INDIRECT_RET]], ptr [[ARG]], ptr [[TYPE]]) #2
|
|
|
|
yield (%t : $*T), resume bb1, unwind bb2
|
|
|
|
bb1:
|
|
copy_addr %t to %outt : $*T
|
|
%r = tuple ()
|
|
return %r : $()
|
|
|
|
bb2:
|
|
unwind
|
|
}
|
|
|
|
// CHECK-LABEL: @test_coro_ret_indirect
|
|
// CHECK-SAME: (i64 [[ARG:%.*]])
|
|
sil [ossa] @test_coro_ret_indirect : $(Builtin.Int64) -> () {
|
|
bb0(%0 : $Builtin.Int64):
|
|
// CHECK: [[ARG_COPY:%.*]] = alloca i64
|
|
// CHECK: [[INDIRECT_RET:%.*]] = alloca i64
|
|
// CHECK: [[FRAME:%.*]] = alloca [[[BUFFER_SIZE]] x i8]
|
|
%coro = function_ref @coro_ret_indirect : $@yield_once @convention(thin) <T> (@in T) -> (@yields @in T, @out T)
|
|
%temp = alloc_stack $Builtin.Int64
|
|
store %0 to [trivial] %temp : $*Builtin.Int64
|
|
|
|
%out = alloc_stack $Builtin.Int64
|
|
|
|
// CHECK: store i64 [[ARG]], ptr [[ARG_COPY]]
|
|
// CHECK: [[CTX:%.*]] = getelementptr inbounds{{.*}} [[[BUFFER_SIZE]] x i8], ptr [[FRAME]], i32 0, i32 0
|
|
// CHECK: [[CORO:%.*]] = call ptr @llvm.coro.prepare.retcon(ptr @coro_ret_indirect)
|
|
// CHECK: [[FRAME:%.*]] = call swiftcc { ptr, ptr } [[CORO]](ptr{{.*}} [[CTX]], ptr [[INDIRECT_RET]], ptr noalias [[ARG_COPY]], ptr getelementptr inbounds (%swift.full_existential_type, ptr @{{.*}}
|
|
|
|
(%f1, %token) = begin_apply %coro<Builtin.Int64>(%out, %temp) : $@yield_once @convention(thin) <T> (@in T) -> (@yields @in T, @out T)
|
|
|
|
%f2 = end_apply %token as $()
|
|
|
|
dealloc_stack %out : $*Builtin.Int64
|
|
dealloc_stack %temp : $*Builtin.Int64
|
|
|
|
%r = tuple ()
|
|
return %r : $()
|
|
}
|