r338339 - [analyzer] Rename test: cxx17-mandatory-elision.cpp -> copy-elision.cpp
Artem Dergachev via cfe-commits
cfe-commits at lists.llvm.org
Mon Jul 30 17:18:36 PDT 2018
Author: dergachev
Date: Mon Jul 30 17:18:35 2018
New Revision: 338339
URL: http://llvm.org/viewvc/llvm-project?rev=338339&view=rev
Log:
[analyzer] Rename test: cxx17-mandatory-elision.cpp -> copy-elision.cpp
It reflects its contents more accurately. No functional change intended.
Added:
cfe/trunk/test/Analysis/copy-elision.cpp
Removed:
cfe/trunk/test/Analysis/cxx17-mandatory-elision.cpp
Added: cfe/trunk/test/Analysis/copy-elision.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Analysis/copy-elision.cpp?rev=338339&view=auto
==============================================================================
--- cfe/trunk/test/Analysis/copy-elision.cpp (added)
+++ cfe/trunk/test/Analysis/copy-elision.cpp Mon Jul 30 17:18:35 2018
@@ -0,0 +1,304 @@
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++11 -verify %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++17 -verify %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++11 -analyzer-config elide-constructors=false -DNO_ELIDE_FLAG -verify %s
+// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++17 -analyzer-config elide-constructors=false -DNO_ELIDE_FLAG -verify %s
+
+// Copy elision always occurs in C++17, otherwise it's under
+// an on-by-default flag.
+#if __cplusplus >= 201703L
+ #define ELIDE 1
+#else
+ #ifndef NO_ELIDE_FLAG
+ #define ELIDE 1
+ #endif
+#endif
+
+void clang_analyzer_eval(bool);
+
+namespace variable_functional_cast_crash {
+
+struct A {
+ A(int) {}
+};
+
+void foo() {
+ A a = A(0);
+}
+
+struct B {
+ A a;
+ B(): a(A(0)) {}
+};
+
+} // namespace variable_functional_cast_crash
+
+
+namespace ctor_initializer {
+
+struct S {
+ int x, y, z;
+};
+
+struct T {
+ S s;
+ int w;
+ T(int w): s(), w(w) {}
+};
+
+class C {
+ T t;
+public:
+ C() : t(T(4)) {
+ S s = {1, 2, 3};
+ t.s = s;
+ // FIXME: Should be TRUE regardless of copy elision.
+ clang_analyzer_eval(t.w == 4);
+#ifdef ELIDE
+ // expected-warning at -2{{TRUE}}
+#else
+ // expected-warning at -4{{UNKNOWN}}
+#endif
+ }
+};
+
+
+struct A {
+ int x;
+ A(): x(0) {}
+ ~A() {}
+};
+
+struct B {
+ A a;
+ B() : a(A()) {}
+};
+
+void foo() {
+ B b;
+ clang_analyzer_eval(b.a.x == 0); // expected-warning{{TRUE}}
+}
+
+} // namespace ctor_initializer
+
+
+namespace elision_on_ternary_op_branches {
+class C1 {
+ int x;
+public:
+ C1(int x): x(x) {}
+ int getX() const { return x; }
+ ~C1();
+};
+
+class C2 {
+ int x;
+ int y;
+public:
+ C2(int x, int y): x(x), y(y) {}
+ int getX() const { return x; }
+ int getY() const { return y; }
+ ~C2();
+};
+
+void foo(int coin) {
+ C1 c1 = coin ? C1(1) : C1(2);
+ if (coin) {
+ clang_analyzer_eval(c1.getX() == 1); // expected-warning{{TRUE}}
+ } else {
+ clang_analyzer_eval(c1.getX() == 2); // expected-warning{{TRUE}}
+ }
+ C2 c2 = coin ? C2(3, 4) : C2(5, 6);
+ if (coin) {
+ clang_analyzer_eval(c2.getX() == 3); // expected-warning{{TRUE}}
+ clang_analyzer_eval(c2.getY() == 4); // expected-warning{{TRUE}}
+ } else {
+ clang_analyzer_eval(c2.getX() == 5); // expected-warning{{TRUE}}
+ clang_analyzer_eval(c2.getY() == 6); // expected-warning{{TRUE}}
+ }
+}
+} // namespace elision_on_ternary_op_branches
+
+
+namespace address_vector_tests {
+
+template <typename T> struct AddressVector {
+ T *buf[10];
+ int len;
+
+ AddressVector() : len(0) {}
+
+ void push(T *t) {
+ buf[len] = t;
+ ++len;
+ }
+};
+
+class ClassWithoutDestructor {
+ AddressVector<ClassWithoutDestructor> &v;
+
+public:
+ ClassWithoutDestructor(AddressVector<ClassWithoutDestructor> &v) : v(v) {
+ v.push(this);
+ }
+
+ ClassWithoutDestructor(ClassWithoutDestructor &&c) : v(c.v) { v.push(this); }
+ ClassWithoutDestructor(const ClassWithoutDestructor &c) : v(c.v) {
+ v.push(this);
+ }
+};
+
+ClassWithoutDestructor make1(AddressVector<ClassWithoutDestructor> &v) {
+ return ClassWithoutDestructor(v);
+}
+ClassWithoutDestructor make2(AddressVector<ClassWithoutDestructor> &v) {
+ return make1(v);
+}
+ClassWithoutDestructor make3(AddressVector<ClassWithoutDestructor> &v) {
+ return make2(v);
+}
+
+void testMultipleReturns() {
+ AddressVector<ClassWithoutDestructor> v;
+ ClassWithoutDestructor c = make3(v);
+
+#if ELIDE
+ clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] == &c); // expected-warning{{TRUE}}
+#else
+ clang_analyzer_eval(v.len == 5); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] != v.buf[1]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[1] != v.buf[2]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[2] != v.buf[3]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[3] != v.buf[4]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[4] == &c); // expected-warning{{TRUE}}
+#endif
+}
+
+class ClassWithDestructor {
+ AddressVector<ClassWithDestructor> &v;
+
+public:
+ ClassWithDestructor(AddressVector<ClassWithDestructor> &v) : v(v) {
+ v.push(this);
+ }
+
+ ClassWithDestructor(ClassWithDestructor &&c) : v(c.v) { v.push(this); }
+ ClassWithDestructor(const ClassWithDestructor &c) : v(c.v) {
+ v.push(this);
+ }
+
+ ~ClassWithDestructor() { v.push(this); }
+};
+
+void testVariable() {
+ AddressVector<ClassWithDestructor> v;
+ {
+ ClassWithDestructor c = ClassWithDestructor(v);
+ // Check if the last destructor is an automatic destructor.
+ // A temporary destructor would have fired by now.
+#if ELIDE
+ clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
+#else
+ clang_analyzer_eval(v.len == 3); // expected-warning{{TRUE}}
+#endif
+ }
+#if ELIDE
+ // 0. Construct the variable.
+ // 1. Destroy the variable.
+ clang_analyzer_eval(v.len == 2); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] == v.buf[1]); // expected-warning{{TRUE}}
+#else
+ // 0. Construct the temporary.
+ // 1. Construct the variable.
+ // 2. Destroy the temporary.
+ // 3. Destroy the variable.
+ clang_analyzer_eval(v.len == 4); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] == v.buf[2]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[1] == v.buf[3]); // expected-warning{{TRUE}}
+#endif
+}
+
+struct TestCtorInitializer {
+ ClassWithDestructor c;
+ TestCtorInitializer(AddressVector<ClassWithDestructor> &v)
+ : c(ClassWithDestructor(v)) {}
+};
+
+void testCtorInitializer() {
+ AddressVector<ClassWithDestructor> v;
+ {
+ TestCtorInitializer t(v);
+ // Check if the last destructor is an automatic destructor.
+ // A temporary destructor would have fired by now.
+#if ELIDE
+ clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
+#else
+ clang_analyzer_eval(v.len == 3); // expected-warning{{TRUE}}
+#endif
+ }
+#if ELIDE
+ // 0. Construct the member variable.
+ // 1. Destroy the member variable.
+ clang_analyzer_eval(v.len == 2); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] == v.buf[1]); // expected-warning{{TRUE}}
+#else
+ // 0. Construct the temporary.
+ // 1. Construct the member variable.
+ // 2. Destroy the temporary.
+ // 3. Destroy the member variable.
+ clang_analyzer_eval(v.len == 4); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] == v.buf[2]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[1] == v.buf[3]); // expected-warning{{TRUE}}
+#endif
+}
+
+
+ClassWithDestructor make1(AddressVector<ClassWithDestructor> &v) {
+ return ClassWithDestructor(v);
+}
+ClassWithDestructor make2(AddressVector<ClassWithDestructor> &v) {
+ return make1(v);
+}
+ClassWithDestructor make3(AddressVector<ClassWithDestructor> &v) {
+ return make2(v);
+}
+
+void testMultipleReturnsWithDestructors() {
+ AddressVector<ClassWithDestructor> v;
+ {
+ ClassWithDestructor c = make3(v);
+ // Check if the last destructor is an automatic destructor.
+ // A temporary destructor would have fired by now.
+#if ELIDE
+ clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
+#else
+ clang_analyzer_eval(v.len == 9); // expected-warning{{TRUE}}
+#endif
+ }
+
+#if ELIDE
+ // 0. Construct the variable. Yes, constructor in make1() constructs
+ // the variable 'c'.
+ // 1. Destroy the variable.
+ clang_analyzer_eval(v.len == 2); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] == v.buf[1]); // expected-warning{{TRUE}}
+#else
+ // 0. Construct the temporary in make1().
+ // 1. Construct the temporary in make2().
+ // 2. Destroy the temporary in make1().
+ // 3. Construct the temporary in make3().
+ // 4. Destroy the temporary in make2().
+ // 5. Construct the temporary here.
+ // 6. Destroy the temporary in make3().
+ // 7. Construct the variable.
+ // 8. Destroy the temporary here.
+ // 9. Destroy the variable.
+ clang_analyzer_eval(v.len == 10); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[0] == v.buf[2]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[1] == v.buf[4]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[3] == v.buf[6]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[5] == v.buf[8]); // expected-warning{{TRUE}}
+ clang_analyzer_eval(v.buf[7] == v.buf[9]); // expected-warning{{TRUE}}
+#endif
+}
+} // namespace address_vector_tests
Removed: cfe/trunk/test/Analysis/cxx17-mandatory-elision.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Analysis/cxx17-mandatory-elision.cpp?rev=338338&view=auto
==============================================================================
--- cfe/trunk/test/Analysis/cxx17-mandatory-elision.cpp (original)
+++ cfe/trunk/test/Analysis/cxx17-mandatory-elision.cpp (removed)
@@ -1,304 +0,0 @@
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++11 -verify %s
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++17 -verify %s
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++11 -analyzer-config elide-constructors=false -DNO_ELIDE_FLAG -verify %s
-// RUN: %clang_analyze_cc1 -analyzer-checker=core,debug.ExprInspection -std=c++17 -analyzer-config elide-constructors=false -DNO_ELIDE_FLAG -verify %s
-
-// Copy elision always occurs in C++17, otherwise it's under
-// an on-by-default flag.
-#if __cplusplus >= 201703L
- #define ELIDE 1
-#else
- #ifndef NO_ELIDE_FLAG
- #define ELIDE 1
- #endif
-#endif
-
-void clang_analyzer_eval(bool);
-
-namespace variable_functional_cast_crash {
-
-struct A {
- A(int) {}
-};
-
-void foo() {
- A a = A(0);
-}
-
-struct B {
- A a;
- B(): a(A(0)) {}
-};
-
-} // namespace variable_functional_cast_crash
-
-
-namespace ctor_initializer {
-
-struct S {
- int x, y, z;
-};
-
-struct T {
- S s;
- int w;
- T(int w): s(), w(w) {}
-};
-
-class C {
- T t;
-public:
- C() : t(T(4)) {
- S s = {1, 2, 3};
- t.s = s;
- // FIXME: Should be TRUE regardless of copy elision.
- clang_analyzer_eval(t.w == 4);
-#ifdef ELIDE
- // expected-warning at -2{{TRUE}}
-#else
- // expected-warning at -4{{UNKNOWN}}
-#endif
- }
-};
-
-
-struct A {
- int x;
- A(): x(0) {}
- ~A() {}
-};
-
-struct B {
- A a;
- B() : a(A()) {}
-};
-
-void foo() {
- B b;
- clang_analyzer_eval(b.a.x == 0); // expected-warning{{TRUE}}
-}
-
-} // namespace ctor_initializer
-
-
-namespace elision_on_ternary_op_branches {
-class C1 {
- int x;
-public:
- C1(int x): x(x) {}
- int getX() const { return x; }
- ~C1();
-};
-
-class C2 {
- int x;
- int y;
-public:
- C2(int x, int y): x(x), y(y) {}
- int getX() const { return x; }
- int getY() const { return y; }
- ~C2();
-};
-
-void foo(int coin) {
- C1 c1 = coin ? C1(1) : C1(2);
- if (coin) {
- clang_analyzer_eval(c1.getX() == 1); // expected-warning{{TRUE}}
- } else {
- clang_analyzer_eval(c1.getX() == 2); // expected-warning{{TRUE}}
- }
- C2 c2 = coin ? C2(3, 4) : C2(5, 6);
- if (coin) {
- clang_analyzer_eval(c2.getX() == 3); // expected-warning{{TRUE}}
- clang_analyzer_eval(c2.getY() == 4); // expected-warning{{TRUE}}
- } else {
- clang_analyzer_eval(c2.getX() == 5); // expected-warning{{TRUE}}
- clang_analyzer_eval(c2.getY() == 6); // expected-warning{{TRUE}}
- }
-}
-} // namespace elision_on_ternary_op_branches
-
-
-namespace address_vector_tests {
-
-template <typename T> struct AddressVector {
- T *buf[10];
- int len;
-
- AddressVector() : len(0) {}
-
- void push(T *t) {
- buf[len] = t;
- ++len;
- }
-};
-
-class ClassWithoutDestructor {
- AddressVector<ClassWithoutDestructor> &v;
-
-public:
- ClassWithoutDestructor(AddressVector<ClassWithoutDestructor> &v) : v(v) {
- v.push(this);
- }
-
- ClassWithoutDestructor(ClassWithoutDestructor &&c) : v(c.v) { v.push(this); }
- ClassWithoutDestructor(const ClassWithoutDestructor &c) : v(c.v) {
- v.push(this);
- }
-};
-
-ClassWithoutDestructor make1(AddressVector<ClassWithoutDestructor> &v) {
- return ClassWithoutDestructor(v);
-}
-ClassWithoutDestructor make2(AddressVector<ClassWithoutDestructor> &v) {
- return make1(v);
-}
-ClassWithoutDestructor make3(AddressVector<ClassWithoutDestructor> &v) {
- return make2(v);
-}
-
-void testMultipleReturns() {
- AddressVector<ClassWithoutDestructor> v;
- ClassWithoutDestructor c = make3(v);
-
-#if ELIDE
- clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] == &c); // expected-warning{{TRUE}}
-#else
- clang_analyzer_eval(v.len == 5); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] != v.buf[1]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[1] != v.buf[2]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[2] != v.buf[3]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[3] != v.buf[4]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[4] == &c); // expected-warning{{TRUE}}
-#endif
-}
-
-class ClassWithDestructor {
- AddressVector<ClassWithDestructor> &v;
-
-public:
- ClassWithDestructor(AddressVector<ClassWithDestructor> &v) : v(v) {
- v.push(this);
- }
-
- ClassWithDestructor(ClassWithDestructor &&c) : v(c.v) { v.push(this); }
- ClassWithDestructor(const ClassWithDestructor &c) : v(c.v) {
- v.push(this);
- }
-
- ~ClassWithDestructor() { v.push(this); }
-};
-
-void testVariable() {
- AddressVector<ClassWithDestructor> v;
- {
- ClassWithDestructor c = ClassWithDestructor(v);
- // Check if the last destructor is an automatic destructor.
- // A temporary destructor would have fired by now.
-#if ELIDE
- clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
-#else
- clang_analyzer_eval(v.len == 3); // expected-warning{{TRUE}}
-#endif
- }
-#if ELIDE
- // 0. Construct the variable.
- // 1. Destroy the variable.
- clang_analyzer_eval(v.len == 2); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] == v.buf[1]); // expected-warning{{TRUE}}
-#else
- // 0. Construct the temporary.
- // 1. Construct the variable.
- // 2. Destroy the temporary.
- // 3. Destroy the variable.
- clang_analyzer_eval(v.len == 4); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] == v.buf[2]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[1] == v.buf[3]); // expected-warning{{TRUE}}
-#endif
-}
-
-struct TestCtorInitializer {
- ClassWithDestructor c;
- TestCtorInitializer(AddressVector<ClassWithDestructor> &v)
- : c(ClassWithDestructor(v)) {}
-};
-
-void testCtorInitializer() {
- AddressVector<ClassWithDestructor> v;
- {
- TestCtorInitializer t(v);
- // Check if the last destructor is an automatic destructor.
- // A temporary destructor would have fired by now.
-#if ELIDE
- clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
-#else
- clang_analyzer_eval(v.len == 3); // expected-warning{{TRUE}}
-#endif
- }
-#if ELIDE
- // 0. Construct the member variable.
- // 1. Destroy the member variable.
- clang_analyzer_eval(v.len == 2); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] == v.buf[1]); // expected-warning{{TRUE}}
-#else
- // 0. Construct the temporary.
- // 1. Construct the member variable.
- // 2. Destroy the temporary.
- // 3. Destroy the member variable.
- clang_analyzer_eval(v.len == 4); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] == v.buf[2]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[1] == v.buf[3]); // expected-warning{{TRUE}}
-#endif
-}
-
-
-ClassWithDestructor make1(AddressVector<ClassWithDestructor> &v) {
- return ClassWithDestructor(v);
-}
-ClassWithDestructor make2(AddressVector<ClassWithDestructor> &v) {
- return make1(v);
-}
-ClassWithDestructor make3(AddressVector<ClassWithDestructor> &v) {
- return make2(v);
-}
-
-void testMultipleReturnsWithDestructors() {
- AddressVector<ClassWithDestructor> v;
- {
- ClassWithDestructor c = make3(v);
- // Check if the last destructor is an automatic destructor.
- // A temporary destructor would have fired by now.
-#if ELIDE
- clang_analyzer_eval(v.len == 1); // expected-warning{{TRUE}}
-#else
- clang_analyzer_eval(v.len == 9); // expected-warning{{TRUE}}
-#endif
- }
-
-#if ELIDE
- // 0. Construct the variable. Yes, constructor in make1() constructs
- // the variable 'c'.
- // 1. Destroy the variable.
- clang_analyzer_eval(v.len == 2); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] == v.buf[1]); // expected-warning{{TRUE}}
-#else
- // 0. Construct the temporary in make1().
- // 1. Construct the temporary in make2().
- // 2. Destroy the temporary in make1().
- // 3. Construct the temporary in make3().
- // 4. Destroy the temporary in make2().
- // 5. Construct the temporary here.
- // 6. Destroy the temporary in make3().
- // 7. Construct the variable.
- // 8. Destroy the temporary here.
- // 9. Destroy the variable.
- clang_analyzer_eval(v.len == 10); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[0] == v.buf[2]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[1] == v.buf[4]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[3] == v.buf[6]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[5] == v.buf[8]); // expected-warning{{TRUE}}
- clang_analyzer_eval(v.buf[7] == v.buf[9]); // expected-warning{{TRUE}}
-#endif
-}
-} // namespace address_vector_tests
More information about the cfe-commits
mailing list