1 ; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --version 2
2 ; RUN: opt < %s -passes=instcombine -S | FileCheck %s
4 target datalayout = "E-p:64:64:64-p1:16:16:16-a0:0:8-f32:32:32-f64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:32:64-v64:64:64-v128:128:128"
6 ; Simple case, argument translatable without changing the value
7 declare void @test1a(ptr)
9 define void @test1(ptr %A) {
10 ; CHECK-LABEL: define void @test1
11 ; CHECK-SAME: (ptr [[A:%.*]]) {
12 ; CHECK-NEXT: call void @test1a(ptr [[A]])
13 ; CHECK-NEXT: ret void
15 call void @test1a( ptr %A )
20 ; Should not do because of change in address space of the parameter
21 define void @test1_as1_illegal(ptr addrspace(1) %A) {
22 ; CHECK-LABEL: define void @test1_as1_illegal
23 ; CHECK-SAME: (ptr addrspace(1) [[A:%.*]]) {
24 ; CHECK-NEXT: call void @test1a(ptr addrspace(1) [[A]])
25 ; CHECK-NEXT: ret void
27 call void @test1a(ptr addrspace(1) %A)
31 ; Test1, but the argument has a different sized address-space
32 declare void @test1a_as1(ptr addrspace(1))
34 ; This one is OK to perform
35 define void @test1_as1(ptr addrspace(1) %A) {
36 ; CHECK-LABEL: define void @test1_as1
37 ; CHECK-SAME: (ptr addrspace(1) [[A:%.*]]) {
38 ; CHECK-NEXT: call void @test1a_as1(ptr addrspace(1) [[A]])
39 ; CHECK-NEXT: ret void
41 call void @test1a_as1(ptr addrspace(1) %A )
45 ; More complex case, translate argument because of resolution. This is safe
46 ; because we have the body of the function
47 define void @test2a(i8 %A) {
48 ; CHECK-LABEL: define void @test2a
49 ; CHECK-SAME: (i8 [[A:%.*]]) {
50 ; CHECK-NEXT: ret void
55 define i32 @test2(i32 %A) {
56 ; CHECK-LABEL: define i32 @test2
57 ; CHECK-SAME: (i32 [[A:%.*]]) {
58 ; CHECK-NEXT: call void @test2a(i32 [[A]])
59 ; CHECK-NEXT: ret i32 [[A]]
61 call void @test2a( i32 %A )
66 ; Resolving this should insert a cast from sbyte to int, following the C
68 define void @test3a(i8, ...) {unreachable }
69 ; CHECK-LABEL: define void @test3a
70 ; CHECK-SAME: (i8 [[TMP0:%.*]], ...) {
71 ; CHECK-NEXT: unreachable
73 define void @test3(i8 %A, i8 %B) {
74 call void @test3a( i8 %A, i8 %B)
78 ; test conversion of return value...
80 ; CHECK-LABEL: define i8 @test4a() {
81 ; CHECK-NEXT: ret i8 0
87 ; CHECK-LABEL: define i32 @test4() {
88 ; CHECK-NEXT: [[X:%.*]] = call i32 @test4a()
89 ; CHECK-NEXT: ret i32 [[X]]
91 %X = call i32 @test4a( ) ; <i32> [#uses=1]
95 ; test conversion of return value... no value conversion occurs so we can do
96 ; this with just a prototype...
100 ; CHECK-LABEL: define i32 @test5() {
101 ; CHECK-NEXT: [[X:%.*]] = call i32 @test5a()
102 ; CHECK-NEXT: ret i32 [[X]]
104 %X = call i32 @test5a( ) ; <i32> [#uses=1]
108 ; test addition of new arguments...
109 declare i32 @test6a(i32)
111 define i32 @test6() {
112 ; CHECK-LABEL: define i32 @test6() {
113 ; CHECK-NEXT: [[X:%.*]] = call i32 @test6a(i32 0)
114 ; CHECK-NEXT: ret i32 [[X]]
116 %X = call i32 @test6a( )
120 ; test removal of arguments, only can happen with a function body
121 define void @test7a() {
122 ; CHECK-LABEL: define void @test7a() {
123 ; CHECK-NEXT: ret void
128 define void @test7() {
129 ; CHECK-LABEL: define void @test7() {
130 ; CHECK-NEXT: call void @test7a()
131 ; CHECK-NEXT: ret void
133 call void @test7a( i32 5 )
139 declare void @test8a()
141 define ptr @test8() personality ptr @__gxx_personality_v0 {
142 ; CHECK-LABEL: define ptr @test8() personality ptr @__gxx_personality_v0 {
143 ; CHECK-NEXT: invoke void @test8a()
144 ; CHECK-NEXT: to label [[INVOKE_CONT:%.*]] unwind label [[TRY_HANDLER:%.*]]
145 ; CHECK: invoke.cont:
146 ; CHECK-NEXT: unreachable
147 ; CHECK: try.handler:
148 ; CHECK-NEXT: [[EXN:%.*]] = landingpad { ptr, i32 }
149 ; CHECK-NEXT: cleanup
150 ; CHECK-NEXT: ret ptr null
152 ; Don't turn this into "unreachable": the callee and caller don't agree in
153 ; calling conv, but the implementation of test8a may actually end up using the
154 ; right calling conv.
155 invoke void @test8a()
156 to label %invoke.cont unwind label %try.handler
158 invoke.cont: ; preds = %entry
161 try.handler: ; preds = %entry
162 %exn = landingpad {ptr, i32}
167 declare i32 @__gxx_personality_v0(...)
170 ; Don't turn this into a direct call, because test9x is just a prototype and
171 ; doing so will make it varargs.
173 declare ptr @test9x(ptr, ptr, ...) noredzone
174 define ptr @test9(ptr %arg, ptr %tmp3) nounwind ssp noredzone {
175 ; CHECK-LABEL: define ptr @test9
176 ; CHECK-SAME: (ptr [[ARG:%.*]], ptr [[TMP3:%.*]]) #[[ATTR1:[0-9]+]] {
178 ; CHECK-NEXT: [[CALL:%.*]] = call ptr @test9x(ptr [[ARG]], ptr [[TMP3]]) #[[ATTR2:[0-9]+]]
179 ; CHECK-NEXT: ret ptr [[CALL]]
182 %call = call ptr @test9x(ptr %arg, ptr %tmp3) noredzone
187 ; Parameter that's a vector of pointers
188 declare void @test10a(<2 x ptr>)
190 define void @test10(<2 x ptr> %A) {
191 ; CHECK-LABEL: define void @test10
192 ; CHECK-SAME: (<2 x ptr> [[A:%.*]]) {
193 ; CHECK-NEXT: call void @test10a(<2 x ptr> [[A]])
194 ; CHECK-NEXT: ret void
196 call void @test10a(<2 x ptr> %A)
200 ; Don't transform because different address spaces
201 declare void @test10a_mixed_as(<2 x ptr addrspace(1)>)
203 define void @test10_mixed_as(<2 x ptr> %A) {
204 ; CHECK-LABEL: define void @test10_mixed_as
205 ; CHECK-SAME: (<2 x ptr> [[A:%.*]]) {
206 ; CHECK-NEXT: call void @test10a_mixed_as(<2 x ptr> [[A]])
207 ; CHECK-NEXT: ret void
209 call void @test10a_mixed_as(<2 x ptr> %A)
213 ; Return type that's a pointer
214 define ptr @test11a() {
215 ; CHECK-LABEL: define ptr @test11a() {
216 ; CHECK-NEXT: ret ptr null
218 ret ptr zeroinitializer
221 define ptr @test11() {
222 ; CHECK-LABEL: define ptr @test11() {
223 ; CHECK-NEXT: [[X:%.*]] = call ptr @test11a()
224 ; CHECK-NEXT: ret ptr [[X]]
226 %X = call ptr @test11a()
230 ; Return type that's a pointer with a different address space
231 define ptr addrspace(1) @test11a_mixed_as() {
232 ; CHECK-LABEL: define ptr addrspace(1) @test11a_mixed_as() {
233 ; CHECK-NEXT: ret ptr addrspace(1) null
235 ret ptr addrspace(1) zeroinitializer
238 define ptr @test11_mixed_as() {
239 ; CHECK-LABEL: define ptr @test11_mixed_as() {
240 ; CHECK-NEXT: [[X:%.*]] = call ptr @test11a_mixed_as()
241 ; CHECK-NEXT: ret ptr [[X]]
243 %X = call ptr @test11a_mixed_as()
247 ; Return type that's a vector of pointers
248 define <2 x ptr> @test12a() {
249 ; CHECK-LABEL: define <2 x ptr> @test12a() {
250 ; CHECK-NEXT: ret <2 x ptr> zeroinitializer
252 ret <2 x ptr> zeroinitializer
255 define <2 x ptr> @test12() {
256 ; CHECK-LABEL: define <2 x ptr> @test12() {
257 ; CHECK-NEXT: [[X:%.*]] = call <2 x ptr> @test12a()
258 ; CHECK-NEXT: ret <2 x ptr> [[X]]
260 %X = call <2 x ptr> @test12a()
264 define <2 x ptr addrspace(1)> @test12a_mixed_as() {
265 ; CHECK-LABEL: define <2 x ptr addrspace(1)> @test12a_mixed_as() {
266 ; CHECK-NEXT: ret <2 x ptr addrspace(1)> zeroinitializer
268 ret <2 x ptr addrspace(1)> zeroinitializer
271 define <2 x ptr> @test12_mixed_as() {
272 ; CHECK-LABEL: define <2 x ptr> @test12_mixed_as() {
273 ; CHECK-NEXT: [[X:%.*]] = call <2 x ptr> @test12a_mixed_as()
274 ; CHECK-NEXT: ret <2 x ptr> [[X]]
276 %X = call <2 x ptr> @test12a_mixed_as()
281 ; Mix parameter that's a vector of integers and pointers of the same size
282 declare void @test13a(<2 x i64>)
284 define void @test13(<2 x ptr> %A) {
285 ; CHECK-LABEL: define void @test13
286 ; CHECK-SAME: (<2 x ptr> [[A:%.*]]) {
287 ; CHECK-NEXT: call void @test13a(<2 x ptr> [[A]])
288 ; CHECK-NEXT: ret void
290 call void @test13a(<2 x ptr> %A)
294 ; Mix parameter that's a vector of integers and pointers of the same
295 ; size, but the other way around
296 declare void @test14a(<2 x ptr>)
298 define void @test14(<2 x i64> %A) {
299 ; CHECK-LABEL: define void @test14
300 ; CHECK-SAME: (<2 x i64> [[A:%.*]]) {
301 ; CHECK-NEXT: call void @test14a(<2 x i64> [[A]])
302 ; CHECK-NEXT: ret void
304 call void @test14a(<2 x i64> %A)
309 ; Return type that's a vector
310 define <2 x i16> @test15a() {
311 ; CHECK-LABEL: define <2 x i16> @test15a() {
312 ; CHECK-NEXT: ret <2 x i16> zeroinitializer
314 ret <2 x i16> zeroinitializer
317 define i32 @test15() {
318 ; CHECK-LABEL: define i32 @test15() {
319 ; CHECK-NEXT: [[X:%.*]] = call <2 x i16> @test15a()
320 ; CHECK-NEXT: [[TMP1:%.*]] = bitcast <2 x i16> [[X]] to i32
321 ; CHECK-NEXT: ret i32 [[TMP1]]
323 %X = call i32 @test15a( )
327 define i32 @test16a() {
328 ; CHECK-LABEL: define i32 @test16a() {
329 ; CHECK-NEXT: ret i32 0
334 define <2 x i16> @test16() {
335 ; CHECK-LABEL: define <2 x i16> @test16() {
336 ; CHECK-NEXT: [[X:%.*]] = call i32 @test16a()
337 ; CHECK-NEXT: [[TMP1:%.*]] = bitcast i32 [[X]] to <2 x i16>
338 ; CHECK-NEXT: ret <2 x i16> [[TMP1]]
340 %X = call <2 x i16> @test16a( )
344 declare i32 @pr28655(i32 returned %V)
346 define i32 @test17() {
347 ; CHECK-LABEL: define i32 @test17() {
349 ; CHECK-NEXT: [[C:%.*]] = call i32 @pr28655(i32 0)
350 ; CHECK-NEXT: ret i32 0
353 %C = call i32 @pr28655(i32 0)
357 define void @non_vararg(ptr, i32) {
358 ; CHECK-LABEL: define void @non_vararg
359 ; CHECK-SAME: (ptr [[TMP0:%.*]], i32 [[TMP1:%.*]]) {
360 ; CHECK-NEXT: ret void
365 define void @test_cast_to_vararg(ptr %this) {
366 ; CHECK-LABEL: define void @test_cast_to_vararg
367 ; CHECK-SAME: (ptr [[THIS:%.*]]) {
368 ; CHECK-NEXT: call void @non_vararg(ptr [[THIS]], i32 42)
369 ; CHECK-NEXT: ret void
371 call void (ptr, ...) @non_vararg(ptr %this, i32 42)