void CheckCondition::alwaysTrueFalse() { if (!_settings->isEnabled("style")) return; const SymbolDatabase *symbolDatabase = _tokenizer->getSymbolDatabase(); const std::size_t functions = symbolDatabase->functionScopes.size(); for (std::size_t i = 0; i < functions; ++i) { const Scope * scope = symbolDatabase->functionScopes[i]; for (const Token* tok = scope->classStart->next(); tok != scope->classEnd; tok = tok->next()) { if (!Token::Match(tok, "%comp%|!")) continue; if (tok->link()) // don't write false positives when templates are used continue; if (tok->values.size() != 1U) continue; if (tok->values.front().valueKind != ValueFlow::Value::Known) continue; if (tok->astParent() && Token::Match(tok->astParent()->previous(), "%name% (")) alwaysTrueFalseError(tok, tok->values.front().intvalue != 0); } } }
void CheckCondition::alwaysTrueFalse() { if (!_settings->isEnabled("style")) return; const SymbolDatabase *symbolDatabase = _tokenizer->getSymbolDatabase(); const std::size_t functions = symbolDatabase->functionScopes.size(); for (std::size_t i = 0; i < functions; ++i) { const Scope * scope = symbolDatabase->functionScopes[i]; for (const Token* tok = scope->classStart->next(); tok != scope->classEnd; tok = tok->next()) { if (!Token::Match(tok, "%comp%|!")) continue; if (tok->link()) // don't write false positives when templates are used continue; if (tok->values.size() != 1U) continue; if (!tok->values.front().isKnown()) continue; if (!tok->astParent() || !Token::Match(tok->astParent()->previous(), "%name% (")) continue; // Don't warn in assertions. Condition is often 'always true' by intention. // If platform,defines,etc cause 'always false' then that is not dangerous neither. const std::string &str = tok->astParent()->previous()->str(); if (str.find("assert")!=std::string::npos || str.find("ASSERT")!=std::string::npos) continue; // Don't warn when there are expanded macros.. bool isExpandedMacro = false; std::stack<const Token*> tokens; tokens.push(tok); while (!tokens.empty()) { const Token *tok2 = tokens.top(); tokens.pop(); if (!tok2) continue; tokens.push(tok2->astOperand1()); tokens.push(tok2->astOperand2()); if (tok2->isExpandedMacro()) { isExpandedMacro = true; break; } } if (isExpandedMacro) continue; alwaysTrueFalseError(tok, tok->values.front().intvalue != 0); } } }
void CheckCondition::alwaysTrueFalse() { if (!_settings->isEnabled("style")) return; const SymbolDatabase *symbolDatabase = _tokenizer->getSymbolDatabase(); const std::size_t functions = symbolDatabase->functionScopes.size(); for (std::size_t i = 0; i < functions; ++i) { const Scope * scope = symbolDatabase->functionScopes[i]; for (const Token* tok = scope->classStart->next(); tok != scope->classEnd; tok = tok->next()) { const bool constValCond = Token::Match(tok->tokAt(-2), "if|while ( %num%|%char% )") && !Token::Match(tok,"0|1"); // just one number or char inside if|while const bool constValExpr = Token::Match(tok, "%num%|%char%") && tok->astParent() && Token::Match(tok->astParent(),"&&|%oror%|?"); // just one number or char in boolean expression const bool compExpr = Token::Match(tok, "%comp%|!"); // a compare expression if (!(constValCond || constValExpr || compExpr)) continue; if (tok->link()) // don't write false positives when templates are used continue; if (tok->values.size() != 1U) continue; if (!tok->values.front().isKnown()) continue; // Don't warn in assertions. Condition is often 'always true' by intention. // If platform,defines,etc cause 'always false' then that is not dangerous neither. bool assertFound = false; for (const Token * tok2 = tok->astParent(); tok2 ; tok2 = tok2->astParent()) { // move backwards and try to find "assert" if (tok2->str() == "(" && tok2->astOperand2()) { const std::string& str = tok2->previous()->str(); if ((str.find("assert")!=std::string::npos || str.find("ASSERT")!=std::string::npos)) assertFound = true; break; } } if (assertFound) continue; // Don't warn when there are expanded macros.. bool isExpandedMacro = false; std::stack<const Token*> tokens; tokens.push(tok); while (!tokens.empty()) { const Token *tok2 = tokens.top(); tokens.pop(); if (!tok2) continue; tokens.push(tok2->astOperand1()); tokens.push(tok2->astOperand2()); if (tok2->isExpandedMacro()) { isExpandedMacro = true; break; } } if (isExpandedMacro) continue; alwaysTrueFalseError(tok, tok->values.front().intvalue != 0); } } }