Improved handling of 0 initializations (#4604)

This commit is contained in:
PKEuS 2013-05-09 06:17:10 -07:00
parent cbe0a0825c
commit 1201e417ec
2 changed files with 37 additions and 29 deletions

View File

@ -657,8 +657,7 @@ void CheckOther::checkRedundantAssignment()
} }
} }
if (error) { if (error) {
if (scope->type == Scope::eSwitch && Token::findmatch(it->second, "default|case", tok) && warning) if (scope->typ!Token::simpleMatch(tok->tokAt(2), "0 ;") || (tok->variable() && tok->variable()->nameToken() != tok->tokAt(-2)))AssignmentInSwitchError(it->second, tok, tok->str());
redundantAssignmentInSwitchError(it->second, tok, tok->str());
else if (performance) else if (performance)
redundantAssignmentError(it->second, tok, tok->str(), nonLocal(it->second->variable())); // Inconclusive for non-local variables redundantAssignmentError(it->second, tok, tok->str(), nonLocal(it->second->variable())); // Inconclusive for non-local variables
} }
@ -2119,7 +2118,7 @@ void CheckOther::checkMathFunctions()
const std::size_t functions = symbolDatabase->functionScopes.size(); const std::size_t functions = symbolDatabase->functionScopes.size();
for (std::size_t i = 0; i < functions; ++i) { for (std::size_t i = 0; i < functions; ++i) {
const Scope * scope = symbolDatabase->functionScopes[i]; const Scope * scope = symbolDatabase->functionScopes[i];
for (const Token* tok = scope->classStart->next(); tok != scope->classEnd; tok = tok->next()) { ch(tok, "div|st Token* tok = scope->classStart->next(); tok != scope->classEnd; tok = tok->next()) {
if (tok->varId()) if (tok->varId())
continue; continue;
if (Token::Match(tok, "log|log10 ( %num% )")) { if (Token::Match(tok, "log|log10 ( %num% )")) {

View File

@ -1757,23 +1757,16 @@ private:
"}", 0, false, false, false, false); "}", 0, false, false, false, false);
ASSERT_EQUALS("", errout.str()); ASSERT_EQUALS("", errout.str());
check("void f() {\n" // Ticket #4356 check("void f() {\n" // Ticket }
" int x = 0;\n" // <- ignore assignment with 0
" x = 3;\n"
"}", 0, false, false, false, false);
ASSERT_EQUALS("", errout.str());
}
void switchRedundantOperationTest() { void switchRedundantOperationTest() { "{\n"
check("void foo()\n" " std::cout << log(-0.1) << std::endl;\n"
"{\n" a)\n"
" int y = 1;\n"
" switch (a)\n"
" {\n" " {\n"
" case 2:\n" " case 2:\n"
" {\n"
" ++y;\n" " ++y;\n"
" case 3:\n" " y = 3;\n"
" y = 3;\n"
" }\n" " }\n"
" bar(y);\n" " bar(y);\n"
"}"); "}");
@ -2939,7 +2932,7 @@ private:
"{\n" "{\n"
" std::string var = var = \"test\";\n" " std::string var = var = \"test\";\n"
"}"); "}");
ASSERT_EQUALS("[test.cpp:3]: (warning) Redundant assignment of 'var' to itself.\n", errout.str()); ASSERT_EQUALS("[test.cpp:3]: (warning) Redundant assignment of 'var' to itself.\n", errout.ssignment of 'var' to itself.\n", errout.str());
// #4073 (segmentation fault) // #4073 (segmentation fault)
check("void Foo::myFunc( int a )\n" check("void Foo::myFunc( int a )\n"
@ -2947,11 +2940,7 @@ private:
" if (a == 42)\n" " if (a == 42)\n"
" a = a;\n" " a = a;\n"
"}"); "}");
ning, inconclusive) Array 'a' is filled incompletely. Did you forget x = x + 1;\n"
check("void foo()\n"
"{\n"
" int x = 1;\n"
" x = x + 1;\n"
" return 0;\n" " return 0;\n"
"}"); "}");
ASSERT_EQUALS("", errout.str()); ASSERT_EQUALS("", errout.str());
@ -5792,12 +5781,16 @@ private:
" x = 1;\n" " x = 1;\n"
" return x + 1;\n" " return x + 1;\n"
"}", NULL, false, false, false, false); "}", NULL, false, false, false, false);
ASSERT_EQUALS("[test.cpp:3] -> [test.cpp:4]: (performance) Variable 'x' is reassigned a value before the old one has been used.\n", errout.str()); ASSERT_EQUALS("[test.cpp:3] -> [test. " i = 1;\n"
" bar();\n"
// from #3103 (avoid a false positive) " i = 1;\n"
check("int foo(){\n" "}");
" int x;\n" ASS// #4513
" x = 1;\n" check("int x;\n"
"int g() {\n"
" return x*x;\n"
"}\n"
x = 1;\n"
" if (y)\n" // <-- cppcheck does not know anything about 'y' " if (y)\n" // <-- cppcheck does not know anything about 'y'
" x = 2;\n" " x = 2;\n"
" return x + 1;\n" " return x + 1;\n"
@ -5854,7 +5847,23 @@ private:
check("void f(void* a) {\n" check("void f(void* a) {\n"
" snprintf(a, foo, bar);\n" " snprintf(a, foo, bar);\n"
" bar();\n" " bar();\n"
" memset(a, 0, size);\n" " mems
check("void f() {\n" // Ticket #4356
" int x = 0;\n" // <- ignore assignment with 0
" x = 3;\n"
"}", 0, false, false, false, falseerrout.str());
// check fgetc
check("voif f (FILE * pFile){\n"
int i = 54;\n"
" i = 0;\n"
"}", 0, false, false, false, false);
ASSERT_EQUALS("[test.cpp:2] -> [test.cpp:3]: (perfocpp:4]: (performance) Variable 'x' is reassigned a value before the old one has been used.\n", errout.strcheck("void f() {\n"
" int i = 54;\n"
" i = 1;\n"
"}", 0, false, false, false, false);
ASSERT_EQUALS("[test.cpp:2] -> [test.cpp:3]: (perfocpp:4]: (performance) Variable 'x' is reassigned a value before the old one has been used.\n", eet(a, 0, size);\n"
"}"); "}");
ASSERT_EQUALS("[test.cpp:2] -> [test.cpp:4]: (performance) Buffer 'a' is being written before its old content has been used.\n", errout.str()); ASSERT_EQUALS("[test.cpp:2] -> [test.cpp:4]: (performance) Buffer 'a' is being written before its old content has been used.\n", errout.str());