diff --git a/clang/lib/Sema/SemaExpr.cpp b/clang/lib/Sema/SemaExpr.cpp --- a/clang/lib/Sema/SemaExpr.cpp +++ b/clang/lib/Sema/SemaExpr.cpp @@ -15745,7 +15745,9 @@ if (hasAnyUnrecoverableErrorsInThisFunction()) DiscardCleanupsInEvaluationContext(); - assert(!Cleanup.exprNeedsCleanups() && + // Cleanups may be needed if temporaries are created in an AsmStmt. + assert((!Cleanup.exprNeedsCleanups() || + (!Compound->body_empty() && isa(Compound->body_front()))) && "cleanups within StmtExpr not correctly bound!"); PopExpressionEvaluationContext(); diff --git a/clang/test/SemaTemplate/instantiate-expr-1.cpp b/clang/test/SemaTemplate/instantiate-expr-1.cpp --- a/clang/test/SemaTemplate/instantiate-expr-1.cpp +++ b/clang/test/SemaTemplate/instantiate-expr-1.cpp @@ -190,3 +190,19 @@ test_asm_tied(1.f); // expected-note {{instantiation of}} } } + +namespace TestAsmCleanup { +struct S { + operator int() const { return 1; } + ~S(); +}; + +template +void foo() { + __asm__ __volatile__("%[i]" + : + : [i] "r"(-S())); +} + +void test() { foo(); } +} // namespace TestAsmCleanup