The AND instruction leaves the V flag unmodified, so it falls victim to the same
[oota-llvm.git] / test / CodeGen / Mips / o32_cc_vararg.ll
1 ; RUN: llc -march=mipsel -mcpu=mips2 -pre-RA-sched=source < %s | FileCheck %s
2 ; RUN: llc -march=mipsel -mcpu=mips2 -pre-RA-sched=source < %s -regalloc=basic | FileCheck %s
3
4
5 ; FIXME: Temporarily disabled until buildpair patch is committed.
6 ; REQUIRES: disabled
7
8 ; All test functions do the same thing - they return the first variable
9 ; argument.
10
11 ; All CHECK's do the same thing - they check whether variable arguments from
12 ; registers are placed on correct stack locations, and whether the first
13 ; variable argument is returned from the correct stack location.
14
15
16 declare void @llvm.va_start(i8*) nounwind
17 declare void @llvm.va_end(i8*) nounwind
18
19 ; return int
20 define i32 @va1(i32 %a, ...) nounwind {
21 entry:
22   %a.addr = alloca i32, align 4
23   %ap = alloca i8*, align 4
24   %b = alloca i32, align 4
25   store i32 %a, i32* %a.addr, align 4
26   %ap1 = bitcast i8** %ap to i8*
27   call void @llvm.va_start(i8* %ap1)
28   %0 = va_arg i8** %ap, i32
29   store i32 %0, i32* %b, align 4
30   %ap2 = bitcast i8** %ap to i8*
31   call void @llvm.va_end(i8* %ap2)
32   %tmp = load i32* %b, align 4
33   ret i32 %tmp
34
35 ; CHECK: va1:
36 ; CHECK: addiu   $sp, $sp, -32
37 ; CHECK: sw      $7, 44($sp)
38 ; CHECK: sw      $6, 40($sp)
39 ; CHECK: sw      $5, 36($sp)
40 ; CHECK: lw      $2, 36($sp)
41 }
42
43 ; check whether the variable double argument will be accessed from the 8-byte
44 ; aligned location (i.e. whether the address is computed by adding 7 and
45 ; clearing lower 3 bits)
46 define double @va2(i32 %a, ...) nounwind {
47 entry:
48   %a.addr = alloca i32, align 4
49   %ap = alloca i8*, align 4
50   %b = alloca double, align 8
51   store i32 %a, i32* %a.addr, align 4
52   %ap1 = bitcast i8** %ap to i8*
53   call void @llvm.va_start(i8* %ap1)
54   %0 = va_arg i8** %ap, double
55   store double %0, double* %b, align 8
56   %ap2 = bitcast i8** %ap to i8*
57   call void @llvm.va_end(i8* %ap2)
58   %tmp = load double* %b, align 8
59   ret double %tmp
60
61 ; CHECK: va2:
62 ; CHECK: addiu   $sp, $sp, -40
63 ; CHECK: sw      $7, 52($sp)
64 ; CHECK: sw      $6, 48($sp)
65 ; CHECK: sw      $5, 44($sp)
66 ; CHECK: addiu   $[[R0:[0-9]+]], $sp, 44
67 ; CHECK: addiu   $[[R1:[0-9]+]], $[[R0]], 7
68 ; CHECK: addiu   $[[R2:[0-9]+]], $zero, -8
69 ; CHECK: and     $[[R3:[0-9]+]], $[[R1]], $[[R2]]
70 ; CHECK: ldc1    $f0, 0($[[R3]])
71 }
72
73 ; int
74 define i32 @va3(double %a, ...) nounwind {
75 entry:
76   %a.addr = alloca double, align 8
77   %ap = alloca i8*, align 4
78   %b = alloca i32, align 4
79   store double %a, double* %a.addr, align 8
80   %ap1 = bitcast i8** %ap to i8*
81   call void @llvm.va_start(i8* %ap1)
82   %0 = va_arg i8** %ap, i32
83   store i32 %0, i32* %b, align 4
84   %ap2 = bitcast i8** %ap to i8*
85   call void @llvm.va_end(i8* %ap2)
86   %tmp = load i32* %b, align 4
87   ret i32 %tmp
88
89 ; CHECK: va3:
90 ; CHECK: addiu   $sp, $sp, -40
91 ; CHECK: sw      $7, 52($sp)
92 ; CHECK: sw      $6, 48($sp)
93 ; CHECK: lw      $2, 48($sp)
94 }
95
96 ; double
97 define double @va4(double %a, ...) nounwind {
98 entry:
99   %a.addr = alloca double, align 8
100   %ap = alloca i8*, align 4
101   %b = alloca double, align 8
102   store double %a, double* %a.addr, align 8
103   %ap1 = bitcast i8** %ap to i8*
104   call void @llvm.va_start(i8* %ap1)
105   %0 = va_arg i8** %ap, double
106   store double %0, double* %b, align 8
107   %ap2 = bitcast i8** %ap to i8*
108   call void @llvm.va_end(i8* %ap2)
109   %tmp = load double* %b, align 8
110   ret double %tmp
111
112 ; CHECK: va4:
113 ; CHECK: addiu   $sp, $sp, -48
114 ; CHECK: sw      $7, 60($sp)
115 ; CHECK: sw      $6, 56($sp)
116 ; CHECK: addiu   $[[R0:[0-9]+]], $sp, 56
117 ; CHECK: addiu   $[[R1:[0-9]+]], $[[R0]], 7
118 ; CHECK: addiu   $[[R2:[0-9]+]], $zero, -8
119 ; CHECK: and     $[[R3:[0-9]+]], $[[R1]], $[[R2]]
120 ; CHECK: ldc1    $f0, 0($[[R3]])
121 }
122
123 ; int
124 define i32 @va5(i32 %a, i32 %b, i32 %c, ...) nounwind {
125 entry:
126   %a.addr = alloca i32, align 4
127   %b.addr = alloca i32, align 4
128   %c.addr = alloca i32, align 4
129   %ap = alloca i8*, align 4
130   %d = alloca i32, align 4
131   store i32 %a, i32* %a.addr, align 4
132   store i32 %b, i32* %b.addr, align 4
133   store i32 %c, i32* %c.addr, align 4
134   %ap1 = bitcast i8** %ap to i8*
135   call void @llvm.va_start(i8* %ap1)
136   %0 = va_arg i8** %ap, i32
137   store i32 %0, i32* %d, align 4
138   %ap2 = bitcast i8** %ap to i8*
139   call void @llvm.va_end(i8* %ap2)
140   %tmp = load i32* %d, align 4
141   ret i32 %tmp
142
143 ; CHECK: va5:
144 ; CHECK: addiu   $sp, $sp, -40
145 ; CHECK: sw      $7, 52($sp)
146 ; CHECK: lw      $2, 52($sp)
147 }
148
149 ; double
150 define double @va6(i32 %a, i32 %b, i32 %c, ...) nounwind {
151 entry:
152   %a.addr = alloca i32, align 4
153   %b.addr = alloca i32, align 4
154   %c.addr = alloca i32, align 4
155   %ap = alloca i8*, align 4
156   %d = alloca double, align 8
157   store i32 %a, i32* %a.addr, align 4
158   store i32 %b, i32* %b.addr, align 4
159   store i32 %c, i32* %c.addr, align 4
160   %ap1 = bitcast i8** %ap to i8*
161   call void @llvm.va_start(i8* %ap1)
162   %0 = va_arg i8** %ap, double
163   store double %0, double* %d, align 8
164   %ap2 = bitcast i8** %ap to i8*
165   call void @llvm.va_end(i8* %ap2)
166   %tmp = load double* %d, align 8
167   ret double %tmp
168
169 ; CHECK: va6:
170 ; CHECK: addiu   $sp, $sp, -48
171 ; CHECK: sw      $7, 60($sp)
172 ; CHECK: addiu   $[[R0:[0-9]+]], $sp, 60
173 ; CHECK: addiu   $[[R1:[0-9]+]], $[[R0]], 7
174 ; CHECK: addiu   $[[R2:[0-9]+]], $zero, -8
175 ; CHECK: and     $[[R3:[0-9]+]], $[[R1]], $[[R2]]
176 ; CHECK: ldc1    $f0, 0($[[R3]])
177 }
178
179 ; int
180 define i32 @va7(i32 %a, double %b, ...) nounwind {
181 entry:
182   %a.addr = alloca i32, align 4
183   %b.addr = alloca double, align 8
184   %ap = alloca i8*, align 4
185   %c = alloca i32, align 4
186   store i32 %a, i32* %a.addr, align 4
187   store double %b, double* %b.addr, align 8
188   %ap1 = bitcast i8** %ap to i8*
189   call void @llvm.va_start(i8* %ap1)
190   %0 = va_arg i8** %ap, i32
191   store i32 %0, i32* %c, align 4
192   %ap2 = bitcast i8** %ap to i8*
193   call void @llvm.va_end(i8* %ap2)
194   %tmp = load i32* %c, align 4
195   ret i32 %tmp
196
197 ; CHECK: va7:
198 ; CHECK: addiu   $sp, $sp, -40
199 ; CHECK: lw      $2, 56($sp)
200 }
201
202 ; double
203 define double @va8(i32 %a, double %b, ...) nounwind {
204 entry:
205   %a.addr = alloca i32, align 4
206   %b.addr = alloca double, align 8
207   %ap = alloca i8*, align 4
208   %c = alloca double, align 8
209   store i32 %a, i32* %a.addr, align 4
210   store double %b, double* %b.addr, align 8
211   %ap1 = bitcast i8** %ap to i8*
212   call void @llvm.va_start(i8* %ap1)
213   %0 = va_arg i8** %ap, double
214   store double %0, double* %c, align 8
215   %ap2 = bitcast i8** %ap to i8*
216   call void @llvm.va_end(i8* %ap2)
217   %tmp = load double* %c, align 8
218   ret double %tmp
219
220 ; CHECK: va8:
221 ; CHECK: addiu   $sp, $sp, -48
222 ; CHECK: addiu   $[[R0:[0-9]+]], $sp, 64
223 ; CHECK: addiu   $[[R1:[0-9]+]], $[[R0]], 7
224 ; CHECK: addiu   $[[R2:[0-9]+]], $zero, -8
225 ; CHECK: and     $[[R3:[0-9]+]], $[[R1]], $[[R2]]
226 ; CHECK: ldc1    $f0, 0($[[R3]])
227 }
228
229 ; int
230 define i32 @va9(double %a, double %b, i32 %c, ...) nounwind {
231 entry:
232   %a.addr = alloca double, align 8
233   %b.addr = alloca double, align 8
234   %c.addr = alloca i32, align 4
235   %ap = alloca i8*, align 4
236   %d = alloca i32, align 4
237   store double %a, double* %a.addr, align 8
238   store double %b, double* %b.addr, align 8
239   store i32 %c, i32* %c.addr, align 4
240   %ap1 = bitcast i8** %ap to i8*
241   call void @llvm.va_start(i8* %ap1)
242   %0 = va_arg i8** %ap, i32
243   store i32 %0, i32* %d, align 4
244   %ap2 = bitcast i8** %ap to i8*
245   call void @llvm.va_end(i8* %ap2)
246   %tmp = load i32* %d, align 4
247   ret i32 %tmp
248
249 ; CHECK: va9:
250 ; CHECK: addiu   $sp, $sp, -56
251 ; CHECK: lw      $2, 76($sp)
252 }
253
254 ; double
255 define double @va10(double %a, double %b, i32 %c, ...) nounwind {
256 entry:
257   %a.addr = alloca double, align 8
258   %b.addr = alloca double, align 8
259   %c.addr = alloca i32, align 4
260   %ap = alloca i8*, align 4
261   %d = alloca double, align 8
262   store double %a, double* %a.addr, align 8
263   store double %b, double* %b.addr, align 8
264   store i32 %c, i32* %c.addr, align 4
265   %ap1 = bitcast i8** %ap to i8*
266   call void @llvm.va_start(i8* %ap1)
267   %0 = va_arg i8** %ap, double
268   store double %0, double* %d, align 8
269   %ap2 = bitcast i8** %ap to i8*
270   call void @llvm.va_end(i8* %ap2)
271   %tmp = load double* %d, align 8
272   ret double %tmp
273
274 ; CHECK: va10:
275 ; CHECK: addiu   $sp, $sp, -56
276 ; CHECK: addiu   $[[R0:[0-9]+]], $sp, 76
277 ; CHECK: addiu   $[[R1:[0-9]+]], $[[R0]], 7
278 ; CHECK: addiu   $[[R2:[0-9]+]], $zero, -8
279 ; CHECK: and     $[[R3:[0-9]+]], $[[R1]], $[[R2]]
280 ; CHECK: ldc1    $f0, 0($[[R3]])
281 }