Fixed #5584 (FP: Division by zero when function not declared)

This commit is contained in:
Daniel Marjamäki 2014-03-20 16:12:58 +01:00
parent b37e9601c1
commit 54e7f34f4a
3 changed files with 24 additions and 11 deletions

View File

@ -2249,26 +2249,28 @@ void CheckOther::checkZeroDivision()
if (tok->variable() || tok->function()) if (tok->variable() || tok->function())
continue; continue;
} }
zerodivError(tok); zerodivError(tok,false);
} else if (Token::Match(tok, "[/%]") && tok->astOperand2() && !tok->astOperand2()->values.empty()) { } else if (Token::Match(tok, "[/%]") && tok->astOperand2() && !tok->astOperand2()->values.empty()) {
// Value flow.. // Value flow..
const ValueFlow::Value *value = tok->astOperand2()->getValue(0LL); const ValueFlow::Value *value = tok->astOperand2()->getValue(0LL);
if (value) { if (value) {
if (!_settings->inconclusive && value->inconclusive)
continue;
if (value->condition == nullptr) if (value->condition == nullptr)
zerodivError(tok); zerodivError(tok, value->inconclusive);
else if (_settings->isEnabled("warning")) else if (_settings->isEnabled("warning"))
zerodivcondError(value->condition,tok); zerodivcondError(value->condition,tok,value->inconclusive);
} }
} }
} }
} }
void CheckOther::zerodivError(const Token *tok) void CheckOther::zerodivError(const Token *tok, bool inconclusive)
{ {
reportError(tok, Severity::error, "zerodiv", "Division by zero."); reportError(tok, Severity::error, "zerodiv", "Division by zero.", inconclusive);
} }
void CheckOther::zerodivcondError(const Token *tokcond, const Token *tokdiv) void CheckOther::zerodivcondError(const Token *tokcond, const Token *tokdiv, bool inconclusive)
{ {
std::list<const Token *> callstack; std::list<const Token *> callstack;
while (Token::Match(tokcond, "(|%oror%|&&")) while (Token::Match(tokcond, "(|%oror%|&&"))
@ -2291,7 +2293,7 @@ void CheckOther::zerodivcondError(const Token *tokcond, const Token *tokdiv)
condition = tokcond->str() + "!=0"; condition = tokcond->str() + "!=0";
} }
const std::string linenr(MathLib::toString(tokdiv ? tokdiv->linenr() : 0)); const std::string linenr(MathLib::toString(tokdiv ? tokdiv->linenr() : 0));
reportError(callstack, Severity::warning, "zerodivcond", "Either the condition '"+condition+"' is useless or there is division by zero at line " + linenr + "."); reportError(callstack, Severity::warning, "zerodivcond", "Either the condition '"+condition+"' is useless or there is division by zero at line " + linenr + ".", inconclusive);
} }
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------

View File

@ -290,8 +290,8 @@ private:
void charBitOpError(const Token *tok); void charBitOpError(const Token *tok);
void variableScopeError(const Token *tok, const std::string &varname); void variableScopeError(const Token *tok, const std::string &varname);
void strPlusCharError(const Token *tok); void strPlusCharError(const Token *tok);
void zerodivError(const Token *tok); void zerodivError(const Token *tok, bool inconclusive);
void zerodivcondError(const Token *tokcond, const Token *tokdiv); void zerodivcondError(const Token *tokcond, const Token *tokdiv, bool inconclusive);
void nanInArithmeticExpressionError(const Token *tok); void nanInArithmeticExpressionError(const Token *tok);
void mathfunctionCallError(const Token *tok, const unsigned int numParam = 1); void mathfunctionCallError(const Token *tok, const unsigned int numParam = 1);
void redundantAssignmentError(const Token *tok1, const Token* tok2, const std::string& var, bool inconclusive); void redundantAssignmentError(const Token *tok1, const Token* tok2, const std::string& var, bool inconclusive);
@ -340,8 +340,8 @@ private:
c.invalidFunctionArgError(0, "func_name", 1, "1-4"); c.invalidFunctionArgError(0, "func_name", 1, "1-4");
c.invalidFunctionArgBoolError(0, "func_name", 1); c.invalidFunctionArgBoolError(0, "func_name", 1);
c.udivError(0, false); c.udivError(0, false);
c.zerodivError(0); c.zerodivError(0, false);
c.zerodivcondError(0,0); c.zerodivcondError(0,0,false);
c.mathfunctionCallError(0); c.mathfunctionCallError(0);
c.misusedScopeObjectError(NULL, "varname"); c.misusedScopeObjectError(NULL, "varname");
c.doubleFreeError(0, "varname"); c.doubleFreeError(0, "varname");

View File

@ -45,6 +45,7 @@ private:
TEST_CASE(zeroDiv5); TEST_CASE(zeroDiv5);
TEST_CASE(zeroDiv6); TEST_CASE(zeroDiv6);
TEST_CASE(zeroDiv7); // #4930 TEST_CASE(zeroDiv7); // #4930
TEST_CASE(zeroDiv8);
TEST_CASE(zeroDivCond); // division by zero / useless condition TEST_CASE(zeroDivCond); // division by zero / useless condition
@ -463,6 +464,16 @@ private:
"[test.cpp:3]: (error) Division by zero.\n", errout.str()); "[test.cpp:3]: (error) Division by zero.\n", errout.str());
} }
void zeroDiv8() {
// #5584 - FP when function is unknown
check("void f() {\n"
" int a = 0;\n"
" do_something(a);\n"
" return 4 / a;\n"
"}");
ASSERT_EQUALS("[test.cpp:4]: (error, inconclusive) Division by zero.\n", errout.str());
}
void zeroDivCond() { void zeroDivCond() {
check("void f(unsigned int x) {\n" check("void f(unsigned int x) {\n"
" int y = 17 / x;\n" " int y = 17 / x;\n"