| 276 | } |
| 277 | |
| 278 | static void parseCompareEachInt( |
| 279 | const Token* tok, |
| 280 | const std::function<void(const Token* varTok, ValueFlow::Value true_value, ValueFlow::Value false_value)>& each, |
| 281 | const std::function<std::vector<ValueFlow::Value>(const Token*)>& evaluate) |
| 282 | { |
| 283 | if (!tok->astOperand1() || !tok->astOperand2()) |
| 284 | return; |
| 285 | if (tok->isComparisonOp()) { |
| 286 | std::vector<ValueFlow::Value> value1 = evaluate(tok->astOperand1()); |
| 287 | std::vector<ValueFlow::Value> value2 = evaluate(tok->astOperand2()); |
| 288 | if (!value1.empty() && !value2.empty()) { |
| 289 | if (tok->astOperand1()->hasKnownIntValue()) |
| 290 | value2.clear(); |
| 291 | if (tok->astOperand2()->hasKnownIntValue()) |
| 292 | value1.clear(); |
| 293 | } |
| 294 | for (const ValueFlow::Value& v1 : value1) { |
| 295 | if (isSaturated(v1.intvalue) || astIsFloat(tok->astOperand2(), /*unknown*/ false)) |
| 296 | continue; |
| 297 | ValueFlow::Value true_value = v1; |
| 298 | ValueFlow::Value false_value = v1; |
| 299 | setConditionalValues(tok, true, v1.intvalue, true_value, false_value); |
| 300 | each(tok->astOperand2(), std::move(true_value), std::move(false_value)); |
| 301 | } |
| 302 | for (const ValueFlow::Value& v2 : value2) { |
| 303 | if (isSaturated(v2.intvalue) || astIsFloat(tok->astOperand1(), /*unknown*/ false)) |
| 304 | continue; |
| 305 | ValueFlow::Value true_value = v2; |
| 306 | ValueFlow::Value false_value = v2; |
| 307 | setConditionalValues(tok, false, v2.intvalue, true_value, false_value); |
| 308 | each(tok->astOperand1(), std::move(true_value), std::move(false_value)); |
| 309 | } |
| 310 | } |
| 311 | } |
| 312 | |
| 313 | static void parseCompareEachInt( |
| 314 | const Token* tok, |
no test coverage detected