blob: c4be5b78c2e4de75c347aed34f1e1d3bd1ec98aa [file] [log] [blame]
Douglas Gregor7c7a7932010-07-15 18:58:16 +00001// RUN: %clang_cc1 -emit-llvm -triple x86_64-apple-darwin10 -o - %s | FileCheck %s
2
3// PR6024
4extern int i;
5
Stephen Hines176edba2014-12-01 14:53:08 -08006// CHECK: define dereferenceable({{[0-9]+}}) i32* @_Z16lvalue_noop_castv() [[NUW:#[0-9]+]]
Douglas Gregor7c7a7932010-07-15 18:58:16 +00007const int &lvalue_noop_cast() {
8 if (i == 0)
9 // CHECK: store i32 17, i32*
10 return (const int&)17;
11 else if (i == 1)
12 // CHECK: store i32 17, i32*
13 return static_cast<const int&>(17);
14 // CHECK: store i32 17, i32*
15 return 17;
16}
17
Stephen Hines176edba2014-12-01 14:53:08 -080018// CHECK-LABEL: define dereferenceable({{[0-9]+}}) i16* @_Z20lvalue_integral_castv()
Douglas Gregor7c7a7932010-07-15 18:58:16 +000019const short &lvalue_integral_cast() {
20 if (i == 0)
21 // CHECK: store i16 17, i16*
22 return (const short&)17;
23 else if (i == 1)
24 // CHECK: store i16 17, i16*
25 return static_cast<const short&>(17);
26 // CHECK: store i16 17, i16*
27 return 17;
28}
29
Stephen Hines176edba2014-12-01 14:53:08 -080030// CHECK-LABEL: define dereferenceable({{[0-9]+}}) i16* @_Z29lvalue_floating_integral_castv()
Douglas Gregor7c7a7932010-07-15 18:58:16 +000031const short &lvalue_floating_integral_cast() {
32 if (i == 0)
33 // CHECK: store i16 17, i16*
34 return (const short&)17.5;
35 else if (i == 1)
36 // CHECK: store i16 17, i16*
37 return static_cast<const short&>(17.5);
38 // CHECK: store i16 17, i16*
39 return 17.5;
40}
41
Stephen Hines176edba2014-12-01 14:53:08 -080042// CHECK-LABEL: define dereferenceable({{[0-9]+}}) float* @_Z29lvalue_integral_floating_castv()
Douglas Gregor7c7a7932010-07-15 18:58:16 +000043const float &lvalue_integral_floating_cast() {
44 if (i == 0)
Benjamin Kramer2b02f7a2010-07-19 11:48:10 +000045 // CHECK: store float 1.700000e+{{0*}}1, float*
Douglas Gregor7c7a7932010-07-15 18:58:16 +000046 return (const float&)17;
47 else if (i == 1)
Benjamin Kramer2b02f7a2010-07-19 11:48:10 +000048 // CHECK: store float 1.700000e+{{0*}}1, float*
Douglas Gregor7c7a7932010-07-15 18:58:16 +000049 return static_cast<const float&>(17);
Benjamin Kramer2b02f7a2010-07-19 11:48:10 +000050 // CHECK: store float 1.700000e+{{0*}}1, float*
Douglas Gregor7c7a7932010-07-15 18:58:16 +000051 return 17;
52}
53
Stephen Hines176edba2014-12-01 14:53:08 -080054// CHECK-LABEL: define dereferenceable({{[0-9]+}}) float* @_Z20lvalue_floating_castv()
Douglas Gregor7c7a7932010-07-15 18:58:16 +000055const float &lvalue_floating_cast() {
56 if (i == 0)
Benjamin Kramer2b02f7a2010-07-19 11:48:10 +000057 // CHECK: store float 1.700000e+{{0*}}1, float*
Douglas Gregor7c7a7932010-07-15 18:58:16 +000058 return (const float&)17.0;
59 else if (i == 1)
Benjamin Kramer2b02f7a2010-07-19 11:48:10 +000060 // CHECK: store float 1.700000e+{{0*}}1, float*
Douglas Gregor7c7a7932010-07-15 18:58:16 +000061 return static_cast<const float&>(17.0);
Benjamin Kramer2b02f7a2010-07-19 11:48:10 +000062 // CHECK: store float 1.700000e+{{0*}}1, float*
Douglas Gregor7c7a7932010-07-15 18:58:16 +000063 return 17.0;
64}
65
66int get_int();
67
Stephen Hines176edba2014-12-01 14:53:08 -080068// CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z24lvalue_integer_bool_castv()
Douglas Gregor7c7a7932010-07-15 18:58:16 +000069const bool &lvalue_integer_bool_cast() {
70 if (i == 0)
71 // CHECK: call i32 @_Z7get_intv()
72 // CHECK: store i8
73 return (const bool&)get_int();
74 else if (i == 1)
75 // CHECK: call i32 @_Z7get_intv()
76 // CHECK: store i8
77 return static_cast<const bool&>(get_int());
78 // CHECK: call i32 @_Z7get_intv()
79 // CHECK: store i8
80 return get_int();
81}
82
83float get_float();
84
Stephen Hines176edba2014-12-01 14:53:08 -080085// CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z25lvalue_floating_bool_castv()
Douglas Gregor7c7a7932010-07-15 18:58:16 +000086const bool &lvalue_floating_bool_cast() {
87 if (i == 0)
88 // CHECK: call float @_Z9get_floatv()
89 // CHECK: fcmp une float
90 // CHECK: store i8
91 return (const bool&)get_float();
92 else if (i == 1)
93 // CHECK: call float @_Z9get_floatv()
94 // CHECK: fcmp une float
95 // CHECK: store i8
96 return static_cast<const bool&>(get_float());
97 // CHECK: call float @_Z9get_floatv()
98 // CHECK: fcmp une float
99 // CHECK: store i8
100 return get_float();
101}
102
103struct X { };
104typedef int X::*pm;
105typedef int (X::*pmf)(int);
106
107pm get_pointer_to_member_data();
108pmf get_pointer_to_member_function();
109
Stephen Hines176edba2014-12-01 14:53:08 -0800110// CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z26lvalue_ptrmem_to_bool_castv()
Douglas Gregor7c7a7932010-07-15 18:58:16 +0000111const bool &lvalue_ptrmem_to_bool_cast() {
112 if (i == 0)
113 // CHECK: call i64 @_Z26get_pointer_to_member_datav()
114 // CHECK: store i8
115 // CHECK: store i8*
116 return (const bool&)get_pointer_to_member_data();
117 else if (i == 1)
118 // CHECK: call i64 @_Z26get_pointer_to_member_datav()
119 // CHECK: store i8
120 // CHECK: store i8*
121 return static_cast<const bool&>(get_pointer_to_member_data());
122 // CHECK: call i64 @_Z26get_pointer_to_member_datav()
123 // CHECK: store i8
124 // CHECK: store i8*
125 return get_pointer_to_member_data();
126}
127
Stephen Hines176edba2014-12-01 14:53:08 -0800128// CHECK-LABEL: define dereferenceable({{[0-9]+}}) i8* @_Z27lvalue_ptrmem_to_bool_cast2v
Douglas Gregor7c7a7932010-07-15 18:58:16 +0000129const bool &lvalue_ptrmem_to_bool_cast2() {
130 if (i == 0)
131 // CHECK: {{call.*_Z30get_pointer_to_member_functionv}}
132 // CHECK: store i8
133 // CHECK: store i8*
134 return (const bool&)get_pointer_to_member_function();
135 else if (i == 1)
136 // CHECK: {{call.*_Z30get_pointer_to_member_functionv}}
137 // CHECK: store i8
138 // CHECK: store i8*
139 return static_cast<const bool&>(get_pointer_to_member_function());
140 // CHECK: {{call.*_Z30get_pointer_to_member_functionv}}
141 // CHECK: store i8
142 // CHECK: store i8*
143 return get_pointer_to_member_function();
144}
145
146_Complex double get_complex_double();
147
148// CHECK: {{define.*_Z2f1v}}
149const _Complex float &f1() {
150 if (i == 0)
151 // CHECK: {{call.*_Z18get_complex_doublev}}
152 // CHECK: fptrunc
153 // CHECK: fptrunc
154 // CHECK: store float
155 // CHECK: store float
156 return (const _Complex float&)get_complex_double();
157 else if (i == 1)
158 // CHECK: {{call.*_Z18get_complex_doublev}}
159 // CHECK: fptrunc
160 // CHECK: fptrunc
161 // CHECK: store float
162 // CHECK: store float
163 return static_cast<const _Complex float&>(get_complex_double());
164 // CHECK: {{call.*_Z18get_complex_doublev}}
165 // CHECK: fptrunc
166 // CHECK: fptrunc
167 // CHECK: store float
168 // CHECK: store float
169 return get_complex_double();
170}
Douglas Gregor3f86ce12011-08-09 00:37:14 +0000171
Stephen Lin93ab6bf2013-08-15 06:47:53 +0000172// CHECK-LABEL: define i32 @_Z7pr10592RKi(i32*
Douglas Gregor3f86ce12011-08-09 00:37:14 +0000173unsigned pr10592(const int &v) {
174 // CHECK: [[VADDR:%[a-zA-Z0-9.]+]] = alloca i32*
175 // CHECK-NEXT: [[REFTMP:%[a-zA-Z0-9.]+]] = alloca i32
176 // CHECK-NEXT: store i32* [[V:%[a-zA-Z0-9.]+]], i32** [[VADDR]]
177 // CHECK-NEXT: [[VADDR_1:%[a-zA-Z0-9.]+]] = load i32** [[VADDR]]
178 // CHECK-NEXT: [[VVAL:%[a-zA-Z0-9.]+]] = load i32* [[VADDR_1]]
179 // CHECK-NEXT: store i32 [[VVAL]], i32* [[REFTMP]]
180 // CHECK-NEXT: [[VVAL_I:%[a-zA-Z0-9.]+]] = load i32* [[REFTMP]]
181 // CHECK-NEXT: ret i32 [[VVAL_I]]
182 return static_cast<const unsigned &>(v);
183}
Eli Friedmanec24b0e2011-08-14 04:50:34 +0000184
185namespace PR10650 {
186 struct Helper {
187 unsigned long long id();
188 };
189 unsigned long long test(Helper *obj) {
190 return static_cast<const unsigned long long&>(obj->id());
191 }
Stephen Lin93ab6bf2013-08-15 06:47:53 +0000192 // CHECK-LABEL: define i64 @_ZN7PR106504testEPNS_6HelperE
Eli Friedmanec24b0e2011-08-14 04:50:34 +0000193 // CHECK: store i64
194}
Bill Wendlingf7a9da02013-02-20 07:22:19 +0000195
Bill Wendlingbe9e8bf2013-02-28 22:49:57 +0000196// CHECK: attributes [[NUW]] = { nounwind{{.*}} }