1 // RUN: %clang_cc1 -std=c++1z -emit-llvm -triple x86_64-linux-gnu -o - %s | FileCheck %s
2
3 struct A {
4 A(int);
5 A(A&&);
6 A(const A&);
7 ~A();
8
9 operator bool();
10
11 int arr[10];
12 };
13
14 A f();
15 void h();
16
17 // CHECK-LABEL: define {{.*}} @_Z1gv(
g()18 void g() {
19 // CHECK: %[[A:.*]] = alloca
20 // CHECK-NOT: alloca
21 // CHECK-NOT: call
22 // CHECK: call {{.*}} @_Z1fv({{.*}}* sret({{.*}}) align 4 %[[A]])
23 A a = A( A{ f() } );
24 // CHECK-NOT: call
25
26 // CHECK: call void @_Z1hv(
27 h();
28 // CHECK-NOT: call
29
30 // CHECK: call void @_ZN1AD1Ev({{.*}}* {{[^,]*}} %[[A]])
31 // CHECK-NOT: call
32 // CHECK-LABEL: }
33 }
34
35 void f(A);
36
37 // CHECK-LABEL: define {{.*}} @_Z1hv(
h()38 void h() {
39 // CHECK: %[[A:.*]] = alloca
40 // CHECK-NOT: alloca
41 // CHECK-NOT: call
42
43 // CHECK: call {{.*}} @_Z1fv({{.*}}* sret({{.*}}) align 4 %[[A]])
44 // CHECK-NOT: call
45 // CHECK: call {{.*}} @_Z1f1A({{.*}}* %[[A]])
46 f(f());
47 // CHECK-NOT: call
48 // CHECK: call void @_ZN1AD1Ev({{.*}}* {{[^,]*}} %[[A]])
49
50 // CHECK: call void @_Z1hv(
51 h();
52
53 // CHECK-NOT: call
54 // CHECK-LABEL: }
55 }
56
57 // We still pass classes with trivial copy/move constructors and destructors in
58 // registers, even if the copy is formally omitted.
59 struct B {
60 B(int);
61 int n;
62 };
63
64 B fB();
65 void fB(B);
66
67 // CHECK-LABEL: define {{.*}} @_Z1iv(
i()68 void i() {
69 // CHECK: %[[B:.*]] = alloca
70 // CHECK-NOT: alloca
71 // CHECK-NOT: call
72
73 // CHECK: %[[B_N:.*]] = call i32 @_Z2fBv()
74 // CHECK-NOT: call
75 // CHECK: store i32 %[[B_N]],
76 // CHECK-NOT: call
77 // CHECK: %[[B_N:.*]] = load i32
78 // CHECK-NOT: call
79 // CHECK: call void @_Z2fB1B(i32 %[[B_N]])
80 fB(fB());
81
82 // CHECK-LABEL: }
83 }
84
85 // CHECK-LABEL: define {{.*}} @_Z1jv(
j()86 void j() {
87 // CHECK: alloca %{{.*}}*
88 // CHECK: %[[OUTERTEMP:.*]] = alloca %{{.*}}
89 // CHECK: %[[INNERTEMP:.*]] = alloca %{{.*}}
90 // CHECK: call void @_ZN1AC1Ei(%{{.*}} %[[INNERTEMP]], i32 1)
91 // CHECK: call zeroext i1 @_ZN1AcvbEv(%{{.*}} %[[INNERTEMP]])
92 // CHECK: br i1
93 //
94 // CHECK: call void @_ZN1AC1EOS_(%{{.*}} %[[OUTERTEMP]], %{{.*}} %[[INNERTEMP]])
95 // CHECK: br label
96 //
97 // CHECK: call void @_ZN1AC1Ei(%{{.*}} %[[OUTERTEMP]], i32 2)
98 // CHECK: br label
99 //
100 // CHECK: call void @_ZN1AD1Ev(%{{.*}} %[[INNERTEMP]])
101 A &&a = A(1) ?: A(2);
102
103 // CHECK: call void @_Z1iv()
104 i();
105
106 // CHECK: call void @_ZN1AD1Ev(%{{.*}} %[[OUTERTEMP]])
107 }
108