1// RUN: %check_clang_tidy %s modernize-use-auto %t -- \
2// RUN: -config="{CheckOptions: {modernize-use-auto.MinTypeNameLength: '0'}}" \
3// RUN: -- -I %S/Inputs/use-auto -frtti
4
5struct A {
6 virtual ~A() {}
7};
8
9struct B : public A {};
10
11struct C {};
12
13void f_static_cast() {
14 long l = 1;
15 int i1 = static_cast<int>(l);
16 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
17 // CHECK-FIXES: auto i1 = static_cast<int>(l);
18
19 const int i2 = static_cast<int>(l);
20 // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use auto when initializing with a cast to avoid duplicating the type name
21 // CHECK-FIXES: const auto i2 = static_cast<int>(l);
22
23 long long ll = static_cast<long long>(l);
24 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
25 // CHECK-FIXES: auto ll = static_cast<long long>(l);
26 unsigned long long ull = static_cast<unsigned long long>(l);
27 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
28 // CHECK-FIXES: auto ull = static_cast<unsigned long long>(l);
29 unsigned int ui = static_cast<unsigned int>(l);
30 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
31 // CHECK-FIXES: auto ui = static_cast<unsigned int>(l);
32 long double ld = static_cast<long double>(l);
33 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
34 // CHECK-FIXES: auto ld = static_cast<long double>(l);
35
36 A *a = new B();
37 B *b1 = static_cast<B *>(a);
38 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
39 // CHECK-FIXES: auto *b1 = static_cast<B *>(a);
40
41 B *const b2 = static_cast<B *>(a);
42 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
43 // CHECK-FIXES: auto *const b2 = static_cast<B *>(a);
44
45 const B *b3 = static_cast<const B *>(a);
46 // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use auto when initializing with a cast to avoid duplicating the type name
47 // CHECK-FIXES: const auto *b3 = static_cast<const B *>(a);
48
49 B &b4 = static_cast<B &>(*a);
50 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
51 // CHECK-FIXES: auto &b4 = static_cast<B &>(*a);
52
53 const B &b5 = static_cast<const B &>(*a);
54 // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use auto when initializing with a cast to avoid duplicating the type name
55 // CHECK-FIXES: const auto &b5 = static_cast<const B &>(*a);
56
57 B &b6 = static_cast<B &>(*a), &b7 = static_cast<B &>(*a);
58 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
59 // CHECK-FIXES: auto &b6 = static_cast<B &>(*a), &b7 = static_cast<B &>(*a);
60
61 // Don't warn when non-cast involved
62 long double cast = static_cast<long double>(l), noncast = 5;
63
64 // Don't warn when auto is already being used.
65 auto i3 = static_cast<int>(l);
66 auto *b8 = static_cast<B *>(a);
67 auto &b9 = static_cast<B &>(*a);
68}
69
70void f_dynamic_cast() {
71 A *a = new B();
72 B *b1 = dynamic_cast<B *>(a);
73 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
74 // CHECK-FIXES: auto *b1 = dynamic_cast<B *>(a);
75
76 B &b2 = dynamic_cast<B &>(*a);
77 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
78 // CHECK-FIXES: auto &b2 = dynamic_cast<B &>(*a);
79}
80
81void f_reinterpret_cast() {
82 auto *a = new A();
83 C *c1 = reinterpret_cast<C *>(a);
84 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
85 // CHECK-FIXES: auto *c1 = reinterpret_cast<C *>(a);
86
87 C &c2 = reinterpret_cast<C &>(*a);
88 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
89 // CHECK-FIXES: auto &c2 = reinterpret_cast<C &>(*a);
90}
91
92void f_const_cast() {
93 const A *a1 = new A();
94 A *a2 = const_cast<A *>(a1);
95 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
96 // CHECK-FIXES: auto *a2 = const_cast<A *>(a1);
97 A &a3 = const_cast<A &>(*a1);
98 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
99 // CHECK-FIXES: auto &a3 = const_cast<A &>(*a1);
100}
101
102typedef unsigned char xmlChar;
103#define BAD_CAST (xmlChar *)
104
105#define XMLCHAR_CAST(x) (xmlChar *)(x)
106
107#define CAST_IN_MACRO(x) \
108 do { \
109 xmlChar *s = (xmlChar *)(x); \
110 } while (false);
111// CHECK-FIXES: xmlChar *s = (xmlChar *)(x);
112
113void f_cstyle_cast() {
114 auto *a = new A();
115 C *c1 = (C *)a;
116 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
117 // CHECK-FIXES: auto *c1 = (C *)a;
118
119 C &c2 = (C &)*a;
120 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
121 // CHECK-FIXES: auto &c2 = (C &)*a;
122
123 xmlChar *s = BAD_CAST "xml";
124 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
125 // CHECK-FIXES: auto *s = BAD_CAST "xml";
126 xmlChar *t = XMLCHAR_CAST("xml");
127 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
128 // CHECK-FIXES: auto *t = XMLCHAR_CAST("xml");
129 CAST_IN_MACRO("xml");
130 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
131}
132
133void f_functional_cast() {
134 long l = 1;
135 int i1 = int(l);
136 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a cast to avoid duplicating the type name
137 // CHECK-FIXES: auto i1 = int(l);
138
139 B b;
140 A a = A(b);
141}
142
143class StringRef
144{
145public:
146 StringRef(const char *);
147 const char *begin() const;
148 const char *end() const;
149};
150
151template <typename T, typename U>
152T template_value_cast(const U &u);
153
154template <typename T, typename U>
155T *template_pointer_cast(U *u);
156
157template <typename T, typename U>
158T &template_reference_cast(U &u);
159
160template <typename T, typename U>
161const T *template_const_pointer_cast(const U *u);
162
163template <typename T, typename U>
164const T &template_const_reference_cast(const U &u);
165
166template <typename T>
167T template_value_get(StringRef s);
168
169struct S {
170 template <typename T>
171 const T *template_member_get();
172};
173
174template <typename T>
175T max(T t1, T t2);
176
177void f_template_cast()
178{
179 double d = 0;
180 int i1 = template_value_cast<int>(u: d);
181 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a template cast to avoid duplicating the type name
182 // CHECK-FIXES: auto i1 = template_value_cast<int>(d);
183
184 A *a = new B();
185 B *b1 = template_value_cast<B *>(u: a);
186 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a template cast to avoid duplicating the type name
187 // CHECK-FIXES: auto *b1 = template_value_cast<B *>(a);
188 B &b2 = template_value_cast<B &>(u: *a);
189 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a template cast to avoid duplicating the type name
190 // CHECK-FIXES: auto &b2 = template_value_cast<B &>(*a);
191 B *b3 = template_pointer_cast<B>(u: a);
192 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a template cast to avoid duplicating the type name
193 // CHECK-FIXES: auto *b3 = template_pointer_cast<B>(a);
194 B &b4 = template_reference_cast<B>(u&: *a);
195 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a template cast to avoid duplicating the type name
196 // CHECK-FIXES: auto &b4 = template_reference_cast<B>(*a);
197 const B *b5 = template_const_pointer_cast<B>(u: a);
198 // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use auto when initializing with a template cast to avoid duplicating the type name
199 // CHECK-FIXES: const auto *b5 = template_const_pointer_cast<B>(a);
200 const B &b6 = template_const_reference_cast<B>(u: *a);
201 // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use auto when initializing with a template cast to avoid duplicating the type name
202 // CHECK-FIXES: const auto &b6 = template_const_reference_cast<B>(*a);
203 B *b7 = template_value_get<B *>(s: "foo");
204 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a template cast to avoid duplicating the type name
205 // CHECK-FIXES: auto *b7 = template_value_get<B *>("foo");
206 B *b8 = template_value_get<B *>(s: "foo"), *b9 = template_value_get<B *>(s: "bar");
207 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use auto when initializing with a template cast to avoid duplicating the type name
208 // CHECK-FIXES: auto *b8 = template_value_get<B *>("foo"), *b9 = template_value_get<B *>("bar");
209
210 S s;
211 const B *b10 = s.template_member_get<B>();
212 // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use auto when initializing with a template cast to avoid duplicating the type name
213 // CHECK-FIXES: const auto *b10 = s.template_member_get<B>();
214
215 // Don't warn when auto is already being used.
216 auto i2 = template_value_cast<int>(u: d);
217 auto *i3 = template_value_cast<int *>(u: d);
218 auto **i4 = template_value_cast<int **>(u: d);
219 auto &i5 = template_reference_cast<int>(u&: d);
220
221 // Don't warn for implicit template arguments.
222 int i6 = max(t1: i1, t2: i2);
223
224 // Don't warn for mismatched var and initializer types.
225 A *a1 = template_value_cast<B *>(u: a);
226
227 // Don't warn for mismatched var types.
228 B *b11 = template_value_get<B *>(s: "foo"), b12 = template_value_get<B>(s: "bar");
229
230 // Don't warn for implicit variables.
231 for (auto &c : template_reference_cast<StringRef>(u&: *a)) {
232 }
233}
234

source code of clang-tools-extra/test/clang-tidy/checkers/modernize/use-auto-cast.cpp