| 437 | } |
| 438 | |
| 439 | bool isTemporary(const Token* tok, const Library* library, bool unknown) |
| 440 | { |
| 441 | if (!tok) |
| 442 | return false; |
| 443 | if (Token::simpleMatch(tok, ".")) |
| 444 | return (tok->originalName() != "->" && isTemporary(tok->astOperand1(), library)) || |
| 445 | isTemporary(tok->astOperand2(), library); |
| 446 | if (Token::Match(tok, ",|::")) |
| 447 | return isTemporary(tok->astOperand2(), library); |
| 448 | if (tok->isCast() || (tok->isCpp() && isCPPCast(tok))) |
| 449 | return isTemporary(tok->astOperand2(), library); |
| 450 | if (findLambdaEndToken(tok) != nullptr) |
| 451 | return true; |
| 452 | if (Token::Match(tok, ".|[|++|--|%name%|%assign%")) |
| 453 | return false; |
| 454 | if (tok->isUnaryOp("*")) |
| 455 | return false; |
| 456 | if (Token::Match(tok, "&|<<|>>") && isLikelyStream(tok->astOperand1())) |
| 457 | return false; |
| 458 | if (Token::simpleMatch(tok, "?")) { |
| 459 | const Token* branchTok = tok->astOperand2(); |
| 460 | if (!branchTok->astOperand1() || !branchTok->astOperand1()->valueType()) |
| 461 | return false; |
| 462 | if (!branchTok->astOperand2()->valueType()) |
| 463 | return false; |
| 464 | return !branchTok->astOperand1()->valueType()->isTypeEqual(branchTok->astOperand2()->valueType()); |
| 465 | } |
| 466 | if (Token::Match(tok, "(|{") && tok->astOperand1() && |
| 467 | (tok->astOperand2() || Token::simpleMatch(tok->next(), ")"))) { |
| 468 | if (Token::simpleMatch(tok->astOperand1(), "typeid")) |
| 469 | return false; |
| 470 | if (tok->valueType()) { |
| 471 | if (tok->valueType()->pointer > 0) { |
| 472 | const Token* const parent = tok->astParent(); |
| 473 | if (Token::simpleMatch(parent, "&")) |
| 474 | return true; |
| 475 | if (Token::simpleMatch(parent, "return") && parent->valueType()->reference != Reference::None && |
| 476 | parent->valueType()->container && parent->valueType()->container->stdStringLike) |
| 477 | return true; |
| 478 | } |
| 479 | return tok->valueType()->reference == Reference::None && tok->valueType()->pointer == 0; |
| 480 | } |
| 481 | const Token* ftok = nullptr; |
| 482 | if (Token::simpleMatch(tok->previous(), ">") && tok->linkAt(-1)) |
| 483 | ftok = tok->linkAt(-1)->previous(); |
| 484 | else |
| 485 | ftok = tok->previous(); |
| 486 | if (!ftok) |
| 487 | return false; |
| 488 | if (const Function * f = ftok->function()) |
| 489 | return !Function::returnsReference(f, true); |
| 490 | if (ftok->type()) |
| 491 | return true; |
| 492 | if (library) { |
| 493 | const std::string& returnType = library->returnValueType(ftok); |
| 494 | return !returnType.empty() && returnType.back() != '&'; |
| 495 | } |
| 496 | return unknown; |
no test coverage detected