Fixed #6495 (Improve check: uninitialized variable, 3rd function argument)

This commit is contained in:
Daniel Marjamäki 2015-03-14 19:23:33 +01:00
parent 42c4aa1c49
commit fd6bd97972
2 changed files with 35 additions and 11 deletions

View File

@ -57,18 +57,22 @@ void CheckNullPointer::parseFunctionCall(const Token &tok, std::list<const Token
(value == 0 && Token::Match(firstParam, "0|NULL ,|)"))) { (value == 0 && Token::Match(firstParam, "0|NULL ,|)"))) {
if (value == 0 && Token::Match(&tok, "snprintf|vsnprintf|fnprintf|vfnprintf") && secondParam && secondParam->str() != "0") // Only if length (second parameter) is not zero if (value == 0 && Token::Match(&tok, "snprintf|vsnprintf|fnprintf|vfnprintf") && secondParam && secondParam->str() != "0") // Only if length (second parameter) is not zero
var.push_back(firstParam); var.push_back(firstParam);
else if (value == 0 && library != nullptr && library->isnullargbad(&tok, 1) && checkNullpointerFunctionCallPlausibility(tok.function(), 1))
var.push_back(firstParam);
else if (value == 1 && library != nullptr && library->isuninitargbad(&tok, 1))
var.push_back(firstParam);
} }
// 2nd parameter.. // Library
if ((value == 0 && Token::Match(secondParam, "0|NULL ,|)")) || (secondParam && secondParam->varId() > 0 && Token::Match(secondParam->next(),"[,)]"))) { if (library) {
if (value == 0 && library != nullptr && library->isnullargbad(&tok, 2) && checkNullpointerFunctionCallPlausibility(tok.function(), 2)) const Token *param = tok.tokAt(2);
var.push_back(secondParam); int argnr = 1;
else if (value == 1 && library != nullptr && library->isuninitargbad(&tok, 2)) while (param) {
var.push_back(secondParam); if (Token::Match(param, "%var% ,|)") || (value==0 && Token::Match(param, "0|NULL ,|)"))) {
if (value == 0 && library->isnullargbad(&tok, argnr) && checkNullpointerFunctionCallPlausibility(tok.function(), argnr))
var.push_back(param);
else if (value == 1 && library->isuninitargbad(&tok, argnr))
var.push_back(param);
}
param = param->nextArgument();
argnr++;
}
} }
if (Token::Match(&tok, "printf|sprintf|snprintf|fprintf|fnprintf|scanf|sscanf|fscanf|wprintf|swprintf|fwprintf|wscanf|swscanf|fwscanf")) { if (Token::Match(&tok, "printf|sprintf|snprintf|fprintf|fnprintf|scanf|sscanf|fscanf|wprintf|swprintf|fwprintf|wscanf|swscanf|fwscanf")) {

View File

@ -2196,7 +2196,7 @@ private:
void functioncalllibrary() { void functioncalllibrary() {
Settings settings1; Settings settings1;
Tokenizer tokenizer(&settings1,this); Tokenizer tokenizer(&settings1,this);
std::istringstream code("void f() { int a,b; x(a,b); }"); std::istringstream code("void f() { int a,b,c; x(a,b,c); }");
tokenizer.tokenize(code,"test.c"); tokenizer.tokenize(code,"test.c");
const Token *xtok = Token::findsimplematch(tokenizer.tokens(), "x"); const Token *xtok = Token::findsimplematch(tokenizer.tokens(), "x");
@ -2206,6 +2206,7 @@ private:
Library::ArgumentChecks arg; Library::ArgumentChecks arg;
library.argumentChecks["x"][1] = arg; library.argumentChecks["x"][1] = arg;
library.argumentChecks["x"][2] = arg; library.argumentChecks["x"][2] = arg;
library.argumentChecks["x"][3] = arg;
std::list<const Token *> null, uninit; std::list<const Token *> null, uninit;
CheckNullPointer::parseFunctionCall(*xtok, null, &library, 0U); CheckNullPointer::parseFunctionCall(*xtok, null, &library, 0U);
@ -2220,6 +2221,7 @@ private:
Library::ArgumentChecks arg; Library::ArgumentChecks arg;
library.argumentChecks["x"][1] = arg; library.argumentChecks["x"][1] = arg;
library.argumentChecks["x"][2] = arg; library.argumentChecks["x"][2] = arg;
library.argumentChecks["x"][3] = arg;
library.argumentChecks["x"][1].notnull = true; library.argumentChecks["x"][1].notnull = true;
std::list<const Token *> null,uninit; std::list<const Token *> null,uninit;
@ -2236,6 +2238,7 @@ private:
Library::ArgumentChecks arg; Library::ArgumentChecks arg;
library.argumentChecks["x"][1] = arg; library.argumentChecks["x"][1] = arg;
library.argumentChecks["x"][2] = arg; library.argumentChecks["x"][2] = arg;
library.argumentChecks["x"][3] = arg;
library.argumentChecks["x"][2].notuninit = true; library.argumentChecks["x"][2].notuninit = true;
std::list<const Token *> null,uninit; std::list<const Token *> null,uninit;
@ -2245,6 +2248,23 @@ private:
ASSERT_EQUALS(1U, uninit.size()); ASSERT_EQUALS(1U, uninit.size());
ASSERT_EQUALS("b", uninit.front()->str()); ASSERT_EQUALS("b", uninit.front()->str());
} }
// for 3rd parameter uninit data is not ok..
{
Library library;
Library::ArgumentChecks arg;
library.argumentChecks["x"][1] = arg;
library.argumentChecks["x"][2] = arg;
library.argumentChecks["x"][3] = arg;
library.argumentChecks["x"][3].notuninit = true;
std::list<const Token *> null,uninit;
CheckNullPointer::parseFunctionCall(*xtok, null, &library, 0U);
CheckNullPointer::parseFunctionCall(*xtok, uninit, &library, 1U);
ASSERT_EQUALS(0U, null.size());
ASSERT_EQUALS(1U, uninit.size());
ASSERT_EQUALS("c", uninit.front()->str());
}
} }
void functioncallDefaultArguments() { void functioncallDefaultArguments() {