[clang] cad0940 - [sema] enhance error handling for compound stmt body in `StmtExpr` (#113760)

via cfe-commits cfe-commits at lists.llvm.org
Tue Oct 29 23:34:23 PDT 2024


Author: Congcong Cai
Date: 2024-10-30T14:34:19+08:00
New Revision: cad09404cc804dd35d2f3b742d1d6efb6d5a9449

URL: https://github.com/llvm/llvm-project/commit/cad09404cc804dd35d2f3b742d1d6efb6d5a9449
DIFF: https://github.com/llvm/llvm-project/commit/cad09404cc804dd35d2f3b742d1d6efb6d5a9449.diff

LOG: [sema] enhance error handling for compound stmt body in `StmtExpr` (#113760)

Mark the whole StmtExpr invalid when the last statement in compound
statement is invalid.
Because the last statement need to do copy initialization, it causes
subsequent errors to simply ignore last invalid statement.

Fixed: #113468

Added: 
    clang/test/SemaCXX/gh113468.cpp

Modified: 
    clang/docs/ReleaseNotes.rst
    clang/lib/Parse/ParseStmt.cpp

Removed: 
    


################################################################################
diff  --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst
index a39ffc8366dda4..1837707b8caecb 100644
--- a/clang/docs/ReleaseNotes.rst
+++ b/clang/docs/ReleaseNotes.rst
@@ -470,6 +470,7 @@ Bug Fixes in This Version
 - The warning emitted for an unsupported register variable type now points to
   the unsupported type instead of the ``register`` keyword (#GH109776).
 - Fixed a crash when emit ctor for global variant with flexible array init  (#GH113187).
+- Fixed a crash when GNU statement expression contains invalid statement (#GH113468).
 
 Bug Fixes to Compiler Builtins
 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

diff  --git a/clang/lib/Parse/ParseStmt.cpp b/clang/lib/Parse/ParseStmt.cpp
index 7d727efb228731..6470e55e521add 100644
--- a/clang/lib/Parse/ParseStmt.cpp
+++ b/clang/lib/Parse/ParseStmt.cpp
@@ -1243,6 +1243,7 @@ StmtResult Parser::ParseCompoundStatementBody(bool isStmtExpr) {
       ParsedStmtContext::Compound |
       (isStmtExpr ? ParsedStmtContext::InStmtExpr : ParsedStmtContext());
 
+  bool LastIsError = false;
   while (!tryParseMisplacedModuleImport() && Tok.isNot(tok::r_brace) &&
          Tok.isNot(tok::eof)) {
     if (Tok.is(tok::annot_pragma_unused)) {
@@ -1299,7 +1300,15 @@ StmtResult Parser::ParseCompoundStatementBody(bool isStmtExpr) {
 
     if (R.isUsable())
       Stmts.push_back(R.get());
+    LastIsError = R.isInvalid();
   }
+  // StmtExpr needs to do copy initialization for last statement.
+  // If last statement is invalid, the last statement in `Stmts` will be
+  // incorrect. Then the whole compound statement should also be marked as
+  // invalid to prevent subsequent errors.
+  if (isStmtExpr && LastIsError && !Stmts.empty())
+    return StmtError();
+
   // Warn the user that using option `-ffp-eval-method=source` on a
   // 32-bit target and feature `sse` disabled, or using
   // `pragma clang fp eval_method=source` and feature `sse` disabled, is not

diff  --git a/clang/test/SemaCXX/gh113468.cpp b/clang/test/SemaCXX/gh113468.cpp
new file mode 100644
index 00000000000000..94551986b0efaa
--- /dev/null
+++ b/clang/test/SemaCXX/gh113468.cpp
@@ -0,0 +1,12 @@
+// RUN: %clang_cc1 -std=c++20 -fsyntax-only -verify %s
+
+constexpr int expr() {
+  if (({
+        int f;
+        f = 0;
+        if (f)
+          break; // expected-error {{'break' statement not in loop or switch statement}}
+      }))
+    return 2;
+  return 1;
+}


        


More information about the cfe-commits mailing list