1 // RUN: %clang_cc1 -O1 -triple wasm32-unknown-unknown -emit-llvm -o - %s \
2 // RUN:   | FileCheck %s
3 // RUN: %clang_cc1 -O1 -triple wasm64-unknown-unknown -emit-llvm -o - %s \
4 // RUN:   | FileCheck %s
5 
6 #define concat_(x, y) x##y
7 #define concat(x, y) concat_(x, y)
8 
9 #define test(T)                \
10   T forward(T x) { return x; } \
11   void use(T x);               \
12   T concat(def_, T)(void);     \
13   void concat(test_, T)(void) { use(concat(def_, T)()); }
14 
15 struct one_field {
16   double d;
17 };
18 test(one_field);
19 // CHECK: define double @_Z7forward9one_field(double returned %{{.*}})
20 //
21 // CHECK: define void @_Z14test_one_fieldv()
22 // CHECK: %[[call:.*]] = call double @_Z13def_one_fieldv()
23 // CHECK: call void @_Z3use9one_field(double %[[call]])
24 // CHECK: ret void
25 //
26 // CHECK: declare void @_Z3use9one_field(double)
27 // CHECK: declare double @_Z13def_one_fieldv()
28 
29 struct two_fields {
30   double d, e;
31 };
32 test(two_fields);
33 // CHECK: define void @_Z7forward10two_fields(%struct.two_fields* noalias nocapture sret(%struct.two_fields) align 8 %{{.*}}, %struct.two_fields* nocapture readonly byval(%struct.two_fields) align 8 %{{.*}})
34 //
35 // CHECK: define void @_Z15test_two_fieldsv()
36 // CHECK: %[[tmp:.*]] = alloca %struct.two_fields, align 8
37 // CHECK: call void @_Z14def_two_fieldsv(%struct.two_fields* nonnull sret(%struct.two_fields) align 8 %[[tmp]])
38 // CHECK: call void @_Z3use10two_fields(%struct.two_fields* nonnull byval(%struct.two_fields) align 8 %[[tmp]])
39 // CHECK: ret void
40 //
41 // CHECK: declare void @_Z3use10two_fields(%struct.two_fields* byval(%struct.two_fields) align 8)
42 // CHECK: declare void @_Z14def_two_fieldsv(%struct.two_fields* sret(%struct.two_fields) align 8)
43 
44 struct copy_ctor {
45   double d;
46   copy_ctor(copy_ctor const &);
47 };
48 test(copy_ctor);
49 // CHECK: define void @_Z7forward9copy_ctor(%struct.copy_ctor* noalias {{[^,]*}} sret(%struct.copy_ctor) align 8 %{{.*}}, %struct.copy_ctor* nonnull %{{.*}})
50 //
51 // CHECK: declare %struct.copy_ctor* @_ZN9copy_ctorC1ERKS_(%struct.copy_ctor* {{[^,]*}} returned {{[^,]*}}, %struct.copy_ctor* nonnull align 8 dereferenceable(8))
52 //
53 // CHECK: define void @_Z14test_copy_ctorv()
54 // CHECK: %[[tmp:.*]] = alloca %struct.copy_ctor, align 8
55 // CHECK: call void @_Z13def_copy_ctorv(%struct.copy_ctor* nonnull sret(%struct.copy_ctor) align 8 %[[tmp]])
56 // CHECK: call void @_Z3use9copy_ctor(%struct.copy_ctor* nonnull %[[tmp]])
57 // CHECK: ret void
58 //
59 // CHECK: declare void @_Z3use9copy_ctor(%struct.copy_ctor*)
60 // CHECK: declare void @_Z13def_copy_ctorv(%struct.copy_ctor* sret(%struct.copy_ctor) align 8)
61 
62 struct __attribute__((aligned(16))) aligned_copy_ctor {
63   double d, e;
64   aligned_copy_ctor(aligned_copy_ctor const &);
65 };
66 test(aligned_copy_ctor);
67 // CHECK: define void @_Z7forward17aligned_copy_ctor(%struct.aligned_copy_ctor* noalias {{[^,]*}} sret(%struct.aligned_copy_ctor) align 16 %{{.*}}, %struct.aligned_copy_ctor* nonnull %{{.*}})
68 //
69 // CHECK: declare %struct.aligned_copy_ctor* @_ZN17aligned_copy_ctorC1ERKS_(%struct.aligned_copy_ctor* {{[^,]*}} returned {{[^,]*}}, %struct.aligned_copy_ctor* nonnull align 16 dereferenceable(16))
70 //
71 // CHECK: define void @_Z22test_aligned_copy_ctorv()
72 // CHECK: %[[tmp:.*]] = alloca %struct.aligned_copy_ctor, align 16
73 // CHECK: call void @_Z21def_aligned_copy_ctorv(%struct.aligned_copy_ctor* nonnull sret(%struct.aligned_copy_ctor) align 16 %[[tmp]])
74 // CHECK: call void @_Z3use17aligned_copy_ctor(%struct.aligned_copy_ctor* nonnull %[[tmp]])
75 // CHECK: ret void
76 //
77 // CHECK: declare void @_Z3use17aligned_copy_ctor(%struct.aligned_copy_ctor*)
78 // CHECK: declare void @_Z21def_aligned_copy_ctorv(%struct.aligned_copy_ctor* sret(%struct.aligned_copy_ctor) align 16)
79 
80 struct empty {};
81 test(empty);
82 // CHECK: define void @_Z7forward5empty()
83 //
84 // CHECK: define void @_Z10test_emptyv()
85 // CHECK: call void @_Z9def_emptyv()
86 // CHECK: call void @_Z3use5empty()
87 // CHECK: ret void
88 //
89 // CHECK: declare void @_Z3use5empty()
90 // CHECK: declare void @_Z9def_emptyv()
91 
92 struct one_bitfield {
93   int d : 3;
94 };
95 test(one_bitfield);
96 // CHECK: define i32 @_Z7forward12one_bitfield(i32 returned %{{.*}})
97 //
98 // CHECK: define void @_Z17test_one_bitfieldv()
99 // CHECK: %[[call:.*]] = call i32 @_Z16def_one_bitfieldv()
100 // CHECK: call void @_Z3use12one_bitfield(i32 %[[call]])
101 // CHECK: ret void
102 //
103 // CHECK: declare void @_Z3use12one_bitfield(i32)
104 // CHECK: declare i32 @_Z16def_one_bitfieldv()
105