[llvm-branch-commits] [clang] [CIR][CodeGen][NFC] Extract the EHPersonality struct into CodeGenUtils (PR #223420)

Henrich Lauko via llvm-branch-commits llvm-branch-commits at lists.llvm.org
Tue Sep 29 04:22:13 PDT 2026


https://github.com/xlauko updated https://github.com/llvm/llvm-project/pull/223420

>From 07e57d771f81537a941d600c21504b90f9fa2e21 Mon Sep 17 00:00:00 2001
From: Henrich Lauko <hlauko at nvidia.com>
Date: Mon, 14 Sep 2026 13:17:32 +0000
Subject: [PATCH] [CIR][CodeGen][NFC] Extract the EHPersonality struct into
 CodeGenUtils

Deduplicates the `EHPersonality` struct and its personality constants between
CIR and classic CodeGen into `EHPersonality.h`. The `EHPersonality::get`
factories become `getEHPersonality` overloads, since the shared struct cannot
name either CodeGenModule.
---
 .../clang/CodeGenUtils/EHPersonality.h        | 65 +++++++++++++++++
 clang/lib/CIR/CodeGen/CIRGenCleanup.h         | 54 +++-----------
 clang/lib/CIR/CodeGen/CIRGenException.cpp     | 54 +++-----------
 clang/lib/CodeGen/CGCall.cpp                  |  2 +-
 clang/lib/CodeGen/CGCleanup.cpp               |  2 +-
 clang/lib/CodeGen/CGCleanup.h                 | 57 +++------------
 clang/lib/CodeGen/CGException.cpp             | 70 +++++--------------
 clang/lib/CodeGen/CGObjCRuntime.cpp           |  6 +-
 clang/lib/CodeGen/ItaniumCXXABI.cpp           |  2 +-
 clang/lib/CodeGenUtils/CMakeLists.txt         |  1 +
 clang/lib/CodeGenUtils/EHPersonality.cpp      | 49 +++++++++++++
 11 files changed, 171 insertions(+), 191 deletions(-)
 create mode 100644 clang/include/clang/CodeGenUtils/EHPersonality.h
 create mode 100644 clang/lib/CodeGenUtils/EHPersonality.cpp

diff --git a/clang/include/clang/CodeGenUtils/EHPersonality.h b/clang/include/clang/CodeGenUtils/EHPersonality.h
new file mode 100644
index 0000000000000..ab604c801e07e
--- /dev/null
+++ b/clang/include/clang/CodeGenUtils/EHPersonality.h
@@ -0,0 +1,65 @@
+//===--- EHPersonality.h - Shared EH personality descriptions ---*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+//
+// This file describes the exception personality functions that both classic
+// CodeGen and CIR CodeGen can select for a function.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_CLANG_CODEGENUTILS_EHPERSONALITY_H
+#define LLVM_CLANG_CODEGENUTILS_EHPERSONALITY_H
+
+namespace clang::CodeGenUtils {
+
+/// The exceptions personality for a function.
+struct EHPersonality {
+  const char *PersonalityFn = nullptr;
+
+  // If this is non-null, this personality requires a non-standard
+  // function for rethrowing an exception after a catchall cleanup.
+  // This function must have prototype void(void*).
+  const char *CatchallRethrowFn = nullptr;
+
+  static const EHPersonality GNU_C;
+  static const EHPersonality GNU_C_SJLJ;
+  static const EHPersonality GNU_C_SEH;
+  static const EHPersonality GNU_ObjC;
+  static const EHPersonality GNU_ObjC_SJLJ;
+  static const EHPersonality GNU_ObjC_SEH;
+  static const EHPersonality GNUstep_ObjC;
+  static const EHPersonality GNU_ObjCXX;
+  static const EHPersonality NeXT_ObjC;
+  static const EHPersonality GNU_CPlusPlus;
+  static const EHPersonality GNU_CPlusPlus_SJLJ;
+  static const EHPersonality GNU_CPlusPlus_SEH;
+  static const EHPersonality MSVC_except_handler;
+  static const EHPersonality MSVC_C_specific_handler;
+  static const EHPersonality MSVC_CxxFrameHandler3;
+  static const EHPersonality GNU_Wasm_CPlusPlus;
+  static const EHPersonality XL_CPlusPlus;
+  static const EHPersonality ZOS_CPlusPlus;
+
+  /// Does this personality use landingpads or the family of pad instructions
+  /// designed to form funclets?
+  bool usesFuncletPads() const {
+    return isMSVCPersonality() || isWasmPersonality();
+  }
+
+  bool isMSVCPersonality() const {
+    return this == &MSVC_except_handler || this == &MSVC_C_specific_handler ||
+           this == &MSVC_CxxFrameHandler3;
+  }
+
+  bool isWasmPersonality() const { return this == &GNU_Wasm_CPlusPlus; }
+
+  bool isMSVCXXPersonality() const { return this == &MSVC_CxxFrameHandler3; }
+};
+
+} // namespace clang::CodeGenUtils
+
+#endif // LLVM_CLANG_CODEGENUTILS_EHPERSONALITY_H
diff --git a/clang/lib/CIR/CodeGen/CIRGenCleanup.h b/clang/lib/CIR/CodeGen/CIRGenCleanup.h
index 46f1382bced7d..0f761b69c02d1 100644
--- a/clang/lib/CIR/CodeGen/CIRGenCleanup.h
+++ b/clang/lib/CIR/CodeGen/CIRGenCleanup.h
@@ -19,6 +19,7 @@
 #include "EHScopeStack.h"
 #include "mlir/IR/Value.h"
 #include "clang/AST/StmtCXX.h"
+#include "clang/CodeGenUtils/EHPersonality.h"
 
 namespace clang::CIRGen {
 
@@ -251,53 +252,16 @@ EHScopeStack::find(stable_iterator savePoint) const {
   return iterator(endOfBuffer - savePoint.size);
 }
 
-/// The exceptions personality for a function.
-struct EHPersonality {
-  const char *personalityFn = nullptr;
-
-  // If this is non-null, this personality requires a non-standard
-  // function for rethrowing an exception after a catchall cleanup.
-  // This function must have prototype void(void*).
-  const char *catchallRethrowFn = nullptr;
-
-  static const EHPersonality &get(CIRGenModule &cgm,
-                                  const clang::FunctionDecl *fd);
-  static const EHPersonality &get(CIRGenFunction &cgf);
-
-  static const EHPersonality GNU_C;
-  static const EHPersonality GNU_C_SJLJ;
-  static const EHPersonality GNU_C_SEH;
-  static const EHPersonality GNU_ObjC;
-  static const EHPersonality GNU_ObjC_SJLJ;
-  static const EHPersonality GNU_ObjC_SEH;
-  static const EHPersonality GNUstep_ObjC;
-  static const EHPersonality GNU_ObjCXX;
-  static const EHPersonality NeXT_ObjC;
-  static const EHPersonality GNU_CPlusPlus;
-  static const EHPersonality GNU_CPlusPlus_SJLJ;
-  static const EHPersonality GNU_CPlusPlus_SEH;
-  static const EHPersonality MSVC_except_handler;
-  static const EHPersonality MSVC_C_specific_handler;
-  static const EHPersonality MSVC_CxxFrameHandler3;
-  static const EHPersonality GNU_Wasm_CPlusPlus;
-  static const EHPersonality XL_CPlusPlus;
-  static const EHPersonality ZOS_CPlusPlus;
-
-  /// Does this personality use landingpads or the family of pad instructions
-  /// designed to form funclets?
-  bool usesFuncletPads() const {
-    return isMSVCPersonality() || isWasmPersonality();
-  }
-
-  bool isMSVCPersonality() const {
-    return this == &MSVC_except_handler || this == &MSVC_C_specific_handler ||
-           this == &MSVC_CxxFrameHandler3;
-  }
+using CodeGenUtils::EHPersonality;
 
-  bool isWasmPersonality() const { return this == &GNU_Wasm_CPlusPlus; }
+/// Selects the personality function to use for \p fd, or for the translation
+/// unit as a whole when \p fd is null.
+const EHPersonality &getEHPersonality(CIRGenModule &cgm,
+                                      const clang::FunctionDecl *fd);
 
-  bool isMSVCXXPersonality() const { return this == &MSVC_CxxFrameHandler3; }
-};
+/// Selects the personality function to use for the function currently being
+/// emitted.
+const EHPersonality &getEHPersonality(CIRGenFunction &cgf);
 
 } // namespace clang::CIRGen
 #endif // CLANG_LIB_CIR_CODEGEN_CIRGENCLEANUP_H
diff --git a/clang/lib/CIR/CodeGen/CIRGenException.cpp b/clang/lib/CIR/CodeGen/CIRGenException.cpp
index 2c2fa83e661d3..bd3e2014756e6 100644
--- a/clang/lib/CIR/CodeGen/CIRGenException.cpp
+++ b/clang/lib/CIR/CodeGen/CIRGenException.cpp
@@ -22,42 +22,6 @@
 using namespace clang;
 using namespace clang::CIRGen;
 
-const EHPersonality EHPersonality::GNU_C = {"__gcc_personality_v0", nullptr};
-const EHPersonality EHPersonality::GNU_C_SJLJ = {"__gcc_personality_sj0",
-                                                 nullptr};
-const EHPersonality EHPersonality::GNU_C_SEH = {"__gcc_personality_seh0",
-                                                nullptr};
-const EHPersonality EHPersonality::NeXT_ObjC = {"__objc_personality_v0",
-                                                nullptr};
-const EHPersonality EHPersonality::GNU_CPlusPlus = {"__gxx_personality_v0",
-                                                    nullptr};
-const EHPersonality EHPersonality::GNU_CPlusPlus_SJLJ = {
-    "__gxx_personality_sj0", nullptr};
-const EHPersonality EHPersonality::GNU_CPlusPlus_SEH = {
-    "__gxx_personality_seh0", nullptr};
-const EHPersonality EHPersonality::GNU_ObjC = {"__gnu_objc_personality_v0",
-                                               "objc_exception_throw"};
-const EHPersonality EHPersonality::GNU_ObjC_SJLJ = {
-    "__gnu_objc_personality_sj0", "objc_exception_throw"};
-const EHPersonality EHPersonality::GNU_ObjC_SEH = {
-    "__gnu_objc_personality_seh0", "objc_exception_throw"};
-const EHPersonality EHPersonality::GNU_ObjCXX = {
-    "__gnustep_objcxx_personality_v0", nullptr};
-const EHPersonality EHPersonality::GNUstep_ObjC = {
-    "__gnustep_objc_personality_v0", nullptr};
-const EHPersonality EHPersonality::MSVC_except_handler = {"_except_handler3",
-                                                          nullptr};
-const EHPersonality EHPersonality::MSVC_C_specific_handler = {
-    "__C_specific_handler", nullptr};
-const EHPersonality EHPersonality::MSVC_CxxFrameHandler3 = {
-    "__CxxFrameHandler3", nullptr};
-const EHPersonality EHPersonality::GNU_Wasm_CPlusPlus = {
-    "__gxx_wasm_personality_v0", nullptr};
-const EHPersonality EHPersonality::XL_CPlusPlus = {"__xlcxx_personality_v1",
-                                                   nullptr};
-const EHPersonality EHPersonality::ZOS_CPlusPlus = {"__zos_cxx_personality_v2",
-                                                    nullptr};
-
 static const EHPersonality &getCPersonality(const TargetInfo &target,
                                             const CodeGenOptions &cgOpts) {
   const llvm::Triple &triple = target.getTriple();
@@ -159,8 +123,10 @@ static const EHPersonality &getSEHPersonalityMSVC(const llvm::Triple &triple) {
              : EHPersonality::MSVC_C_specific_handler;
 }
 
-const EHPersonality &EHPersonality::get(CIRGenModule &cgm,
-                                        const FunctionDecl *fd) {
+namespace clang::CIRGen {
+
+const EHPersonality &getEHPersonality(CIRGenModule &cgm,
+                                      const FunctionDecl *fd) {
   const llvm::Triple &triple = cgm.getTarget().getTriple();
   const LangOptions &langOpts = cgm.getLangOpts();
   const CodeGenOptions &cgOpts = cgm.getCodeGenOpts();
@@ -178,15 +144,17 @@ const EHPersonality &EHPersonality::get(CIRGenModule &cgm,
                             : getCPersonality(target, cgOpts);
 }
 
-const EHPersonality &EHPersonality::get(CIRGenFunction &cgf) {
+const EHPersonality &getEHPersonality(CIRGenFunction &cgf) {
   const auto *fg = cgf.curCodeDecl;
   // For outlined finallys and filters, use the SEH personality in case they
   // contain more SEH. This mostly only affects finallys. Filters could
   // hypothetically use gnu statement expressions to sneak in nested SEH.
   fg = fg ? fg : cgf.curSEHParent.getDecl();
-  return get(cgf.cgm, dyn_cast_or_null<FunctionDecl>(fg));
+  return getEHPersonality(cgf.cgm, dyn_cast_or_null<FunctionDecl>(fg));
 }
 
+} // namespace clang::CIRGen
+
 static llvm::StringRef getPersonalityFn(CIRGenModule &cgm,
                                         const EHPersonality &personality) {
   // Create the personality function type: i32 (...)
@@ -194,7 +162,7 @@ static llvm::StringRef getPersonalityFn(CIRGenModule &cgm,
   auto funcTy = cir::FuncType::get({}, i32Ty, /*isVarArg=*/true);
 
   cir::FuncOp personalityFn = cgm.createRuntimeFunction(
-      funcTy, personality.personalityFn, {}, /*isLocal=*/true);
+      funcTy, personality.PersonalityFn, {}, /*isLocal=*/true);
 
   return personalityFn.getSymName();
 }
@@ -281,7 +249,7 @@ void CIRGenFunction::emitStartEHSpec(const Decl *d) {
 
   cir::FuncOp funcOp = mlir::cast<cir::FuncOp>(curFn);
   if (!funcOp.getPersonality())
-    funcOp.setPersonality(getPersonalityFn(cgm, EHPersonality::get(*this)));
+    funcOp.setPersonality(getPersonalityFn(cgm, getEHPersonality(*this)));
 
   bool emptyFilter = permittedTypes.empty();
   ehSpecTryOp = cir::TryOp::create(
@@ -657,7 +625,7 @@ CIRGenFunction::emitCXXTryStmt(const CXXTryStmt &s,
   // Set personality function if not already set
   auto funcOp = mlir::cast<cir::FuncOp>(curFn);
   if (!funcOp.getPersonality())
-    funcOp.setPersonality(getPersonalityFn(cgm, EHPersonality::get(*this)));
+    funcOp.setPersonality(getPersonalityFn(cgm, getEHPersonality(*this)));
 
   mlir::OpBuilder::InsertionGuard guard(builder);
   builder.restoreInsertionPoint(scopeIP);
diff --git a/clang/lib/CodeGen/CGCall.cpp b/clang/lib/CodeGen/CGCall.cpp
index 2193a89203f29..c294621b28d1d 100644
--- a/clang/lib/CodeGen/CGCall.cpp
+++ b/clang/lib/CodeGen/CGCall.cpp
@@ -6322,7 +6322,7 @@ RValue CodeGenFunction::EmitCall(const CGFunctionInfo &CallInfo,
     // SEH cares about asynchronous exceptions, so everything can "throw."
     CannotThrow = false;
   } else if (isCleanupPadScope() &&
-             EHPersonality::get(*this).isMSVCXXPersonality()) {
+             getEHPersonality(*this).isMSVCXXPersonality()) {
     // The MSVC++ personality will implicitly terminate the program if an
     // exception is thrown during a cleanup outside of a try/catch.
     // We don't need to model anything in IR to get this behavior.
diff --git a/clang/lib/CodeGen/CGCleanup.cpp b/clang/lib/CodeGen/CGCleanup.cpp
index 9d279bebe5e0d..3cac452a5f215 100644
--- a/clang/lib/CodeGen/CGCleanup.cpp
+++ b/clang/lib/CodeGen/CGCleanup.cpp
@@ -1049,7 +1049,7 @@ void CodeGenFunction::PopCleanupBlock(bool FallthroughIsBranchThrough,
     SaveAndRestore RestoreCurrentFuncletPad(CurrentFuncletPad);
     llvm::CleanupPadInst *CPI = nullptr;
 
-    const EHPersonality &Personality = EHPersonality::get(*this);
+    const EHPersonality &Personality = getEHPersonality(*this);
     if (Personality.usesFuncletPads()) {
       llvm::Value *ParentPad = CurrentFuncletPad;
       if (!ParentPad)
diff --git a/clang/lib/CodeGen/CGCleanup.h b/clang/lib/CodeGen/CGCleanup.h
index 375dbbbb19709..fd8206fbccfe1 100644
--- a/clang/lib/CodeGen/CGCleanup.h
+++ b/clang/lib/CodeGen/CGCleanup.h
@@ -16,6 +16,7 @@
 #include "EHScopeStack.h"
 
 #include "Address.h"
+#include "clang/CodeGenUtils/EHPersonality.h"
 #include "llvm/ADT/STLExtras.h"
 #include "llvm/ADT/SetVector.h"
 #include "llvm/ADT/SmallPtrSet.h"
@@ -674,52 +675,16 @@ EHScopeStack::stabilize(iterator ir) const {
   return stable_iterator(EndOfBuffer - ir.Ptr);
 }
 
-/// The exceptions personality for a function.
-struct EHPersonality {
-  const char *PersonalityFn;
-
-  // If this is non-null, this personality requires a non-standard
-  // function for rethrowing an exception after a catchall cleanup.
-  // This function must have prototype void(void*).
-  const char *CatchallRethrowFn;
-
-  static const EHPersonality &get(CodeGenModule &CGM, const FunctionDecl *FD);
-  static const EHPersonality &get(CodeGenFunction &CGF);
-
-  static const EHPersonality GNU_C;
-  static const EHPersonality GNU_C_SJLJ;
-  static const EHPersonality GNU_C_SEH;
-  static const EHPersonality GNU_ObjC;
-  static const EHPersonality GNU_ObjC_SJLJ;
-  static const EHPersonality GNU_ObjC_SEH;
-  static const EHPersonality GNUstep_ObjC;
-  static const EHPersonality GNU_ObjCXX;
-  static const EHPersonality NeXT_ObjC;
-  static const EHPersonality GNU_CPlusPlus;
-  static const EHPersonality GNU_CPlusPlus_SJLJ;
-  static const EHPersonality GNU_CPlusPlus_SEH;
-  static const EHPersonality MSVC_except_handler;
-  static const EHPersonality MSVC_C_specific_handler;
-  static const EHPersonality MSVC_CxxFrameHandler3;
-  static const EHPersonality GNU_Wasm_CPlusPlus;
-  static const EHPersonality XL_CPlusPlus;
-  static const EHPersonality ZOS_CPlusPlus;
-
-  /// Does this personality use landingpads or the family of pad instructions
-  /// designed to form funclets?
-  bool usesFuncletPads() const {
-    return isMSVCPersonality() || isWasmPersonality();
-  }
-
-  bool isMSVCPersonality() const {
-    return this == &MSVC_except_handler || this == &MSVC_C_specific_handler ||
-           this == &MSVC_CxxFrameHandler3;
-  }
-
-  bool isWasmPersonality() const { return this == &GNU_Wasm_CPlusPlus; }
-
-  bool isMSVCXXPersonality() const { return this == &MSVC_CxxFrameHandler3; }
-};
+using CodeGenUtils::EHPersonality;
+
+/// Selects the personality function to use for \p FD, or for the translation
+/// unit as a whole when \p FD is null.
+const EHPersonality &getEHPersonality(CodeGenModule &CGM,
+                                      const FunctionDecl *FD);
+
+/// Selects the personality function to use for the function currently being
+/// emitted.
+const EHPersonality &getEHPersonality(CodeGenFunction &CGF);
 }
 }
 
diff --git a/clang/lib/CodeGen/CGException.cpp b/clang/lib/CodeGen/CGException.cpp
index f06edde9739b4..f8b4cbc516a40 100644
--- a/clang/lib/CodeGen/CGException.cpp
+++ b/clang/lib/CodeGen/CGException.cpp
@@ -82,42 +82,6 @@ static llvm::FunctionCallee getCatchallRethrowFn(CodeGenModule &CGM,
   return CGM.CreateRuntimeFunction(FTy, Name);
 }
 
-const EHPersonality EHPersonality::GNU_C = { "__gcc_personality_v0", nullptr };
-const EHPersonality
-EHPersonality::GNU_C_SJLJ = { "__gcc_personality_sj0", nullptr };
-const EHPersonality
-EHPersonality::GNU_C_SEH = { "__gcc_personality_seh0", nullptr };
-const EHPersonality
-EHPersonality::NeXT_ObjC = { "__objc_personality_v0", nullptr };
-const EHPersonality
-EHPersonality::GNU_CPlusPlus = { "__gxx_personality_v0", nullptr };
-const EHPersonality
-EHPersonality::GNU_CPlusPlus_SJLJ = { "__gxx_personality_sj0", nullptr };
-const EHPersonality
-EHPersonality::GNU_CPlusPlus_SEH = { "__gxx_personality_seh0", nullptr };
-const EHPersonality
-EHPersonality::GNU_ObjC = {"__gnu_objc_personality_v0", "objc_exception_throw"};
-const EHPersonality
-EHPersonality::GNU_ObjC_SJLJ = {"__gnu_objc_personality_sj0", "objc_exception_throw"};
-const EHPersonality
-EHPersonality::GNU_ObjC_SEH = {"__gnu_objc_personality_seh0", "objc_exception_throw"};
-const EHPersonality
-EHPersonality::GNU_ObjCXX = { "__gnustep_objcxx_personality_v0", nullptr };
-const EHPersonality
-EHPersonality::GNUstep_ObjC = { "__gnustep_objc_personality_v0", nullptr };
-const EHPersonality
-EHPersonality::MSVC_except_handler = { "_except_handler3", nullptr };
-const EHPersonality
-EHPersonality::MSVC_C_specific_handler = { "__C_specific_handler", nullptr };
-const EHPersonality
-EHPersonality::MSVC_CxxFrameHandler3 = { "__CxxFrameHandler3", nullptr };
-const EHPersonality
-EHPersonality::GNU_Wasm_CPlusPlus = { "__gxx_wasm_personality_v0", nullptr };
-const EHPersonality EHPersonality::XL_CPlusPlus = {"__xlcxx_personality_v1",
-                                                   nullptr};
-const EHPersonality EHPersonality::ZOS_CPlusPlus = {"__zos_cxx_personality_v2",
-                                                    nullptr};
-
 static const EHPersonality &getCPersonality(const TargetInfo &Target,
                                             const CodeGenOptions &CGOpts) {
   const llvm::Triple &T = Target.getTriple();
@@ -230,8 +194,10 @@ static const EHPersonality &getSEHPersonalityMSVC(const llvm::Triple &T) {
   return EHPersonality::MSVC_C_specific_handler;
 }
 
-const EHPersonality &EHPersonality::get(CodeGenModule &CGM,
-                                        const FunctionDecl *FD) {
+namespace clang::CodeGen {
+
+const EHPersonality &getEHPersonality(CodeGenModule &CGM,
+                                      const FunctionDecl *FD) {
   const llvm::Triple &T = CGM.getTarget().getTriple();
   const CodeGenOptions &CGOpts = CGM.getCodeGenOpts();
   const LangOptions &L = CGM.getLangOpts();
@@ -248,15 +214,17 @@ const EHPersonality &EHPersonality::get(CodeGenModule &CGM,
                      : getCPersonality(Target, CGOpts);
 }
 
-const EHPersonality &EHPersonality::get(CodeGenFunction &CGF) {
+const EHPersonality &getEHPersonality(CodeGenFunction &CGF) {
   const auto *FD = CGF.CurCodeDecl;
   // For outlined finallys and filters, use the SEH personality in case they
   // contain more SEH. This mostly only affects finallys. Filters could
   // hypothetically use gnu statement expressions to sneak in nested SEH.
   FD = FD ? FD : CGF.CurSEHParent.getDecl();
-  return get(CGF.CGM, dyn_cast_or_null<FunctionDecl>(FD));
+  return getEHPersonality(CGF.CGM, dyn_cast_or_null<FunctionDecl>(FD));
 }
 
+} // namespace clang::CodeGen
+
 static llvm::FunctionCallee getPersonalityFn(CodeGenModule &CGM,
                                              const EHPersonality &Personality) {
   llvm::FunctionType *FTy;
@@ -346,7 +314,7 @@ void CodeGenModule::SimplifyPersonality() {
   if (!LangOpts.ObjCRuntime.isNeXTFamily())
     return;
 
-  const EHPersonality &ObjCXX = EHPersonality::get(*this, /*FD=*/nullptr);
+  const EHPersonality &ObjCXX = getEHPersonality(*this, /*FD=*/nullptr);
   const EHPersonality &CXX = getCXXPersonality(getTarget(), CodeGenOpts);
   if (&ObjCXX == &CXX)
     return;
@@ -676,7 +644,7 @@ void CodeGenFunction::EnterCXXTryStmt(const CXXTryStmt &S, bool IsFnTryBlock) {
 
 llvm::BasicBlock *
 CodeGenFunction::getEHDispatchBlock(EHScopeStack::stable_iterator si) {
-  if (EHPersonality::get(*this).usesFuncletPads())
+  if (getEHPersonality(*this).usesFuncletPads())
     return getFuncletEHDispatchBlock(si);
 
   // The dispatch block for the end of the scope chain is a block that
@@ -802,7 +770,7 @@ llvm::BasicBlock *CodeGenFunction::getInvokeDestImpl() {
   llvm::BasicBlock *LP = EHStack.begin()->getCachedLandingPad();
   if (LP) return LP;
 
-  const EHPersonality &Personality = EHPersonality::get(*this);
+  const EHPersonality &Personality = getEHPersonality(*this);
 
   if (!CurFn->hasPersonalityFn())
     CurFn->setPersonalityFn(getOpaquePersonalityFn(CGM, Personality));
@@ -995,7 +963,7 @@ static void emitCatchPadBlock(CodeGenFunction &CGF, EHCatchScope &CatchScope) {
 
     CGF.Builder.SetInsertPoint(Handler.Block);
 
-    if (EHPersonality::get(CGF).isMSVCXXPersonality()) {
+    if (getEHPersonality(CGF).isMSVCXXPersonality()) {
       CGF.Builder.CreateCatchPad(
           CatchSwitch, {TypeInfo.RTTI, CGF.Builder.getInt32(TypeInfo.Flags),
                         llvm::Constant::getNullValue(CGF.VoidPtrTy)});
@@ -1122,9 +1090,9 @@ static void emitWasmCatchPadBlock(CodeGenFunction &CGF,
 /// It is an invariant that the dispatch block already exists.
 static void emitCatchDispatchBlock(CodeGenFunction &CGF,
                                    EHCatchScope &catchScope) {
-  if (EHPersonality::get(CGF).isWasmPersonality())
+  if (getEHPersonality(CGF).isWasmPersonality())
     return emitWasmCatchPadBlock(CGF, catchScope);
-  if (EHPersonality::get(CGF).usesFuncletPads())
+  if (getEHPersonality(CGF).usesFuncletPads())
     return emitCatchPadBlock(CGF, catchScope);
 
   llvm::BasicBlock *dispatchBlock = catchScope.getCachedEHDispatchBlock();
@@ -1269,7 +1237,7 @@ void CodeGenFunction::ExitCXXTryStmt(const CXXTryStmt &S, bool IsFnTryBlock) {
   // each catch handler.
   SaveAndRestore RestoreCurrentFuncletPad(CurrentFuncletPad);
   llvm::BasicBlock *WasmCatchStartBlock = nullptr;
-  if (EHPersonality::get(*this).isWasmPersonality()) {
+  if (getEHPersonality(*this).isWasmPersonality()) {
     auto *CatchSwitch =
         cast<llvm::CatchSwitchInst>(DispatchBlock->getFirstNonPHIIt());
     WasmCatchStartBlock = CatchSwitch->hasUnwindDest()
@@ -1333,7 +1301,7 @@ void CodeGenFunction::ExitCXXTryStmt(const CXXTryStmt &S, bool IsFnTryBlock) {
       Builder.CreateBr(ContBB);
   }
 
-  if (EHPersonality::get(*this).isWasmPersonality() && !HasCatchAll) {
+  if (getEHPersonality(*this).isWasmPersonality() && !HasCatchAll) {
     WasmEmitFallthroughRethrow(WasmCatchStartBlock);
   }
 
@@ -1543,7 +1511,7 @@ llvm::BasicBlock *CodeGenFunction::getTerminateLandingPad() {
   Builder.SetInsertPoint(TerminateLandingPad);
 
   // Tell the backend that this is a landing pad.
-  const EHPersonality &Personality = EHPersonality::get(*this);
+  const EHPersonality &Personality = getEHPersonality(*this);
 
   if (!CurFn->hasPersonalityFn())
     CurFn->setPersonalityFn(getOpaquePersonalityFn(CGM, Personality));
@@ -1591,7 +1559,7 @@ llvm::BasicBlock *CodeGenFunction::getTerminateHandler() {
 }
 
 llvm::BasicBlock *CodeGenFunction::getTerminateFunclet() {
-  assert(EHPersonality::get(*this).usesFuncletPads() &&
+  assert(getEHPersonality(*this).usesFuncletPads() &&
          "use getTerminateLandingPad for non-funclet EH");
 
   llvm::BasicBlock *&TerminateFunclet = TerminateFunclets[CurrentFuncletPad];
@@ -1634,7 +1602,7 @@ llvm::BasicBlock *CodeGenFunction::getEHResumeBlock(bool isCleanup) {
   EHResumeBlock = createBasicBlock("eh.resume");
   Builder.SetInsertPoint(EHResumeBlock);
 
-  const EHPersonality &Personality = EHPersonality::get(*this);
+  const EHPersonality &Personality = getEHPersonality(*this);
 
   // This can always be a call because we necessarily didn't find
   // anything on the EH stack which needs our help.
diff --git a/clang/lib/CodeGen/CGObjCRuntime.cpp b/clang/lib/CodeGen/CGObjCRuntime.cpp
index 3935987144756..3a009a1b248d2 100644
--- a/clang/lib/CodeGen/CGObjCRuntime.cpp
+++ b/clang/lib/CodeGen/CGObjCRuntime.cpp
@@ -150,9 +150,9 @@ void CGObjCRuntime::EmitTryCatchStmt(CodeGenFunction &CGF,
   if (S.getNumCatchStmts())
     Cont = CGF.getJumpDestInCurrentScope("eh.cont");
 
-  bool useFunclets = EHPersonality::get(CGF).usesFuncletPads();
-  bool IsWasm = EHPersonality::get(CGF).isWasmPersonality();
-  bool IsMSVC = EHPersonality::get(CGF).isMSVCPersonality();
+  bool useFunclets = getEHPersonality(CGF).usesFuncletPads();
+  bool IsWasm = getEHPersonality(CGF).isWasmPersonality();
+  bool IsMSVC = getEHPersonality(CGF).isMSVCPersonality();
 
   CodeGenFunction::FinallyInfo FinallyInfo;
   if (const ObjCAtFinallyStmt *Finally = S.getFinallyStmt()) {
diff --git a/clang/lib/CodeGen/ItaniumCXXABI.cpp b/clang/lib/CodeGen/ItaniumCXXABI.cpp
index 754511e6a7d41..6dbf3fbbb0b12 100644
--- a/clang/lib/CodeGen/ItaniumCXXABI.cpp
+++ b/clang/lib/CodeGen/ItaniumCXXABI.cpp
@@ -5266,7 +5266,7 @@ WebAssemblyCXXABI::emitTerminateForUnexpectedException(CodeGenFunction &CGF,
   // and call __clang_call_terminate only in Emscripten EH.
   // TODO Consider code transformation that makes calling __clang_call_terminate
   // in Wasm EH possible.
-  if (Exn && !EHPersonality::get(CGF).isWasmPersonality()) {
+  if (Exn && !getEHPersonality(CGF).isWasmPersonality()) {
     assert(CGF.CGM.getLangOpts().CPlusPlus);
     return CGF.EmitNounwindRuntimeCall(getClangCallTerminateFn(CGF.CGM), Exn);
   }
diff --git a/clang/lib/CodeGenUtils/CMakeLists.txt b/clang/lib/CodeGenUtils/CMakeLists.txt
index 804ed682305ca..5839e8f2e1fe5 100644
--- a/clang/lib/CodeGenUtils/CMakeLists.txt
+++ b/clang/lib/CodeGenUtils/CMakeLists.txt
@@ -6,6 +6,7 @@ add_clang_library(clangCodeGenUtils
   CallUtils.cpp
   ClassUtils.cpp
   CodeGenUtils.cpp
+  EHPersonality.cpp
   ExprUtils.cpp
   FunctionUtils.cpp
   ItaniumCXXABIUtils.cpp
diff --git a/clang/lib/CodeGenUtils/EHPersonality.cpp b/clang/lib/CodeGenUtils/EHPersonality.cpp
new file mode 100644
index 0000000000000..ee9fe010c98a7
--- /dev/null
+++ b/clang/lib/CodeGenUtils/EHPersonality.cpp
@@ -0,0 +1,49 @@
+//===--- EHPersonality.cpp - Shared EH personality descriptions -----------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "clang/CodeGenUtils/EHPersonality.h"
+
+namespace clang::CodeGenUtils {
+
+const EHPersonality EHPersonality::GNU_C = {"__gcc_personality_v0", nullptr};
+const EHPersonality EHPersonality::GNU_C_SJLJ = {"__gcc_personality_sj0",
+                                                 nullptr};
+const EHPersonality EHPersonality::GNU_C_SEH = {"__gcc_personality_seh0",
+                                                nullptr};
+const EHPersonality EHPersonality::NeXT_ObjC = {"__objc_personality_v0",
+                                                nullptr};
+const EHPersonality EHPersonality::GNU_CPlusPlus = {"__gxx_personality_v0",
+                                                    nullptr};
+const EHPersonality EHPersonality::GNU_CPlusPlus_SJLJ = {
+    "__gxx_personality_sj0", nullptr};
+const EHPersonality EHPersonality::GNU_CPlusPlus_SEH = {
+    "__gxx_personality_seh0", nullptr};
+const EHPersonality EHPersonality::GNU_ObjC = {"__gnu_objc_personality_v0",
+                                               "objc_exception_throw"};
+const EHPersonality EHPersonality::GNU_ObjC_SJLJ = {
+    "__gnu_objc_personality_sj0", "objc_exception_throw"};
+const EHPersonality EHPersonality::GNU_ObjC_SEH = {
+    "__gnu_objc_personality_seh0", "objc_exception_throw"};
+const EHPersonality EHPersonality::GNU_ObjCXX = {
+    "__gnustep_objcxx_personality_v0", nullptr};
+const EHPersonality EHPersonality::GNUstep_ObjC = {
+    "__gnustep_objc_personality_v0", nullptr};
+const EHPersonality EHPersonality::MSVC_except_handler = {"_except_handler3",
+                                                          nullptr};
+const EHPersonality EHPersonality::MSVC_C_specific_handler = {
+    "__C_specific_handler", nullptr};
+const EHPersonality EHPersonality::MSVC_CxxFrameHandler3 = {
+    "__CxxFrameHandler3", nullptr};
+const EHPersonality EHPersonality::GNU_Wasm_CPlusPlus = {
+    "__gxx_wasm_personality_v0", nullptr};
+const EHPersonality EHPersonality::XL_CPlusPlus = {"__xlcxx_personality_v1",
+                                                   nullptr};
+const EHPersonality EHPersonality::ZOS_CPlusPlus = {"__zos_cxx_personality_v2",
+                                                    nullptr};
+
+} // namespace clang::CodeGenUtils



More information about the llvm-branch-commits mailing list