blob: 06f9c58bae60290d5e1d42b59df2d12a46aa8765 [file] [log] [blame]
Richard Trieuac3eca52015-04-29 01:52:17 +00001// RUN: %clang_cc1 -fsyntax-only -Wredundant-move -std=c++11 -verify %s
Richard Trieu8d4006a2015-07-28 19:06:16 +00002// RUN: not %clang_cc1 -fsyntax-only -Wredundant-move -std=c++11 -fdiagnostics-parseable-fixits %s 2>&1 | FileCheck %s
Richard Trieuac3eca52015-04-29 01:52:17 +00003
4// definitions for std::move
5namespace std {
6inline namespace foo {
7template <class T> struct remove_reference { typedef T type; };
8template <class T> struct remove_reference<T&> { typedef T type; };
9template <class T> struct remove_reference<T&&> { typedef T type; };
10
11template <class T> typename remove_reference<T>::type &&move(T &&t);
12}
13}
14
15struct A {};
16struct B : public A {};
17
18A test1(B b1) {
19 B b2;
Richard Trieu1d4911bc2015-05-18 19:54:08 +000020 return b1;
21 return b2;
Richard Trieuac3eca52015-04-29 01:52:17 +000022 return std::move(b1);
23 // expected-warning@-1{{redundant move}}
24 // expected-note@-2{{remove std::move call}}
25 // CHECK: fix-it:"{{.*}}":{[[@LINE-3]]:10-[[@LINE-3]]:20}:""
26 // CHECK: fix-it:"{{.*}}":{[[@LINE-4]]:22-[[@LINE-4]]:23}:""
27 return std::move(b2);
28 // expected-warning@-1{{redundant move}}
29 // expected-note@-2{{remove std::move call}}
30 // CHECK: fix-it:"{{.*}}":{[[@LINE-3]]:10-[[@LINE-3]]:20}:""
31 // CHECK: fix-it:"{{.*}}":{[[@LINE-4]]:22-[[@LINE-4]]:23}:""
32}
33
34struct C {
35 C() {}
36 C(A) {}
37};
38
39C test2(A a1, B b1) {
40 A a2;
41 B b2;
42
43 return a1;
44 return a2;
45 return b1;
46 return b2;
47
48 return std::move(a1);
49 // expected-warning@-1{{redundant move}}
50 // expected-note@-2{{remove std::move call}}
51 // CHECK: fix-it:"{{.*}}":{[[@LINE-3]]:10-[[@LINE-3]]:20}:""
52 // CHECK: fix-it:"{{.*}}":{[[@LINE-4]]:22-[[@LINE-4]]:23}:""
53 return std::move(a2);
54 // expected-warning@-1{{redundant move}}
55 // expected-note@-2{{remove std::move call}}
56 // CHECK: fix-it:"{{.*}}":{[[@LINE-3]]:10-[[@LINE-3]]:20}:""
57 // CHECK: fix-it:"{{.*}}":{[[@LINE-4]]:22-[[@LINE-4]]:23}:""
58 return std::move(b1);
59 // expected-warning@-1{{redundant move}}
60 // expected-note@-2{{remove std::move call}}
61 // CHECK: fix-it:"{{.*}}":{[[@LINE-3]]:10-[[@LINE-3]]:20}:""
62 // CHECK: fix-it:"{{.*}}":{[[@LINE-4]]:22-[[@LINE-4]]:23}:""
63 return std::move(b2);
64 // expected-warning@-1{{redundant move}}
65 // expected-note@-2{{remove std::move call}}
66 // CHECK: fix-it:"{{.*}}":{[[@LINE-3]]:10-[[@LINE-3]]:20}:""
67 // CHECK: fix-it:"{{.*}}":{[[@LINE-4]]:22-[[@LINE-4]]:23}:""
68}
Richard Trieu1d4911bc2015-05-18 19:54:08 +000069
70// Copy of tests above with types changed to reference types.
71A test3(B& b1) {
72 B& b2 = b1;
73 return b1;
74 return b2;
75 return std::move(b1);
76 return std::move(b2);
77}
78
79C test4(A& a1, B& b1) {
80 A& a2 = a1;
81 B& b2 = b1;
82
83 return a1;
84 return a2;
85 return b1;
86 return b2;
87
88 return std::move(a1);
89 return std::move(a2);
90 return std::move(b1);
91 return std::move(b2);
92}
Davide Italiano7842c3f2015-07-18 01:15:19 +000093
Richard Trieu159e5ed2015-07-21 23:38:30 +000094// PR23819, case 2
95struct D {};
96D test5(D d) {
97 return d;
98
99 return std::move(d);
100 // expected-warning@-1{{redundant move in return statement}}
101 // expected-note@-2{{remove std::move call here}}
102 // CHECK: fix-it:"{{.*}}":{[[@LINE-3]]:10-[[@LINE-3]]:20}:""
103 // CHECK: fix-it:"{{.*}}":{[[@LINE-4]]:21-[[@LINE-4]]:22}:""
104}
Richard Trieu8d4006a2015-07-28 19:06:16 +0000105
106// No more fix-its past here.
107// CHECK-NOT: fix-it
108
109// A deleted copy constructor will prevent moves without std::move
110struct E {
111 E(E &&e);
112 E(const E &e) = delete;
113 // expected-note@-1{{deleted here}}
114};
115
116struct F {
117 F(E);
118 // expected-note@-1{{passing argument to parameter here}}
119};
120
121F test6(E e) {
122 return e;
123 // expected-error@-1{{call to deleted constructor of 'E'}}
124 return std::move(e);
125}
126
127struct G {
128 G(G &&g);
129 // expected-note@-1{{copy constructor is implicitly deleted because 'G' has a user-declared move constructor}}
130};
131
132struct H {
133 H(G);
134 // expected-note@-1{{passing argument to parameter here}}
135};
136
137H test6(G g) {
138 return g; // expected-error{{call to implicitly-deleted copy constructor of 'G'}}
139 return std::move(g);
140}