From 02193ce76c1bcc2c1e2d712dcd061cd80740b7fd Mon Sep 17 00:00:00 2001 From: David Majnemer Date: Tue, 9 Jun 2015 18:05:33 +0000 Subject: [PATCH] [ItaniumMangle] Mangle long double as __float128 for some Power targets GCC mangles long double like __float128 in order to support compatibility with ABI variants which had a different interpretation of long double. This fixes PR23791. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@239421 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/clang/Basic/TargetInfo.h | 4 ++++ lib/AST/ItaniumMangle.cpp | 6 +++++- lib/Basic/Targets.cpp | 6 ++++++ test/CodeGenCXX/mangle-long-double.cpp | 10 ++++++++++ 4 files changed, 25 insertions(+), 1 deletion(-) create mode 100644 test/CodeGenCXX/mangle-long-double.cpp diff --git a/include/clang/Basic/TargetInfo.h b/include/clang/Basic/TargetInfo.h index 8406205c7f..e415733189 100644 --- a/include/clang/Basic/TargetInfo.h +++ b/include/clang/Basic/TargetInfo.h @@ -363,6 +363,10 @@ public: return *LongDoubleFormat; } + /// \brief Return true if the 'long double' type should be mangled like + /// __float128. + virtual bool useFloat128ManglingForLongDouble() const { return false; } + /// \brief Return the value for the C99 FLT_EVAL_METHOD macro. virtual unsigned getFloatEvalMethod() const { return 0; } diff --git a/lib/AST/ItaniumMangle.cpp b/lib/AST/ItaniumMangle.cpp index d07efaee7b..968f0308b6 100644 --- a/lib/AST/ItaniumMangle.cpp +++ b/lib/AST/ItaniumMangle.cpp @@ -2010,7 +2010,11 @@ void CXXNameMangler::mangleType(const BuiltinType *T) { case BuiltinType::Half: Out << "Dh"; break; case BuiltinType::Float: Out << 'f'; break; case BuiltinType::Double: Out << 'd'; break; - case BuiltinType::LongDouble: Out << 'e'; break; + case BuiltinType::LongDouble: + Out << (getASTContext().getTargetInfo().useFloat128ManglingForLongDouble() + ? 'g' + : 'e'); + break; case BuiltinType::NullPtr: Out << "Dn"; break; #define BUILTIN_TYPE(Id, SingletonId) diff --git a/lib/Basic/Targets.cpp b/lib/Basic/Targets.cpp index c0c6924845..9c55979679 100644 --- a/lib/Basic/Targets.cpp +++ b/lib/Basic/Targets.cpp @@ -992,6 +992,12 @@ public: bool hasSjLjLowering() const override { return true; } + + bool useFloat128ManglingForLongDouble() const override { + return LongDoubleWidth == 128 && + LongDoubleFormat == &llvm::APFloat::PPCDoubleDouble && + getTriple().isOSBinFormatELF(); + } }; const Builtin::Info PPCTargetInfo::BuiltinInfo[] = { diff --git a/test/CodeGenCXX/mangle-long-double.cpp b/test/CodeGenCXX/mangle-long-double.cpp new file mode 100644 index 0000000000..4a476fb0fd --- /dev/null +++ b/test/CodeGenCXX/mangle-long-double.cpp @@ -0,0 +1,10 @@ +// RUN: %clang_cc1 -triple powerpc64-unknown-linux-gnu %s -emit-llvm -o - | FileCheck %s --check-prefix=POWER64-LINUX +// RUN: %clang_cc1 -triple powerpc-unknown-linux-gnu %s -emit-llvm -o - | FileCheck %s --check-prefix=POWER-LINUX +// RUN: %clang_cc1 -triple powerpc64-apple-darwin9 %s -emit-llvm -o - | FileCheck %s --check-prefix=POWER64-DARWIN +// RUN: %clang_cc1 -triple powerpc-apple-darwin9 %s -emit-llvm -o - | FileCheck %s --check-prefix=POWER-DARWIN + +void f(long double) {} +// POWER64-LINUX: _Z1fg +// POWER-LINUX: _Z1fg +// POWER64-DARWIN: _Z1fe +// POWER-DARWIN: _Z1fe -- 2.40.0