• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // RUN: %clang_cc1 -triple x86_64-unknown-unknown -emit-llvm -o - %s| FileCheck %s
2 #include <stdarg.h>
3 
4 // CHECK: define signext i8 @f0()
f0(void)5 char f0(void) {
6   return 0;
7 }
8 
9 // CHECK: define signext i16 @f1()
f1(void)10 short f1(void) {
11   return 0;
12 }
13 
14 // CHECK: define i32 @f2()
f2(void)15 int f2(void) {
16   return 0;
17 }
18 
19 // CHECK: define float @f3()
f3(void)20 float f3(void) {
21   return 0;
22 }
23 
24 // CHECK: define double @f4()
f4(void)25 double f4(void) {
26   return 0;
27 }
28 
29 // CHECK: define x86_fp80 @f5()
f5(void)30 long double f5(void) {
31   return 0;
32 }
33 
34 // CHECK: define void @f6(i8 signext %a0, i16 signext %a1, i32 %a2, i64 %a3, i8* %a4)
f6(char a0,short a1,int a2,long long a3,void * a4)35 void f6(char a0, short a1, int a2, long long a3, void *a4) {
36 }
37 
38 // CHECK: define void @f7(i32 %a0)
39 typedef enum { A, B, C } e7;
f7(e7 a0)40 void f7(e7 a0) {
41 }
42 
43 // Test merging/passing of upper eightbyte with X87 class.
44 //
45 // CHECK: define void @f8_1(%union.u8* sret %agg.result)
46 // CHECK: define void @f8_2(%union.u8* byval align 16 %a0)
47 union u8 {
48   long double a;
49   int b;
50 };
f8_1()51 union u8 f8_1() { while (1) {} }
f8_2(union u8 a0)52 void f8_2(union u8 a0) {}
53 
54 // CHECK: define i64 @f9()
f9(void)55 struct s9 { int a; int b; int : 0; } f9(void) { while (1) {} }
56 
57 // CHECK: define void @f10(i64 %a0.coerce)
58 struct s10 { int a; int b; int : 0; };
f10(struct s10 a0)59 void f10(struct s10 a0) {}
60 
61 // CHECK: define void @f11(%union.anon* sret %agg.result)
f11()62 union { long double a; float b; } f11() { while (1) {} }
63 
64 // CHECK: define i32 @f12_0()
65 // CHECK: define void @f12_1(i32 %a0.coerce)
66 struct s12 { int a __attribute__((aligned(16))); };
f12_0(void)67 struct s12 f12_0(void) { while (1) {} }
f12_1(struct s12 a0)68 void f12_1(struct s12 a0) {}
69 
70 // Check that sret parameter is accounted for when checking available integer
71 // registers.
72 // CHECK: define void @f13(%struct.s13_0* sret %agg.result, i32 %a, i32 %b, i32 %c, i32 %d, {{.*}}* byval align 8 %e, i32 %f)
73 
74 struct s13_0 { long long f0[3]; };
75 struct s13_1 { long long f0[2]; };
f13(int a,int b,int c,int d,struct s13_1 e,int f)76 struct s13_0 f13(int a, int b, int c, int d,
77                  struct s13_1 e, int f) { while (1) {} }
78 
79 // CHECK: define void @f14({{.*}}, i8 signext %X)
f14(int a,int b,int c,int d,int e,int f,char X)80 void f14(int a, int b, int c, int d, int e, int f, char X) {}
81 
82 // CHECK: define void @f15({{.*}}, i8* %X)
f15(int a,int b,int c,int d,int e,int f,void * X)83 void f15(int a, int b, int c, int d, int e, int f, void *X) {}
84 
85 // CHECK: define void @f16({{.*}}, float %X)
f16(float a,float b,float c,float d,float e,float f,float g,float h,float X)86 void f16(float a, float b, float c, float d, float e, float f, float g, float h,
87          float X) {}
88 
89 // CHECK: define void @f17({{.*}}, x86_fp80 %X)
f17(float a,float b,float c,float d,float e,float f,float g,float h,long double X)90 void f17(float a, float b, float c, float d, float e, float f, float g, float h,
91          long double X) {}
92 
93 // Check for valid coercion.  The struct should be passed/returned as i32, not
94 // as i64 for better code quality.
95 // rdar://8135035
96 // CHECK: define void @f18(i32 %a, i32 %f18_arg1.coerce)
97 struct f18_s0 { int f0; };
f18(int a,struct f18_s0 f18_arg1)98 void f18(int a, struct f18_s0 f18_arg1) { while (1) {} }
99 
100 // Check byval alignment.
101 
102 // CHECK: define void @f19(%struct.s19* byval align 16 %x)
103 struct s19 {
104   long double a;
105 };
f19(struct s19 x)106 void f19(struct s19 x) {}
107 
108 // CHECK: define void @f20(%struct.s20* byval align 32 %x)
109 struct __attribute__((aligned(32))) s20 {
110   int x;
111   int y;
112 };
f20(struct s20 x)113 void f20(struct s20 x) {}
114 
115 struct StringRef {
116   long x;
117   const char *Ptr;
118 };
119 
120 // rdar://7375902
121 // CHECK: define i8* @f21(i64 %S.coerce0, i8* %S.coerce1)
f21(struct StringRef S)122 const char *f21(struct StringRef S) { return S.x+S.Ptr; }
123 
124 // PR7567
125 typedef __attribute__ ((aligned(16))) struct f22s { unsigned long long x[2]; } L;
f22(L x,L y)126 void f22(L x, L y) { }
127 // CHECK: @f22
128 // CHECK: %x = alloca{{.*}}, align 16
129 // CHECK: %y = alloca{{.*}}, align 16
130 
131 
132 
133 // PR7714
134 struct f23S {
135   short f0;
136   unsigned f1;
137   int f2;
138 };
139 
140 
f23(int A,struct f23S B)141 void f23(int A, struct f23S B) {
142   // CHECK: define void @f23(i32 %A, i64 %B.coerce0, i32 %B.coerce1)
143 }
144 
145 struct f24s { long a; int b; };
146 
f24(struct f23S * X,struct f24s * P2)147 struct f23S f24(struct f23S *X, struct f24s *P2) {
148   return *X;
149 
150   // CHECK: define { i64, i32 } @f24(%struct.f23S* %X, %struct.f24s* %P2)
151 }
152 
153 // rdar://8248065
154 typedef float v4f32 __attribute__((__vector_size__(16)));
f25(v4f32 X)155 v4f32 f25(v4f32 X) {
156   // CHECK: define <4 x float> @f25(<4 x float> %X)
157   // CHECK-NOT: alloca
158   // CHECK: alloca <4 x float>
159   // CHECK-NOT: alloca
160   // CHECK: store <4 x float> %X, <4 x float>*
161   // CHECK-NOT: store
162   // CHECK: ret <4 x float>
163   return X+X;
164 }
165 
166 struct foo26 {
167   int *X;
168   float *Y;
169 };
170 
f26(struct foo26 * P)171 struct foo26 f26(struct foo26 *P) {
172   // CHECK: define { i32*, float* } @f26(%struct.foo26* %P)
173   return *P;
174 }
175 
176 
177 struct v4f32wrapper {
178   v4f32 v;
179 };
180 
f27(struct v4f32wrapper X)181 struct v4f32wrapper f27(struct v4f32wrapper X) {
182   // CHECK: define <4 x float> @f27(<4 x float> %X.coerce)
183   return X;
184 }
185 
186 // rdar://5711709
187 struct f28c {
188   double x;
189   int y;
190 };
f28(struct f28c C)191 void f28(struct f28c C) {
192   // CHECK: define void @f28(double %C.coerce0, i32 %C.coerce1)
193 }
194 
195 struct f29a {
196   struct c {
197     double x;
198     int y;
199   } x[1];
200 };
201 
f29a(struct f29a A)202 void f29a(struct f29a A) {
203   // CHECK: define void @f29a(double %A.coerce0, i32 %A.coerce1)
204 }
205 
206 // rdar://8249586
207 struct S0 { char f0[8]; char f2; char f3; char f4; };
f30(struct S0 p_4)208 void f30(struct S0 p_4) {
209   // CHECK: define void @f30(i64 %p_4.coerce0, i24 %p_4.coerce1)
210 }
211 
212 // Pass the third element as a float when followed by tail padding.
213 // rdar://8251384
214 struct f31foo { float a, b, c; };
f31(struct f31foo X)215 float f31(struct f31foo X) {
216   // CHECK: define float @f31(<2 x float> %X.coerce0, float %X.coerce1)
217   return X.c;
218 }
219 
f32(_Complex float A,_Complex float B)220 _Complex float f32(_Complex float A, _Complex float B) {
221   // rdar://6379669
222   // CHECK: define <2 x float> @f32(<2 x float> %A.coerce, <2 x float> %B.coerce)
223   return A+B;
224 }
225 
226 
227 // rdar://8357396
228 struct f33s { long x; float c,d; };
229 
f33(va_list X)230 void f33(va_list X) {
231   va_arg(X, struct f33s);
232 }
233 
234 typedef unsigned long long v1i64 __attribute__((__vector_size__(8)));
235 
236 // rdar://8359248
237 // CHECK: define i64 @f34(i64 %arg.coerce)
f34(v1i64 arg)238 v1i64 f34(v1i64 arg) { return arg; }
239 
240 
241 // rdar://8358475
242 // CHECK: define i64 @f35(i64 %arg.coerce)
243 typedef unsigned long v1i64_2 __attribute__((__vector_size__(8)));
f35(v1i64_2 arg)244 v1i64_2 f35(v1i64_2 arg) { return arg+arg; }
245 
246 // rdar://9122143
247 // CHECK: declare void @func(%struct._str* byval align 16)
248 typedef struct _str {
249   union {
250     long double a;
251     long c;
252   };
253 } str;
254 
255 void func(str s);
256 str ss;
f9122143()257 void f9122143()
258 {
259   func(ss);
260 }
261 
262 // CHECK: define double @f36(double %arg.coerce)
263 typedef unsigned v2i32 __attribute((__vector_size__(8)));
f36(v2i32 arg)264 v2i32 f36(v2i32 arg) { return arg; }
265 
266 // CHECK: declare void @f38(<8 x float>)
267 // CHECK: declare void @f37(<8 x float>)
268 typedef float __m256 __attribute__ ((__vector_size__ (32)));
269 typedef struct {
270   __m256 m;
271 } s256;
272 
273 s256 x38;
274 __m256 x37;
275 
276 void f38(s256 x);
277 void f37(__m256 x);
f39()278 void f39() { f38(x38); f37(x37); }
279 
280 // The two next tests make sure that the struct below is passed
281 // in the same way regardless of avx being used
282 
283 // CHECK: declare void @func40(%struct.t128* byval align 16)
284 typedef float __m128 __attribute__ ((__vector_size__ (16)));
285 typedef struct t128 {
286   __m128 m;
287   __m128 n;
288 } two128;
289 
290 extern void func40(two128 s);
func41(two128 s)291 void func41(two128 s) {
292   func40(s);
293 }
294 
295 // CHECK: declare void @func42(%struct.t128_2* byval align 16)
296 typedef struct xxx {
297   __m128 array[2];
298 } Atwo128;
299 typedef struct t128_2 {
300   Atwo128 x;
301 } SA;
302 
303 extern void func42(SA s);
func43(SA s)304 void func43(SA s) {
305   func42(s);
306 }
307