[clang] [PowerPC][Clang] fix IEEE f128 complex div/mul use IBM f128 libcalls on powerpc (PR #218151)
via cfe-commits
cfe-commits at lists.llvm.org
Sat Aug 22 11:53:18 PDT 2026
llvmorg-github-actions[bot] wrote:
<!--LLVM PR SUMMARY COMMENT-->
@llvm/pr-subscribers-clang-codegen
Author: Folkert de Vries (folkertdev)
<details>
<summary>Changes</summary>
fixes https://github.com/llvm/llvm-project/issues/216820
Previously the IBM f128 libcall was used also for IEEE f128 complex mul/div.
---
Full diff: https://github.com/llvm/llvm-project/pull/218151.diff
3 Files Affected:
- (modified) clang/docs/ReleaseNotes.md (+1)
- (modified) clang/lib/CodeGen/CGExprComplex.cpp (+8-4)
- (modified) clang/test/CodeGen/fp128_complex.c (+31-3)
``````````diff
diff --git a/clang/docs/ReleaseNotes.md b/clang/docs/ReleaseNotes.md
index aa741bbf961e2..18a785abadd63 100644
--- a/clang/docs/ReleaseNotes.md
+++ b/clang/docs/ReleaseNotes.md
@@ -412,6 +412,7 @@ features cannot lower the translation-unit ABI level;
- Fixed a crash when checking scalar type with excess braces. (#GH69213), (#GH137845), (#GH198767), (#GH207566), (#GH106180)
- Fixed an assertion crash when instantiating a nested requirement with an invalid constraint. (#GH213575)
- Clang now defines the GCC-compatible predefined macro `__SIG_ATOMIC_TYPE__`. (#GH213895)
+- Fixed IEEE f128 complex mul/div using the IBM f128 libcalls on powerpc. (#GH216820)
- Fixed an ICE that occurred when a structured binding pack is expanded outside the lambda where it was declared. (#GH214160)
- Fixed a bug where a stray closing curley brace in an OpenMP/OpenACC pragma could cause pragma parsing issues when inside of a member function. (#GH214195)
diff --git a/clang/lib/CodeGen/CGExprComplex.cpp b/clang/lib/CodeGen/CGExprComplex.cpp
index 350cbd18c7ed7..30d693fb371cb 100644
--- a/clang/lib/CodeGen/CGExprComplex.cpp
+++ b/clang/lib/CodeGen/CGExprComplex.cpp
@@ -798,7 +798,8 @@ ComplexPairTy ComplexExprEmitter::EmitComplexBinOpLibCall(StringRef LibCallName,
/// Lookup the libcall name for a given floating point type complex
/// multiply.
-static StringRef getComplexMultiplyLibCallName(llvm::Type *Ty) {
+static StringRef getComplexMultiplyLibCallName(const llvm::Triple &T,
+ llvm::Type *Ty) {
switch (Ty->getTypeID()) {
default:
llvm_unreachable("Unsupported floating point type!");
@@ -813,7 +814,7 @@ static StringRef getComplexMultiplyLibCallName(llvm::Type *Ty) {
case llvm::Type::X86_FP80TyID:
return "__mulxc3";
case llvm::Type::FP128TyID:
- return "__multc3";
+ return T.isPPC() ? "__mulkc3" : "__multc3";
}
}
@@ -880,8 +881,9 @@ ComplexPairTy ComplexExprEmitter::EmitBinMul(const BinOpInfo &Op) {
// Now emit the libcall on this slowest of the slow paths.
CGF.EmitBlock(LibCallBB);
Value *LibCallR, *LibCallI;
+ llvm::Triple Triple = CGF.getTarget().getTriple();
std::tie(LibCallR, LibCallI) = EmitComplexBinOpLibCall(
- getComplexMultiplyLibCallName(Op.LHS.first->getType()), Op);
+ getComplexMultiplyLibCallName(Triple, Op.LHS.first->getType()), Op);
Builder.CreateBr(ContBB);
// Finally continue execution by phi-ing together the different
@@ -1078,7 +1080,9 @@ ComplexPairTy ComplexExprEmitter::EmitBinDiv(const BinOpInfo &Op) {
case llvm::Type::X86_FP80TyID:
return EmitComplexBinOpLibCall("__divxc3", LibCallOp);
case llvm::Type::FP128TyID:
- return EmitComplexBinOpLibCall("__divtc3", LibCallOp);
+ return EmitComplexBinOpLibCall(
+ CGF.getTarget().getTriple().isPPC() ? "__divkc3" : "__divtc3",
+ LibCallOp);
}
} else {
return EmitAlgebraicDiv(LHSr, LHSi, RHSr, RHSi);
diff --git a/clang/test/CodeGen/fp128_complex.c b/clang/test/CodeGen/fp128_complex.c
index d1593fae9c9bc..0cd3b59bf3615 100644
--- a/clang/test/CodeGen/fp128_complex.c
+++ b/clang/test/CodeGen/fp128_complex.c
@@ -1,9 +1,37 @@
-// RUN: %clang --target=aarch64 %s -S -emit-llvm -o - | FileCheck %s
+// RUN: %clang --target=aarch64 %s -S -emit-llvm -o - | FileCheck %s --check-prefix=TC3
+// RUN: %clang_cc1 -triple powerpc64le-unknown-linux-gnu -target-feature +float128 -DTEST_PPC128 -emit-llvm -o - %s \
+// RUN: | FileCheck %s --check-prefixes=IBM,PPC
+// RUN: %clang_cc1 -triple powerpc64le-unknown-linux-gnu -target-feature +float128 -DTEST_PPC128 -mabi=ieeelongdouble -emit-llvm -o - %s \
+// RUN: | FileCheck %s --check-prefixes=KC3,PPC
_Complex long double a, b, c, d;
void test_fp128_compound_assign(void) {
- // CHECK: call { fp128, fp128 } @__multc3
+ // TC3: call { fp128, fp128 } @__multc3
+ // IBM: call { ppc_fp128, ppc_fp128 } @__multc3
+ // KC3: call { fp128, fp128 } @__mulkc3
a *= b;
- // CHECK: call { fp128, fp128 } @__divtc3
+ // TC3: call { fp128, fp128 } @__divtc3
+ // IBM: call { ppc_fp128, ppc_fp128 } @__divtc3
+ // KC3: call { fp128, fp128 } @__divkc3
c /= d;
}
+
+#ifdef __FLOAT128__
+_Complex __float128 e, f, g, h;
+void test_float128_compound_assign(void) {
+ // PPC: call { fp128, fp128 } @__mulkc3
+ e *= f;
+ // PPC: call { fp128, fp128 } @__divkc3
+ g /= h;
+}
+#endif
+
+#ifdef __powerpc__
+_Complex __ibm128 i, j, k, l;
+void test_ibm128_compound_assign(void) {
+ // PPC: call { ppc_fp128, ppc_fp128 } @__multc3
+ i *= j;
+ // PPC: call { ppc_fp128, ppc_fp128 } @__divtc3
+ k /= l;
+}
+#endif
``````````
</details>
https://github.com/llvm/llvm-project/pull/218151
More information about the cfe-commits
mailing list