Fixed #886 (new check: wrong value passed to isgraph function)
This commit is contained in:
parent
68a1b69d32
commit
994f08fdf0
|
@ -2027,7 +2027,6 @@ void CheckOther::checkMathFunctions()
|
|||
MathLib::isNegative(tok->strAt(4))) {
|
||||
mathfunctionCallError(tok, 2);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2041,7 +2040,22 @@ void CheckOther::mathfunctionCallError(const Token *tok, const unsigned int numP
|
|||
} else
|
||||
reportError(tok, Severity::error, "wrongmathcall", "Passing value " " to " "() leads to undefined result");
|
||||
}
|
||||
|
||||
//---------------------------------------------------------------------------
|
||||
//---------------------------------------------------------------------------
|
||||
void CheckOther::checkCCTypeFunctions()
|
||||
{
|
||||
for (const Token *tok = _tokenizer->tokens(); tok; tok = tok->next()) {
|
||||
if (tok->varId() == 0 &&
|
||||
Token::Match(tok, "isalnum|isalpha|iscntrl|isdigit|isgraph|islower|isprint|ispunct|isspace|isupper|isxdigit ( %num% )") &&
|
||||
MathLib::isNegative(tok->strAt(2))) {
|
||||
cctypefunctionCallError(tok, tok->str(), tok->tokAt(2)->str());
|
||||
}
|
||||
}
|
||||
}
|
||||
void CheckOther::cctypefunctionCallError(const Token *tok, const std::string &functionName, const std::string &value)
|
||||
{
|
||||
reportError(tok, Severity::error, "wrongcctypecall", "Passing value " + value + " to " + functionName + "() cause undefined behavior, which may lead to a crash");
|
||||
}
|
||||
//---------------------------------------------------------------------------
|
||||
//---------------------------------------------------------------------------
|
||||
/** Is there a function with given name? */
|
||||
|
|
|
@ -87,6 +87,7 @@ public:
|
|||
checkOther.invalidFunctionUsage();
|
||||
checkOther.checkZeroDivision();
|
||||
checkOther.checkMathFunctions();
|
||||
checkOther.checkCCTypeFunctions();
|
||||
checkOther.checkFflushOnInputStream();
|
||||
checkOther.invalidScanf();
|
||||
checkOther.checkWrongPrintfScanfArguments();
|
||||
|
@ -151,6 +152,9 @@ public:
|
|||
/** @brief %Check for parameters given to math function that do not make sense*/
|
||||
void checkMathFunctions();
|
||||
|
||||
/** @brief %Check for parameters given to cctype function that do make error*/
|
||||
void checkCCTypeFunctions();
|
||||
|
||||
void lookupVar(const Token *tok1, const std::string &varname);
|
||||
|
||||
/** @brief %Check for using fflush() on an input stream*/
|
||||
|
@ -264,6 +268,7 @@ public:
|
|||
void zerodivError(const Token *tok);
|
||||
void coutCerrMisusageError(const Token* tok, const std::string& streamName);
|
||||
void mathfunctionCallError(const Token *tok, const unsigned int numParam = 1);
|
||||
void cctypefunctionCallError(const Token *tok, const std::string &functionName, const std::string &value);
|
||||
void fflushOnInputStreamError(const Token *tok, const std::string &varname);
|
||||
void redundantAssignmentInSwitchError(const Token *tok, const std::string &varname);
|
||||
void redundantStrcpyInSwitchError(const Token *tok, const std::string &varname);
|
||||
|
@ -349,6 +354,7 @@ public:
|
|||
c.comparisonOfBoolExpressionWithIntError(0);
|
||||
c.SuspiciousSemicolonError(0);
|
||||
c.wrongPrintfScanfArgumentsError(0,"printf",3,2);
|
||||
c.cctypefunctionCallError(0, "funname", "value");
|
||||
}
|
||||
|
||||
std::string myName() const {
|
||||
|
@ -402,6 +408,7 @@ public:
|
|||
"* testing is unsigned variable is positive\n"
|
||||
"* using bool in bitwise expression\n"
|
||||
"* Suspicious use of ; at the end of 'if/for/while' statement.\n"
|
||||
"* incorrect usage of functions from ctype library.\n"
|
||||
|
||||
// optimisations
|
||||
"* optimisation: detect post increment/decrement\n";
|
||||
|
|
|
@ -71,6 +71,7 @@ private:
|
|||
TEST_CASE(passedByValue);
|
||||
|
||||
TEST_CASE(mathfunctionCall1);
|
||||
TEST_CASE(cctypefunctionCall);
|
||||
|
||||
TEST_CASE(fflushOnInputStreamTest);
|
||||
|
||||
|
@ -1030,6 +1031,141 @@ private:
|
|||
|
||||
}
|
||||
|
||||
void cctypefunctionCall() {
|
||||
// isalnum
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isalnum(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isalnum(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isalnum() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isalpha(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isalpha(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isalpha() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << iscntrl(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << iscntrl(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to iscntrl() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isdigit(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isdigit(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isdigit() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isgraph(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isgraph(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isgraph() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << islower(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << islower(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to islower() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isprint(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isprint(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isprint() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << ispunct(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << ispunct(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to ispunct() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isspace(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isspace(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isspace() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isupper(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isupper(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isupper() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isxdigit(61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("", errout.str());
|
||||
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
" std::cout << isxdigit(-61) << std::endl;\n"
|
||||
"}");
|
||||
ASSERT_EQUALS("[test.cpp:3]: (error) Passing value -61 to isxdigit() cause undefined behavior, which may lead to a crash\n", errout.str());
|
||||
|
||||
}
|
||||
void fflushOnInputStreamTest() {
|
||||
check("void foo()\n"
|
||||
"{\n"
|
||||
|
|
Loading…
Reference in New Issue