Patch https://reviews.llvm.org/rC329780 not only rearranges comparisons but also binary expressions. This latter behavior is not protected by the analyzer option. Hower, since no complexity threshold is enforced to the symbols this may result in exponential execution time if the expressions are too complex: https://bugs.llvm.org/show_bug.cgi?id=38208. For a quick fix we extended the analyzer option to also cover the additive cases. This is only a temporary fix, the final solution should be enforcing the complexity threshold to the symbols. Differential Revision: https://reviews.llvm.org/D49536 llvm-svn: 337678
123 lines
3.1 KiB
C++
123 lines
3.1 KiB
C++
// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=core,cplusplus,alpha.cplusplus.IteratorRange -analyzer-eagerly-assume -analyzer-config aggressive-binary-operation-simplification=true -analyzer-config c++-container-inlining=false %s -verify
|
|
// RUN: %clang_analyze_cc1 -std=c++11 -analyzer-checker=core,cplusplus,alpha.cplusplus.IteratorRange -analyzer-eagerly-assume -analyzer-config aggressive-binary-operation-simplification=true -analyzer-config c++-container-inlining=true -DINLINE=1 %s -verify
|
|
|
|
#include "Inputs/system-header-simulator-cxx.h"
|
|
|
|
void clang_analyzer_warnIfReached();
|
|
|
|
void simple_good_end(const std::vector<int> &v) {
|
|
auto i = v.end();
|
|
if (i != v.end()) {
|
|
clang_analyzer_warnIfReached();
|
|
*i; // no-warning
|
|
}
|
|
}
|
|
|
|
void simple_good_end_negated(const std::vector<int> &v) {
|
|
auto i = v.end();
|
|
if (!(i == v.end())) {
|
|
clang_analyzer_warnIfReached();
|
|
*i; // no-warning
|
|
}
|
|
}
|
|
|
|
void simple_bad_end(const std::vector<int> &v) {
|
|
auto i = v.end();
|
|
*i; // expected-warning{{Iterator accessed outside of its range}}
|
|
}
|
|
|
|
void simple_good_begin(const std::vector<int> &v) {
|
|
auto i = v.begin();
|
|
if (i != v.begin()) {
|
|
clang_analyzer_warnIfReached();
|
|
*--i; // no-warning
|
|
}
|
|
}
|
|
|
|
void simple_good_begin_negated(const std::vector<int> &v) {
|
|
auto i = v.begin();
|
|
if (!(i == v.begin())) {
|
|
clang_analyzer_warnIfReached();
|
|
*--i; // no-warning
|
|
}
|
|
}
|
|
|
|
void simple_bad_begin(const std::vector<int> &v) {
|
|
auto i = v.begin();
|
|
*--i; // expected-warning{{Iterator accessed outside of its range}}
|
|
}
|
|
|
|
void copy(const std::vector<int> &v) {
|
|
auto i1 = v.end();
|
|
auto i2 = i1;
|
|
*i2; // expected-warning{{Iterator accessed outside of its range}}
|
|
}
|
|
|
|
void decrease(const std::vector<int> &v) {
|
|
auto i = v.end();
|
|
--i;
|
|
*i; // no-warning
|
|
}
|
|
|
|
void copy_and_decrease1(const std::vector<int> &v) {
|
|
auto i1 = v.end();
|
|
auto i2 = i1;
|
|
--i1;
|
|
*i1; // no-warning
|
|
}
|
|
|
|
void copy_and_decrease2(const std::vector<int> &v) {
|
|
auto i1 = v.end();
|
|
auto i2 = i1;
|
|
--i1;
|
|
*i2; // expected-warning{{Iterator accessed outside of its range}}
|
|
}
|
|
|
|
void copy_and_increase1(const std::vector<int> &v) {
|
|
auto i1 = v.begin();
|
|
auto i2 = i1;
|
|
++i1;
|
|
if (i1 == v.end())
|
|
*i2; // no-warning
|
|
}
|
|
|
|
void copy_and_increase2(const std::vector<int> &v) {
|
|
auto i1 = v.begin();
|
|
auto i2 = i1;
|
|
++i1;
|
|
if (i2 == v.end())
|
|
*i2; // expected-warning{{Iterator accessed outside of its range}}
|
|
}
|
|
|
|
void copy_and_increase3(const std::vector<int> &v) {
|
|
auto i1 = v.begin();
|
|
auto i2 = i1;
|
|
++i1;
|
|
if (v.end() == i2)
|
|
*i2; // 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());
|
|
if (comp1)
|
|
*first;
|
|
}
|
|
|
|
void loop(std::vector<int> &V, int e) {
|
|
auto start = V.begin();
|
|
while (true) {
|
|
auto item = std::find(start, V.end(), e);
|
|
if (item == V.end())
|
|
break;
|
|
*item; // no-warning
|
|
start = ++item; // no-warning
|
|
}
|
|
}
|
|
|
|
void bad_move(std::list<int> &L1, std::list<int> &L2) {
|
|
auto i0 = --L2.cend();
|
|
L1 = std::move(L2);
|
|
*++i0; // expected-warning{{Iterator accessed outside of its range}}
|
|
}
|