]> granicus.if.org Git - clang/commitdiff
[Analyzer] Iterator Checker - Part 10: Tests for iterators passed as parameter
authorAdam Balogh <adam.balogh@ericsson.com>
Sat, 13 Oct 2018 10:24:48 +0000 (10:24 +0000)
committerAdam Balogh <adam.balogh@ericsson.com>
Sat, 13 Oct 2018 10:24:48 +0000 (10:24 +0000)
In earlier Clang Static Analyzer versions `check::Bind() was not invoked for
parameter passing, so we needed a trick which is not needed anymore. However
add the tests to ensure its working.

Differential Revision: https::/reviews.llvm.org/D32906

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@344443 91177308-0d34-0410-b5e6-96231b3b80d8

test/Analysis/iterator-range.cpp
test/Analysis/mismatched-iterator.cpp

index 32e3495a12b6a79fda7cffdf06aabc51ea27d459..78cdb095c4d163e94a87af14a1279d3effe472fa 100644 (file)
@@ -97,6 +97,28 @@ void copy_and_increase3(const std::vector<int> &v) {
     *i2; // expected-warning{{Iterator accessed outside of its range}}
 }
 
+template <class InputIterator, class T>
+InputIterator nonStdFind(InputIterator first, InputIterator last,
+                         const T &val) {
+  for (auto i = first; i != last; ++i) {
+    if (*i == val) {
+      return i;
+    }
+  }
+  return last;
+}
+
+void good_non_std_find(std::vector<int> &V, int e) {
+  auto first = nonStdFind(V.begin(), V.end(), e);
+  if (V.end() != first)
+    *first; // no-warning
+}
+
+void bad_non_std_find(std::vector<int> &V, int e) {
+  auto first = nonStdFind(V.begin(), V.end(), e);
+  *first; // expected-warning{{Iterator accessed outside of its range}}
+}
+
 void tricky(std::vector<int> &V, int e) {
   const auto first = V.begin();
   const auto comp1 = (first != V.end()), comp2 = (first == V.end());
index 7910b77c0b9a936d86bb13822188db43fd5a4ce2..23f54d3f796a1cd39d9dcf3def47aba29531271e 100644 (file)
@@ -144,6 +144,19 @@ void bad_overwrite(std::vector<int> &v1, std::vector<int> &v2, int n) {
   v1.insert(i, n); // expected-warning{{Container accessed using foreign iterator argument}}
 }
 
+template<typename Container, typename Iterator>
+bool is_cend(Container cont, Iterator it) {
+  return it == cont.cend();
+}
+
+void good_empty(std::vector<int> &v) {
+  is_cend(v, v.cbegin()); // no-warning
+}
+
+void bad_empty(std::vector<int> &v1, std::vector<int> &v2) {
+  is_cend(v1, v2.cbegin()); // expected-warning@-8{{Iterators of different containers used where the same container is expected}}
+}
+
 void good_move(std::vector<int> &v1, std::vector<int> &v2) {
   const auto i0 = ++v2.cbegin();
   v1 = std::move(v2);