[clang] 68427bc - [C++20] [Modules] Support generating in-class defined function with try-catch body (#129212)
via cfe-commits
cfe-commits at lists.llvm.org
Tue Mar 4 18:32:22 PST 2025
Author: Chuanqi Xu
Date: 2025-03-05T10:32:19+08:00
New Revision: 68427bc8d808a8f70ed345278fc498a1e0b5a8d2
URL: https://github.com/llvm/llvm-project/commit/68427bc8d808a8f70ed345278fc498a1e0b5a8d2
DIFF: https://github.com/llvm/llvm-project/commit/68427bc8d808a8f70ed345278fc498a1e0b5a8d2.diff
LOG: [C++20] [Modules] Support generating in-class defined function with try-catch body (#129212)
See the example:
```
export module func;
class C {
public:
void member() try {
} catch (...) {
}
};
```
We woudln't generate the definition for `C::member` but we should. Since
the function is non-inline in modules.
This turns out to be an oversight in parser to me. Since the try-catch
body is relatively rare, so maybe we just forgot it.
Added:
clang/test/Modules/try-func-body.cppm
Modified:
clang/lib/Parse/ParseCXXInlineMethods.cpp
Removed:
################################################################################
diff --git a/clang/lib/Parse/ParseCXXInlineMethods.cpp b/clang/lib/Parse/ParseCXXInlineMethods.cpp
index 6c01af55ef3c4..b1064eb02b907 100644
--- a/clang/lib/Parse/ParseCXXInlineMethods.cpp
+++ b/clang/lib/Parse/ParseCXXInlineMethods.cpp
@@ -17,6 +17,7 @@
#include "clang/Sema/DeclSpec.h"
#include "clang/Sema/EnterExpressionEvaluationContext.h"
#include "clang/Sema/Scope.h"
+#include "llvm/ADT/ScopeExit.h"
using namespace clang;
@@ -624,14 +625,21 @@ void Parser::ParseLexedMethodDef(LexedMethod &LM) {
Actions.ActOnStartOfFunctionDef(getCurScope(), LM.D);
- if (Tok.is(tok::kw_try)) {
- ParseFunctionTryBlock(LM.D, FnScope);
-
+ auto _ = llvm::make_scope_exit([&]() {
while (Tok.isNot(tok::eof))
ConsumeAnyToken();
if (Tok.is(tok::eof) && Tok.getEofData() == LM.D)
ConsumeAnyToken();
+
+ if (auto *FD = dyn_cast_or_null<FunctionDecl>(LM.D))
+ if (isa<CXXMethodDecl>(FD) ||
+ FD->isInIdentifierNamespace(Decl::IDNS_OrdinaryFriend))
+ Actions.ActOnFinishInlineFunctionDef(FD);
+ });
+
+ if (Tok.is(tok::kw_try)) {
+ ParseFunctionTryBlock(LM.D, FnScope);
return;
}
if (Tok.is(tok::colon)) {
@@ -641,12 +649,6 @@ void Parser::ParseLexedMethodDef(LexedMethod &LM) {
if (!Tok.is(tok::l_brace)) {
FnScope.Exit();
Actions.ActOnFinishFunctionBody(LM.D, nullptr);
-
- while (Tok.isNot(tok::eof))
- ConsumeAnyToken();
-
- if (Tok.is(tok::eof) && Tok.getEofData() == LM.D)
- ConsumeAnyToken();
return;
}
} else
@@ -660,17 +662,6 @@ void Parser::ParseLexedMethodDef(LexedMethod &LM) {
"current template being instantiated!");
ParseFunctionStatementBody(LM.D, FnScope);
-
- while (Tok.isNot(tok::eof))
- ConsumeAnyToken();
-
- if (Tok.is(tok::eof) && Tok.getEofData() == LM.D)
- ConsumeAnyToken();
-
- if (auto *FD = dyn_cast_or_null<FunctionDecl>(LM.D))
- if (isa<CXXMethodDecl>(FD) ||
- FD->isInIdentifierNamespace(Decl::IDNS_OrdinaryFriend))
- Actions.ActOnFinishInlineFunctionDef(FD);
}
/// ParseLexedMemberInitializers - We finished parsing the member specification
diff --git a/clang/test/Modules/try-func-body.cppm b/clang/test/Modules/try-func-body.cppm
new file mode 100644
index 0000000000000..379f5e47f4f8e
--- /dev/null
+++ b/clang/test/Modules/try-func-body.cppm
@@ -0,0 +1,13 @@
+// RUN: %clang_cc1 -std=c++20 %s -fexceptions -fcxx-exceptions -emit-llvm -triple %itanium_abi_triple -o - | FileCheck %s
+
+export module func;
+class C {
+public:
+ void member() try {
+
+ } catch (...) {
+
+ }
+};
+
+// CHECK: define {{.*}}@_ZNW4func1C6memberEv
More information about the cfe-commits
mailing list