From f22108bcbe97365a29e134ecd496533641f901fb Mon Sep 17 00:00:00 2001 From: Viktoriia Bakalova Date: Mon, 30 Sep 2024 12:50:09 +0000 Subject: [PATCH] [clang][Itanium Mangle] Enable mangling of enclosing class for member-like friend function templates only if ` -fclang-abi-compat>=19`. --- clang/docs/ReleaseNotes.rst | 2 +- clang/include/clang/Basic/LangOptions.h | 3 ++- clang/lib/AST/ItaniumMangle.cpp | 11 ++++++++++- clang/test/CodeGenCXX/mangle-concept.cpp | 4 ++++ 4 files changed, 17 insertions(+), 3 deletions(-) diff --git a/clang/docs/ReleaseNotes.rst b/clang/docs/ReleaseNotes.rst index 35c31452cef4118..d824213d700905c 100644 --- a/clang/docs/ReleaseNotes.rst +++ b/clang/docs/ReleaseNotes.rst @@ -104,6 +104,7 @@ ABI Changes in This Version - Fixed Microsoft name mangling of placeholder, auto and decltype(auto), return types for MSVC 1920+. This change resolves incompatibilities with code compiled by MSVC 1920+ but will introduce incompatibilities with code compiled by earlier versions of Clang unless such code is built with the compiler option -fms-compatibility-version=19.14 to imitate the MSVC 1914 mangling behavior. - Fixed the Itanium mangling of the construction vtable name. This change will introduce incompatibilities with code compiled by Clang 19 and earlier versions, unless the -fclang-abi-compat=19 option is used. (#GH108015) +- Mangle friend function templates with a constraint that depends on a template parameter from an enclosing template as members of the enclosing class. (#GH110247, #GH110503) AST Dumping Potentially Breaking Changes ---------------------------------------- @@ -447,7 +448,6 @@ Bug Fixes to C++ Support - Fixed an assertion failure in debug mode, and potential crashes in release mode, when diagnosing a failed cast caused indirectly by a failed implicit conversion to the type of the constructor parameter. - Fixed an assertion failure by adjusting integral to boolean vector conversions (#GH108326) -- Mangle friend function templates with a constraint that depends on a template parameter from an enclosing template as members of the enclosing class. (#GH110247) Bug Fixes to AST Handling ^^^^^^^^^^^^^^^^^^^^^^^^^ diff --git a/clang/include/clang/Basic/LangOptions.h b/clang/include/clang/Basic/LangOptions.h index 8c605f6852016ea..f5fa1bd8df19675 100644 --- a/clang/include/clang/Basic/LangOptions.h +++ b/clang/include/clang/Basic/LangOptions.h @@ -241,8 +241,9 @@ class LangOptionsBase { /// Attempt to be ABI-compatible with code generated by Clang 19.0.x. /// This causes clang to: - /// - Incorrectly mangles the 'base type' substitutions of the CXX + /// - Incorrectly mangle the 'base type' substitutions of the CXX /// construction vtable because it hasn't added 'type' as a substitution. + /// - Skip mangling enclosing class templates of member-like friend function templates. Ver19, /// Conform to the underlying platform's C and C++ ABIs as closely diff --git a/clang/lib/AST/ItaniumMangle.cpp b/clang/lib/AST/ItaniumMangle.cpp index 117255178eebb41..3d9d1e3f22f8327 100644 --- a/clang/lib/AST/ItaniumMangle.cpp +++ b/clang/lib/AST/ItaniumMangle.cpp @@ -693,7 +693,7 @@ ItaniumMangleContextImpl::getEffectiveDeclContext(const Decl *D) { if (VD->isExternC()) return getASTContext().getTranslationUnitDecl(); - if (const auto *FD = D->getAsFunction()) { + if (const auto *FD = dyn_cast(D)) { if (FD->isExternC()) return getASTContext().getTranslationUnitDecl(); // Member-like constrained friends are mangled as if they were members of @@ -704,6 +704,15 @@ ItaniumMangleContextImpl::getEffectiveDeclContext(const Decl *D) { return D->getLexicalDeclContext()->getRedeclContext(); } + if (const auto *FTD = dyn_cast(D)) { + // Member-like constrained friends are mangled as if they were members of + // the enclosing class. + if (FTD->getTemplatedDecl()->isMemberLikeConstrainedFriend() && + getASTContext().getLangOpts().getClangABICompat() > + LangOptions::ClangABI::Ver19) + return D->getLexicalDeclContext()->getRedeclContext(); + } + return DC->getRedeclContext(); } diff --git a/clang/test/CodeGenCXX/mangle-concept.cpp b/clang/test/CodeGenCXX/mangle-concept.cpp index 6053511c00a7b55..aa0940c35b237af 100644 --- a/clang/test/CodeGenCXX/mangle-concept.cpp +++ b/clang/test/CodeGenCXX/mangle-concept.cpp @@ -1,4 +1,5 @@ // RUN: %clang_cc1 -verify -std=c++20 -emit-llvm -triple %itanium_abi_triple -o - %s -fclang-abi-compat=latest | FileCheck %s +// RUN: %clang_cc1 -verify -std=c++20 -emit-llvm -triple %itanium_abi_triple -o - %s -fclang-abi-compat=19 | FileCheck %s --check-prefix=CLANG19 // RUN: %clang_cc1 -verify -std=c++20 -emit-llvm -triple %itanium_abi_triple -o - %s -fclang-abi-compat=17 | FileCheck %s --check-prefix=CLANG17 // expected-no-diagnostics @@ -59,18 +60,21 @@ namespace test2 { // CLANG17: call {{.*}}@_ZN5test21fEz( f(ai); // CHECK: call {{.*}}@_ZN5test21AIiEF1gIvEEvzQaa4TrueIT_E4TrueITL0__E( + // CLANG19: call {{.*}}@_ZN5test2F1gIvEEvzQaa4TrueIT_E4TrueITL0__E( // CLANG17: call {{.*}}@_ZN5test21gIvEEvz( g(ai); // CHECK: call {{.*}}@_ZN5test21hIvEEvzQ4TrueITL0__E( // CLANG17: call {{.*}}@_ZN5test21hIvEEvz( h(ai); // CHECK: call {{.*}}@_ZN5test21AIiEF1iIvQaa4TrueIT_E4TrueITL0__EEEvz( + // CLANG19: call {{.*}}@_ZN5test2F1iIvQaa4TrueIT_E4TrueITL0__EEEvz( // CLANG17: call {{.*}}@_ZN5test21iIvEEvz( i(ai); // CHECK: call {{.*}}@_ZN5test21jIvQ4TrueITL0__EEEvz( // CLANG17: call {{.*}}@_ZN5test21jIvEEvz( j(ai); // CHECK: call {{.*}}@_ZN5test21AIiEF1kITk4TruevQ4TrueIT_EEEvz( + // CLANG19: call {{.*}}@_ZN5test2F1kITk4TruevQ4TrueIT_EEEvz( // CLANG17: call {{.*}}@_ZN5test21kIvEEvz( k(ai); // CHECK: call {{.*}}@_ZN5test21lITk4TruevEEvz(