1// RUN:   mlir-opt %s -pass-pipeline="async-to-async-runtime,func.func(async-runtime-ref-counting,async-runtime-ref-counting-opt),convert-async-to-llvm,func.func(convert-linalg-to-loops,convert-scf-to-cf),convert-linalg-to-llvm,convert-vector-to-llvm,func.func(convert-arith-to-llvm),convert-func-to-llvm,reconcile-unrealized-casts" \
2// RUN: | mlir-cpu-runner                                                      \
3// RUN:     -e main -entry-point-result=void -O0                               \
4// RUN:     -shared-libs=%linalg_test_lib_dir/libmlir_c_runner_utils%shlibext  \
5// RUN:     -shared-libs=%linalg_test_lib_dir/libmlir_runner_utils%shlibext    \
6// RUN:     -shared-libs=%linalg_test_lib_dir/libmlir_async_runtime%shlibext   \
7// RUN: | FileCheck %s --dump-input=always
8
9func.func @main() {
10  %false = arith.constant 0 : i1
11
12  // ------------------------------------------------------------------------ //
13  // Check that simple async region completes without errors.
14  // ------------------------------------------------------------------------ //
15  %token0 = async.execute {
16    async.yield
17  }
18  async.runtime.await %token0 : !async.token
19
20  // CHECK: 0
21  %err0 = async.runtime.is_error %token0 : !async.token
22  vector.print %err0 : i1
23
24  // ------------------------------------------------------------------------ //
25  // Check that assertion in the async region converted to async error.
26  // ------------------------------------------------------------------------ //
27  %token1 = async.execute {
28    cf.assert %false, "error"
29    async.yield
30  }
31  async.runtime.await %token1 : !async.token
32
33  // CHECK: 1
34  %err1 = async.runtime.is_error %token1 : !async.token
35  vector.print %err1 : i1
36
37  // ------------------------------------------------------------------------ //
38  // Check error propagation from the nested region.
39  // ------------------------------------------------------------------------ //
40  %token2 = async.execute {
41    %token = async.execute {
42      cf.assert %false, "error"
43      async.yield
44    }
45    async.await %token : !async.token
46    async.yield
47  }
48  async.runtime.await %token2 : !async.token
49
50  // CHECK: 1
51  %err2 = async.runtime.is_error %token2 : !async.token
52  vector.print %err2 : i1
53
54  // ------------------------------------------------------------------------ //
55  // Check error propagation from the nested region with async values.
56  // ------------------------------------------------------------------------ //
57  %token3, %value3 = async.execute -> !async.value<f32> {
58    %token, %value = async.execute -> !async.value<f32> {
59      cf.assert %false, "error"
60      %0 = arith.constant 123.45 : f32
61      async.yield %0 : f32
62    }
63    %ret = async.await %value : !async.value<f32>
64    async.yield %ret : f32
65  }
66  async.runtime.await %token3 : !async.token
67  async.runtime.await %value3 : !async.value<f32>
68
69  // CHECK: 1
70  // CHECK: 1
71  %err3_0 = async.runtime.is_error %token3 : !async.token
72  %err3_1 = async.runtime.is_error %value3 : !async.value<f32>
73  vector.print %err3_0 : i1
74  vector.print %err3_1 : i1
75
76  // ------------------------------------------------------------------------ //
77  // Check error propagation from a token to the group.
78  // ------------------------------------------------------------------------ //
79
80  %c2 = arith.constant 2 : index
81  %group0 = async.create_group %c2 : !async.group
82
83  %token4 = async.execute {
84    async.yield
85  }
86
87  %token5 = async.execute {
88    cf.assert %false, "error"
89    async.yield
90  }
91
92  %idx0 = async.add_to_group %token4, %group0 : !async.token
93  %idx1 = async.add_to_group %token5, %group0 : !async.token
94
95  async.runtime.await %group0 : !async.group
96
97  // CHECK: 1
98  %err4 = async.runtime.is_error %group0 : !async.group
99  vector.print %err4 : i1
100
101  return
102}
103