Fixed #6811 (ValueFlow: result of ?:)

This commit is contained in:
Daniel Marjamäki 2015-07-02 20:11:27 +02:00
parent 14044bf60b
commit c751039612
2 changed files with 41 additions and 0 deletions

View File

@ -329,6 +329,40 @@ static void setTokenValue(Token* tok, const ValueFlow::Value &value)
setTokenValue(parent,value);
}
else if (parent->str() == ":") {
setTokenValue(parent,value);
}
else if (parent->str() == "?") {
// is condition only depending on 1 variable?
std::stack<const Token*> tokens;
tokens.push(parent->astOperand1());
std::set<unsigned int> variables; // used variables
while (!tokens.empty()) {
const Token *t = tokens.top();
tokens.pop();
if (!t)
continue;
tokens.push(t->astOperand1());
tokens.push(t->astOperand2());
if (t->varId()) {
variables.insert(t->varId());
if (variables.size() > 1U || value.varId != 0U)
return;
} else if (t->str() == "(" && Token::Match(t->previous(), "%name%"))
return; // function call
}
ValueFlow::Value v(value);
if (!variables.empty()) {
v.varId = *(variables.begin());
return;
}
setTokenValue(parent, v);
}
// Calculations..
else if (parent->isArithmeticalOp() && parent->astOperand1() && parent->astOperand2()) {
std::list<ValueFlow::Value>::const_iterator value1, value2;

View File

@ -253,6 +253,13 @@ private:
ASSERT_EQUALS(4, values.front().intvalue);
ASSERT_EQUALS(16, values.back().intvalue);
// ? :
code = "x = y ? 2 : 3;\n";
values = tokenValues(code,"?");
ASSERT_EQUALS(2U, values.size());
ASSERT_EQUALS(2, values.front().intvalue);
ASSERT_EQUALS(3, values.back().intvalue);
// function call => calculation
code = "void f(int x) {\n"
" a = x + 8;\n"