OLD | NEW |
---|---|
1 ; RUN: opt < %s -resolve-pnacl-intrinsics -S | FileCheck %s | 1 ; RUN: opt < %s -resolve-pnacl-intrinsics -S | FileCheck %s |
2 | 2 |
3 declare i32 @llvm.nacl.setjmp(i8*) | 3 declare i32 @llvm.nacl.setjmp(i8*) |
4 declare void @llvm.nacl.longjmp(i8*, i32) | 4 declare void @llvm.nacl.longjmp(i8*, i32) |
5 | 5 |
6 ; These declarations must be here because the function pass expects | 6 ; These declarations must be here because the function pass expects |
7 ; to find them. In real life they're inserted by the translator | 7 ; to find them. In real life they're inserted by the translator |
8 ; before the function pass runs. | 8 ; before the function pass runs. |
9 declare i32 @setjmp(i8*) | 9 declare i32 @setjmp(i8*) |
10 declare void @longjmp(i8*, i32) | 10 declare void @longjmp(i8*, i32) |
11 declare i8 @llvm.nacl.atomic.8(i32, i8*, i8, i8, i32) | |
12 declare i16 @llvm.nacl.atomic.16(i32, i16*, i16, i16, i32) | |
13 declare i32 @llvm.nacl.atomic.32(i32, i32*, i32, i32, i32) | |
14 declare i64 @llvm.nacl.atomic.64(i32, i64*, i64, i64, i32) | |
11 | 15 |
12 ; CHECK-NOT: call i32 @llvm.nacl.setjmp | 16 ; CHECK-NOT: call i32 @llvm.nacl.setjmp |
13 ; CHECK-NOT: call void @llvm.nacl.longjmp | 17 ; CHECK-NOT: call void @llvm.nacl.longjmp |
14 | 18 |
15 define i32 @call_setjmp(i8* %arg) { | 19 define i32 @call_setjmp(i8* %arg) { |
16 %val = call i32 @llvm.nacl.setjmp(i8* %arg) | 20 %val = call i32 @llvm.nacl.setjmp(i8* %arg) |
17 ; CHECK: %val = call i32 @setjmp(i8* %arg) | 21 ; CHECK: %val = call i32 @setjmp(i8* %arg) |
18 ret i32 %val | 22 ret i32 %val |
19 } | 23 } |
20 | 24 |
21 define void @call_longjmp(i8* %arg, i32 %num) { | 25 define void @call_longjmp(i8* %arg, i32 %num) { |
22 call void @llvm.nacl.longjmp(i8* %arg, i32 %num) | 26 call void @llvm.nacl.longjmp(i8* %arg, i32 %num) |
23 ; CHECK: call void @longjmp(i8* %arg, i32 %num) | 27 ; CHECK: call void @longjmp(i8* %arg, i32 %num) |
24 ret void | 28 ret void |
25 } | 29 } |
30 | |
31 ; atomics | |
32 ; Only load/store tests {i8, i16, i32, i64}, the others only test i32 | |
33 ; since the mechanism should be the same. | |
34 | |
35 ; CHECK: @test_fetch_and_add_i32 | |
36 define i32 @test_fetch_and_add_i32(i32* %ptr, i32 %value) { | |
37 ; CHECK: %1 = atomicrmw add i32* %ptr, i32 %value seq_cst | |
38 ; CHECK-NOT: @llvm.nacl.atomic | |
Mark Seaborn
2013/06/26 14:33:41
This would be better done with the following once,
JF
2013/06/26 15:52:29
Done.
| |
39 %1 = call i32 @llvm.nacl.atomic.32(i32 3, i32* %ptr, i32 %value, i32 0, i32 6) | |
40 ret i32 %1 | |
41 } | |
42 | |
43 ; CHECK: @test_fetch_and_sub_i32 | |
44 define i32 @test_fetch_and_sub_i32(i32* %ptr, i32 %value) { | |
45 ; CHECK: %1 = atomicrmw sub i32* %ptr, i32 %value seq_cst | |
46 ; CHECK-NOT: @llvm.nacl.atomic | |
47 %1 = call i32 @llvm.nacl.atomic.32(i32 4, i32* %ptr, i32 %value, i32 0, i32 6) | |
48 ret i32 %1 | |
49 } | |
50 | |
51 ; CHECK: @test_fetch_and_or_i32 | |
52 define i32 @test_fetch_and_or_i32(i32* %ptr, i32 %value) { | |
53 ; CHECK: %1 = atomicrmw or i32* %ptr, i32 %value seq_cst | |
54 ; CHECK-NOT: @llvm.nacl.atomic | |
55 %1 = call i32 @llvm.nacl.atomic.32(i32 5, i32* %ptr, i32 %value, i32 0, i32 6) | |
56 ret i32 %1 | |
57 } | |
58 | |
59 ; CHECK: @test_fetch_and_and_i32 | |
60 define i32 @test_fetch_and_and_i32(i32* %ptr, i32 %value) { | |
61 ; CHECK: %1 = atomicrmw and i32* %ptr, i32 %value seq_cst | |
62 ; CHECK-NOT: @llvm.nacl.atomic | |
63 %1 = call i32 @llvm.nacl.atomic.32(i32 6, i32* %ptr, i32 %value, i32 0, i32 6) | |
64 ret i32 %1 | |
65 } | |
66 | |
67 ; CHECK: @test_fetch_and_xor_i32 | |
68 define i32 @test_fetch_and_xor_i32(i32* %ptr, i32 %value) { | |
69 ; CHECK: %1 = atomicrmw xor i32* %ptr, i32 %value seq_cst | |
70 ; CHECK-NOT: @llvm.nacl.atomic | |
71 %1 = call i32 @llvm.nacl.atomic.32(i32 7, i32* %ptr, i32 %value, i32 0, i32 6) | |
72 ret i32 %1 | |
73 } | |
74 | |
75 ; CHECK: @test_val_compare_and_swap_i32 | |
76 define i32 @test_val_compare_and_swap_i32(i32* %ptr, i32 %oldval, i32 %newval) { | |
77 ; CHECK: %1 = cmpxchg i32* %ptr, i32 %oldval, i32 %newval seq_cst | |
78 ; CHECK-NOT: @llvm.nacl.atomic | |
79 %1 = call i32 @llvm.nacl.atomic.32(i32 9, i32* %ptr, i32 %newval, i32 %oldval, i32 6) | |
80 ret i32 %1 | |
81 } | |
82 | |
83 ; CHECK: @test_synchronize | |
84 define void @test_synchronize() { | |
85 ; CHECK: fence seq_cst | |
86 ; CHECK-NOT: @llvm.nacl.atomic | |
87 call i32 @llvm.nacl.atomic.32(i32 10, i32* null, i32 0, i32 0, i32 6) | |
88 ret void | |
89 } | |
90 | |
91 ; CHECK: @test_lock_test_and_set_i32 | |
92 define i32 @test_lock_test_and_set_i32(i32* %ptr, i32 %value) { | |
93 ; CHECK: %1 = atomicrmw xchg i32* %ptr, i32 %value seq_cst | |
94 ; CHECK-NOT: @llvm.nacl.atomic | |
95 %1 = call i32 @llvm.nacl.atomic.32(i32 8, i32* %ptr, i32 %value, i32 0, i32 6) | |
96 ret i32 %1 | |
97 } | |
98 | |
99 ; CHECK: @test_lock_release_i32 | |
100 define void @test_lock_release_i32(i32* %ptr) { | |
101 ; Note that the 'release' was changed to a 'seq_cst'. | |
102 ; CHECK: store atomic i32 0, i32* %ptr seq_cst, align 4 | |
103 ; CHECK-NOT: @llvm.nacl.atomic | |
104 call i32 @llvm.nacl.atomic.32(i32 2, i32* %ptr, i32 0, i32 0, i32 6) | |
105 ret void | |
106 } | |
107 | |
108 ; CHECK: @test_atomic_load_i8 | |
109 define zeroext i8 @test_atomic_load_i8(i8* %ptr) { | |
110 ; CHECK: %1 = load atomic i8* %ptr seq_cst, align 1 | |
111 ; CHECK-NOT: @llvm.nacl.atomic | |
112 %1 = call i8 @llvm.nacl.atomic.8(i32 1, i8* %ptr, i8 0, i8 0, i32 6) | |
113 ret i8 %1 | |
114 } | |
115 | |
116 ; CHECK: @test_atomic_store_i8 | |
117 define void @test_atomic_store_i8(i8* %ptr, i8 zeroext %value) { | |
118 ; CHECK: store atomic i8 %value, i8* %ptr seq_cst, align 1 | |
119 ; CHECK-NOT: @llvm.nacl.atomic | |
120 call i8 @llvm.nacl.atomic.8(i32 2, i8* %ptr, i8 %value, i8 0, i32 6) | |
121 ret void | |
122 } | |
123 | |
124 ; CHECK: @test_atomic_load_i16 | |
125 define zeroext i16 @test_atomic_load_i16(i16* %ptr) { | |
126 ; CHECK: %1 = load atomic i16* %ptr seq_cst, align 2 | |
127 ; CHECK-NOT: @llvm.nacl.atomic | |
128 %1 = call i16 @llvm.nacl.atomic.16(i32 1, i16* %ptr, i16 0, i16 0, i32 6) | |
129 ret i16 %1 | |
130 } | |
131 | |
132 ; CHECK: @test_atomic_store_i16 | |
133 define void @test_atomic_store_i16(i16* %ptr, i16 zeroext %value) { | |
134 ; CHECK: store atomic i16 %value, i16* %ptr seq_cst, align 2 | |
135 ; CHECK-NOT: @llvm.nacl.atomic | |
136 call i16 @llvm.nacl.atomic.16(i32 2, i16* %ptr, i16 %value, i16 0, i32 6) | |
137 ret void | |
138 } | |
139 | |
140 ; CHECK: @test_atomic_load_i32 | |
141 define i32 @test_atomic_load_i32(i32* %ptr) { | |
142 ; CHECK: %1 = load atomic i32* %ptr seq_cst, align 4 | |
143 ; CHECK-NOT: @llvm.nacl.atomic | |
144 %1 = call i32 @llvm.nacl.atomic.32(i32 1, i32* %ptr, i32 0, i32 0, i32 6) | |
145 ret i32 %1 | |
146 } | |
147 | |
148 ; CHECK: @test_atomic_store_i32 | |
149 define void @test_atomic_store_i32(i32* %ptr, i32 %value) { | |
150 ; CHECK: store atomic i32 %value, i32* %ptr seq_cst, align 4 | |
151 ; CHECK-NOT: @llvm.nacl.atomic | |
152 call i32 @llvm.nacl.atomic.32(i32 2, i32* %ptr, i32 %value, i32 0, i32 6) | |
153 ret void | |
154 } | |
155 | |
156 ; CHECK: @test_atomic_load_i64 | |
157 define i64 @test_atomic_load_i64(i64* %ptr) { | |
158 ; CHECK: %1 = load atomic i64* %ptr seq_cst, align 8 | |
159 ; CHECK-NOT: @llvm.nacl.atomic | |
160 %1 = call i64 @llvm.nacl.atomic.64(i32 1, i64* %ptr, i64 0, i64 0, i32 6) | |
161 ret i64 %1 | |
162 } | |
163 | |
164 ; CHECK: @test_atomic_store_i64 | |
165 define void @test_atomic_store_i64(i64* %ptr, i64 %value) { | |
166 ; CHECK: store atomic i64 %value, i64* %ptr seq_cst, align 8 | |
167 ; CHECK-NOT: @llvm.nacl.atomic | |
168 call i64 @llvm.nacl.atomic.64(i32 2, i64* %ptr, i64 %value, i64 0, i32 6) | |
169 ret void | |
170 } | |
OLD | NEW |