================ @@ -6298,10 +6304,60 @@ static bool isImmediateSinkBlock(const CFGBlock *Blk) { // at least for now, but once we have better support for exceptions, // we'd need to carefully handle the case when the throw is being // immediately caught. - if (llvm::any_of(*Blk, [](const CFGElement &Elm) { + if (llvm::any_of(*Blk, [](const CFGElement &Elm) -> bool { + if (std::optional<CFGStmt> StmtElm = Elm.getAs<CFGStmt>()) + return isa<CXXThrowExpr>(StmtElm->getStmt()); + return false; + })) + return true; + + auto HasNoReturnCall = [&](const CallExpr *CE) { + if (!CE) + return false; + + auto *FD = CE->getDirectCallee(); + + if (!FD) + return false; + + auto *CanCD = FD->getCanonicalDecl(); + auto *DefFD = CanCD->getDefinition(); + auto NoRetAttrOpt = CanCD->getAnalyzerNoReturn(); + auto NoReturn = false; + + if (!NoRetAttrOpt && DefFD && DefFD->getBody()) { + // HACK: we are gonna cache analysis result as implicit + // `analyzer_noreturn` attribute + auto *MutCD = const_cast<FunctionDecl *>(CanCD); + + // Mark function as `analyzer_noreturn(false)` to: + // * prevent infinite recursion in noreturn analysis + // * indicate that we've already analyzed(-ing) this function + // * serve as a safe default assumption (function may return) + MutCD->addAttr(AnalyzerNoReturnAttr::CreateImplicit( + CanCD->getASTContext(), false, CanCD->getLocation())); + + auto CalleeCFG = + CFG::buildCFG(DefFD, DefFD->getBody(), &DefFD->getASTContext(), {}); + + NoReturn = CalleeCFG && CalleeCFG->getEntry().isInevitablySinking(); + + // Override to `analyzer_noreturn(true)` + if (NoReturn) { + MutCD->dropAttr<AnalyzerNoReturnAttr>(); + MutCD->addAttr(AnalyzerNoReturnAttr::CreateImplicit( + CanCD->getASTContext(), NoReturn, CanCD->getLocation())); ---------------- negativ wrote:
We will drop this attribute only if we've created it before: ```cpp auto *CanCD = FD->getCanonicalDecl(); auto *DefFD = CanCD->getDefinition(); auto NoRetAttrOpt = CanCD->getAnalyzerNoReturn(); auto NoReturn = false; if (!NoRetAttrOpt && DefFD && DefFD->getBody()) { ... // Override to `analyzer_noreturn(true)` if (NoReturn) { ``` https://github.com/llvm/llvm-project/pull/146355 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits