value flow: loosen up bailouts in valueFlowSubFunction

This commit is contained in:
Daniel Marjamäki 2014-01-11 07:52:25 +01:00
parent 1f53018b8e
commit 1ad94a8be5
2 changed files with 13 additions and 8 deletions

View File

@ -87,11 +87,13 @@ static void valueFlowBeforeCondition(TokenList *tokenlist, ErrorLogger *errorLog
const ValueFlow::Value val(tok, num); const ValueFlow::Value val(tok, num);
ValueFlow::Value val2; ValueFlow::Value val2;
if (var && if (var && num==1U && Token::Match(tok,"<=|>=")) {
var->typeStartToken()->isUnsigned() && bool isunsigned = var->typeEndToken()->isUnsigned();
((num==0 && Token::Match(tok,"<|>")) || for (const Token* type = var->typeStartToken(); type != var->typeEndToken(); type = type->next())
(num==1 && Token::Match(tok,"<=|>=")))) isunsigned |= type->isUnsigned();
val2 = ValueFlow::Value(tok,0); if (isunsigned)
val2 = ValueFlow::Value(tok,0);
}
for (Token *tok2 = tok->previous(); ; tok2 = tok2->previous()) { for (Token *tok2 = tok->previous(); ; tok2 = tok2->previous()) {
if (!tok2) { if (!tok2) {
@ -273,11 +275,10 @@ static void valueFlowSubFunction(TokenList *tokenlist, ErrorLogger *errorLogger,
// Set value in function scope.. // Set value in function scope..
const unsigned int varid2 = arg->nameToken()->varId(); const unsigned int varid2 = arg->nameToken()->varId();
for (const Token *tok2 = functionScope->classStart->next(); tok2 != functionScope->classEnd; tok2 = tok2->next()) { for (const Token *tok2 = functionScope->classStart->next(); tok2 != functionScope->classEnd; tok2 = tok2->next()) {
if (Token::Match(tok2, "%cop%|return %varid%", varid2) || Token::Match(tok2, "= %varid% %cop%|;", varid2)) { if (Token::Match(tok2, "%varid% !!=", varid2)) {
tok2 = tok2->next();
std::list<ValueFlow::Value> &values = const_cast<Token*>(tok2)->values; std::list<ValueFlow::Value> &values = const_cast<Token*>(tok2)->values;
values.insert(values.begin(), argvalues.begin(), argvalues.end()); values.insert(values.begin(), argvalues.begin(), argvalues.end());
} else if (tok2->varId() == varid2 || tok2->str() == "{") { } else if (tok2->str() == "{") {
if (settings->debugwarnings) if (settings->debugwarnings)
bailout(tokenlist, errorLogger, tok2, "parameter " + arg->nameToken()->str()); bailout(tokenlist, errorLogger, tok2, "parameter " + arg->nameToken()->str());
break; break;

View File

@ -203,6 +203,10 @@ private:
"void f2(int y) { f1(y<123); }\n"; "void f2(int y) { f1(y<123); }\n";
ASSERT_EQUALS(true, testValueOfX(code, 1U, 0)); ASSERT_EQUALS(true, testValueOfX(code, 1U, 0));
ASSERT_EQUALS(true, testValueOfX(code, 1U, 1)); ASSERT_EQUALS(true, testValueOfX(code, 1U, 1));
code = "void f1(int x) { a=(abc)x; }\n"
"void f2(int y) { f1(123); }\n";
ASSERT_EQUALS(true, testValueOfX(code, 1U, 123));
} }
}; };