llvmorg-github-actions[bot] wrote:

<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-clang-codegen

Author: Folkert de Vries (folkertdev)

<details>
<summary>Changes</summary>

closes https://github.com/llvm/llvm-project/pull/77732
cc https://github.com/llvm/llvm-project/issues/44482

Replaces https://github.com/llvm/llvm-project/pull/77732 and truly fixes 
https://github.com/llvm/llvm-project/issues/56023.

The design, as per 
https://github.com/llvm/llvm-project/pull/77732#issuecomment-4938515656, is 
that `-fclang-abi-compat=22` continues to give the old ABI behavior, and in 23 
(or 24, we're close to the cutoff and this might not make it) gives the new 
GCC-compatible behavior.

So, the challenge is of course how to test and review all this. I have a 
collection of input file that I used for testing empirically versus GCC:

https://github.com/folkertdev/powerpc-complex-abi-validation

 I'd happily just add (a subset of) those and run the `CHECK` generation on 
them, but I'm not sure that's really worth it. As you can see though from the 
current tests that were touched, the testing is rather thin.

And the GCC logic is non-trivial: some types must be converted to integers, 
vectors or arrays to get the right behavior. There is register alignment for 
some types. 

Future work is to make `va_arg` work. The pre-existing implementation has a big 
FIXME for it, but it should be possible to implement in a GCC-compatible way 
now.


---

Patch is 60.86 KiB, truncated to 20.00 KiB below, full version: 
https://github.com/llvm/llvm-project/pull/208917.diff


5 Files Affected:

- (modified) clang/lib/CodeGen/Targets/PPC.cpp (+111-2) 
- (modified) clang/test/CodeGen/PowerPC/builtins-ppc-xlcompat-cmplx.c 
(+230-130) 
- (modified) clang/test/CodeGen/PowerPC/powerpc-c99complex.c (+72-20) 
- (modified) clang/test/CodeGen/long_double_fp128.cpp (+6-3) 
- (modified) clang/test/CodeGen/math-libcalls-tbaa-indirect-args.c (+42-29) 


``````````diff
diff --git a/clang/lib/CodeGen/Targets/PPC.cpp 
b/clang/lib/CodeGen/Targets/PPC.cpp
index ab069bfbd1b51..fc07e57656d09 100644
--- a/clang/lib/CodeGen/Targets/PPC.cpp
+++ b/clang/lib/CodeGen/Targets/PPC.cpp
@@ -361,7 +361,18 @@ class PPC32_SVR4_ABIInfo : public DefaultABIInfo {
   bool IsSoftFloatABI;
   bool IsRetSmallStructInRegABI;
 
+  // Number of GPRs (r3..=r10) available for passing arguments, and their 
width.
+  static const int NumArgGPRs = 8;
+  static const unsigned GPRBits = 32;
+
+  bool isComplexGnuABI() const {
+    return !getTarget().getTriple().isOSDarwin() &&
+           !getContext().getLangOpts().isCompatibleWith(
+               LangOptions::ClangABI::Ver22);
+  }
+
   CharUnits getParamTypeAlignment(QualType Ty) const;
+  ABIArgInfo classifyComplexType(QualType Ty) const;
 
 public:
   PPC32_SVR4_ABIInfo(CodeGen::CodeGenTypes &CGT, bool SoftFloatABI,
@@ -370,12 +381,15 @@ class PPC32_SVR4_ABIInfo : public DefaultABIInfo {
         IsRetSmallStructInRegABI(RetSmallStructInRegABI) {}
 
   ABIArgInfo classifyReturnType(QualType RetTy) const;
+  ABIArgInfo classifyArgumentType(QualType Ty, int &ArgGPRsLeft) const;
 
   void computeInfo(CGFunctionInfo &FI) const override {
     if (!getCXXABI().classifyReturnType(FI))
       FI.getReturnInfo() = classifyReturnType(FI.getReturnType());
+
+    int ArgGPRsLeft = NumArgGPRs;
     for (auto &I : FI.arguments())
-      I.info = classifyArgumentType(I.type);
+      I.info = classifyArgumentType(I.type, ArgGPRsLeft);
   }
 
   RValue EmitVAArg(CodeGenFunction &CGF, Address VAListAddr, QualType Ty,
@@ -426,9 +440,102 @@ CharUnits 
PPC32_SVR4_ABIInfo::getParamTypeAlignment(QualType Ty) const {
   return CharUnits::fromQuantity(4);
 }
 
+ABIArgInfo PPC32_SVR4_ABIInfo::classifyComplexType(QualType Ty) const {
+  uint64_t Size = getContext().getTypeSize(Ty);
+  llvm::LLVMContext &VMC = getVMContext();
+  llvm::Type *I32 = llvm::Type::getInt32Ty(VMC);
+
+  assert(Ty->isAnyComplexType() && "not a complex type");
+  QualType ElemTy = Ty->castAs<ComplexType>()->getElementType();
+
+  // Work around https://github.com/llvm/llvm-project/issues/44482.
+  // This is a bug where the two halves of a ppc_fp128 are swapped.
+  // Using i128 for the ABI instead circumvents this issue.
+  if (CGT.ConvertType(ElemTy)->isPPC_FP128Ty())
+    return ABIArgInfo::getDirect(
+        llvm::ArrayType::get(llvm::Type::getInt128Ty(VMC), 2));
+
+  // Coerce to an integer for _Complex char and _Complex short.
+  if (Size <= GPRBits)
+    return ABIArgInfo::getDirect(llvm::IntegerType::get(VMC, Size));
+
+  // Coerce to a vector <N x i32> for _Complex float and _Complex int.
+  // A vector gives this the correct 8-byte register alignment.
+  if (Size == 2 * GPRBits)
+    return ABIArgInfo::getDirect(llvm::FixedVectorType::get(I32, 2));
+
+  // Coerce to an array [N x i32] for _Complex double and similar.
+  // An array of i32 gives the correct 4-byte register alignment.
+  return ABIArgInfo::getDirect(llvm::ArrayType::get(I32, Size / GPRBits));
+}
+
+ABIArgInfo PPC32_SVR4_ABIInfo::classifyArgumentType(QualType Ty,
+                                                    int &ArgGPRsLeft) const {
+  assert(ArgGPRsLeft <= NumArgGPRs && "Arg GPR tracking underflow");
+  Ty = useFirstFieldIfTransparentUnion(Ty);
+
+  bool IsComplex = Ty->isAnyComplexType() && isComplexGnuABI();
+
+  // Use the default implementation when this argument is not relevant for GPR
+  // budget:
+  //
+  // - floating-point types are passed in FPRs
+  // - when GPRs are already exhausted
+  //
+  // Complex types (when GNU compatible) always need custom handling.
+  if (!IsComplex && (!ArgGPRsLeft || (Ty->isFloatingType() && 
!IsSoftFloatABI)))
+    return DefaultABIInfo::classifyArgumentType(Ty);
+
+  uint64_t TypeSize = getContext().getTypeSize(Ty);
+  uint64_t RegsNeeded = (TypeSize + GPRBits - 1) / GPRBits;
+
+  if (IsComplex || !isAggregateTypeForABI(Ty)) {
+    // Complex values and scalars are passed in GPRs.
+
+    // An 8-byte value (e.g. _Complex float, _Complex int, i64, soft-float
+    // double) must start in an even-numbered GPR, so skip an odd register to
+    // keep the pair aligned.
+    if (TypeSize == 2 * GPRBits && ArgGPRsLeft % 2 == 1)
+      ArgGPRsLeft -= 1;
+
+    if (RegsNeeded <= (uint64_t)ArgGPRsLeft) {
+      // All fits.
+      ArgGPRsLeft -= RegsNeeded;
+
+      // _Complex needs a type coercion to be passed correctly.
+      if (IsComplex)
+        return classifyComplexType(Ty);
+    } else if (IsComplex) {
+      // Never split a Complex value across GPRs and the stack. When a Complex
+      // value does not fit in the remaining GPRs, it is passed via the stack
+      // and the remaining GPRs are considered consumed, so any further
+      // arguments will be passed via the stack as well.
+
+      // _Complex needs a type coercion to be passed correctly.
+      llvm::Type *CoerceTy = classifyComplexType(Ty).getCoerceToType();
+
+      // Soak up the remaining GPRs with a padding argument.
+      llvm::Type *I32 = llvm::Type::getInt32Ty(getVMContext());
+      llvm::Type *Padding =
+          ArgGPRsLeft > 0 ? llvm::ArrayType::get(I32, ArgGPRsLeft) : nullptr;
+
+      ArgGPRsLeft = 0;
+      return ABIArgInfo::getDirect(CoerceTy, /*Offset=*/0, Padding);
+    }
+  } else {
+    // Other aggregates are passed indirectly, and consume one GPR.
+    ArgGPRsLeft -= 1;
+  }
+
+  return DefaultABIInfo::classifyArgumentType(Ty);
+}
+
 ABIArgInfo PPC32_SVR4_ABIInfo::classifyReturnType(QualType RetTy) const {
   uint64_t Size;
 
+  if (RetTy->isAnyComplexType() && isComplexGnuABI())
+    return classifyComplexType(RetTy);
+
   // -msvr4-struct-return puts small aggregates in GPR3 and GPR4.
   if (isAggregateTypeForABI(RetTy) && IsRetSmallStructInRegABI &&
       (Size = getContext().getTypeSize(RetTy)) <= 64) {
@@ -463,8 +570,10 @@ RValue PPC32_SVR4_ABIInfo::EmitVAArg(CodeGenFunction &CGF, 
Address VAList,
     TI.Align = getParamTypeAlignment(Ty);
 
     CharUnits SlotSize = CharUnits::fromQuantity(4);
+    int ArgGPRsLeft = NumArgGPRs;
     return emitVoidPtrVAArg(CGF, VAList, Ty,
-                            classifyArgumentType(Ty).isIndirect(), TI, 
SlotSize,
+                            classifyArgumentType(Ty, ArgGPRsLeft).isIndirect(),
+                            TI, SlotSize,
                             /*AllowHigherAlign=*/true, Slot);
   }
 
diff --git a/clang/test/CodeGen/PowerPC/builtins-ppc-xlcompat-cmplx.c 
b/clang/test/CodeGen/PowerPC/builtins-ppc-xlcompat-cmplx.c
index cf03af38b3784..ae224aef66da9 100644
--- a/clang/test/CodeGen/PowerPC/builtins-ppc-xlcompat-cmplx.c
+++ b/clang/test/CodeGen/PowerPC/builtins-ppc-xlcompat-cmplx.c
@@ -6,10 +6,14 @@
 // RUN:   -emit-llvm %s -o -  -target-cpu pwr8 | FileCheck %s 
--check-prefix=64BITLE
 // RUN: %clang_cc1 -triple powerpc64-unknown-aix \
 // RUN:    -emit-llvm %s -o -  -target-cpu pwr7 | FileCheck %s 
--check-prefix=64BITAIX
-// RUN: %clang_cc1 -triple powerpc-unknown-linux-gnu \
-// RUN:    -emit-llvm %s -o -  -target-cpu pwr7 | FileCheck %s 
--check-prefix=32BIT
-// RUN: %clang_cc1 -triple powerpcle-unknown-linux-gnu \
-// RUN:   -emit-llvm %s -o -  -target-cpu pwr8 | FileCheck %s 
--check-prefix=32BITLE
+// RUN: %clang_cc1 -triple powerpc-unknown-linux-gnu -fclang-abi-compat=22 \
+// RUN:    -emit-llvm %s -o -  -target-cpu pwr7 | FileCheck %s 
--check-prefix=32BIT-CLANG22
+// RUN: %clang_cc1 -triple powerpc-unknown-linux-gnu -fclang-abi-compat=23 \
+// RUN:    -emit-llvm %s -o -  -target-cpu pwr7 | FileCheck %s 
--check-prefix=32BIT-CLANG23
+// RUN: %clang_cc1 -triple powerpcle-unknown-linux-gnu -fclang-abi-compat=22 \
+// RUN:   -emit-llvm %s -o -  -target-cpu pwr8 | FileCheck %s 
--check-prefix=32BITLE-CLANG22
+// RUN: %clang_cc1 -triple powerpcle-unknown-linux-gnu -fclang-abi-compat=23 \
+// RUN:   -emit-llvm %s -o -  -target-cpu pwr8 | FileCheck %s 
--check-prefix=32BITLE-CLANG23
 // RUN: %clang_cc1 -triple powerpc-unknown-aix \
 // RUN:    -emit-llvm %s -o -  -target-cpu pwr7 | FileCheck %s 
--check-prefix=32BITAIX
 
@@ -61,49 +65,81 @@
 // 64BITAIX-NEXT:    [[TMP2:%.*]] = load { double, double }, ptr [[RETVAL]], 
align 4
 // 64BITAIX-NEXT:    ret { double, double } [[TMP2]]
 //
-// 32BIT-LABEL: @testcmplx(
-// 32BIT-NEXT:  entry:
-// 32BIT-NEXT:    [[REAL_ADDR:%.*]] = alloca double, align 8
-// 32BIT-NEXT:    [[IMAG_ADDR:%.*]] = alloca double, align 8
-// 32BIT-NEXT:    store double [[REAL:%.*]], ptr [[REAL_ADDR]], align 8
-// 32BIT-NEXT:    store double [[IMAG:%.*]], ptr [[IMAG_ADDR]], align 8
-// 32BIT-NEXT:    [[TMP0:%.*]] = load double, ptr [[REAL_ADDR]], align 8
-// 32BIT-NEXT:    [[TMP1:%.*]] = load double, ptr [[IMAG_ADDR]], align 8
-// 32BIT-NEXT:    [[AGG_RESULT_REALP:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT:%.*]], i32 0, i32 0
-// 32BIT-NEXT:    [[AGG_RESULT_IMAGP:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BIT-NEXT:    store double [[TMP0]], ptr [[AGG_RESULT_REALP]], align 8
-// 32BIT-NEXT:    store double [[TMP1]], ptr [[AGG_RESULT_IMAGP]], align 8
-// 32BIT-NEXT:    [[AGG_RESULT_REALP1:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
-// 32BIT-NEXT:    [[AGG_RESULT_REAL:%.*]] = load double, ptr 
[[AGG_RESULT_REALP1]], align 8
-// 32BIT-NEXT:    [[AGG_RESULT_IMAGP2:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BIT-NEXT:    [[AGG_RESULT_IMAG:%.*]] = load double, ptr 
[[AGG_RESULT_IMAGP2]], align 8
-// 32BIT-NEXT:    [[AGG_RESULT_REALP3:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
-// 32BIT-NEXT:    [[AGG_RESULT_IMAGP4:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BIT-NEXT:    store double [[AGG_RESULT_REAL]], ptr [[AGG_RESULT_REALP3]], 
align 8
-// 32BIT-NEXT:    store double [[AGG_RESULT_IMAG]], ptr [[AGG_RESULT_IMAGP4]], 
align 8
-// 32BIT-NEXT:    ret void
+// 32BIT-CLANG22-LABEL: @testcmplx(
+// 32BIT-CLANG22-NEXT:  entry:
+// 32BIT-CLANG22-NEXT:    [[REAL_ADDR:%.*]] = alloca double, align 8
+// 32BIT-CLANG22-NEXT:    [[IMAG_ADDR:%.*]] = alloca double, align 8
+// 32BIT-CLANG22-NEXT:    store double [[REAL:%.*]], ptr [[REAL_ADDR]], align 8
+// 32BIT-CLANG22-NEXT:    store double [[IMAG:%.*]], ptr [[IMAG_ADDR]], align 8
+// 32BIT-CLANG22-NEXT:    [[TMP0:%.*]] = load double, ptr [[REAL_ADDR]], align 
8
+// 32BIT-CLANG22-NEXT:    [[TMP1:%.*]] = load double, ptr [[IMAG_ADDR]], align 
8
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_REALP:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT:%.*]], i32 0, i32 0
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_IMAGP:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
+// 32BIT-CLANG22-NEXT:    store double [[TMP0]], ptr [[AGG_RESULT_REALP]], 
align 8
+// 32BIT-CLANG22-NEXT:    store double [[TMP1]], ptr [[AGG_RESULT_IMAGP]], 
align 8
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_REALP1:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_REAL:%.*]] = load double, ptr 
[[AGG_RESULT_REALP1]], align 8
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_IMAGP2:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_IMAG:%.*]] = load double, ptr 
[[AGG_RESULT_IMAGP2]], align 8
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_REALP3:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
+// 32BIT-CLANG22-NEXT:    [[AGG_RESULT_IMAGP4:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
+// 32BIT-CLANG22-NEXT:    store double [[AGG_RESULT_REAL]], ptr 
[[AGG_RESULT_REALP3]], align 8
+// 32BIT-CLANG22-NEXT:    store double [[AGG_RESULT_IMAG]], ptr 
[[AGG_RESULT_IMAGP4]], align 8
+// 32BIT-CLANG22-NEXT:    ret void
 //
-// 32BITLE-LABEL: @testcmplx(
-// 32BITLE-NEXT:  entry:
-// 32BITLE-NEXT:    [[REAL_ADDR:%.*]] = alloca double, align 8
-// 32BITLE-NEXT:    [[IMAG_ADDR:%.*]] = alloca double, align 8
-// 32BITLE-NEXT:    store double [[REAL:%.*]], ptr [[REAL_ADDR]], align 8
-// 32BITLE-NEXT:    store double [[IMAG:%.*]], ptr [[IMAG_ADDR]], align 8
-// 32BITLE-NEXT:    [[TMP0:%.*]] = load double, ptr [[REAL_ADDR]], align 8
-// 32BITLE-NEXT:    [[TMP1:%.*]] = load double, ptr [[IMAG_ADDR]], align 8
-// 32BITLE-NEXT:    [[AGG_RESULT_REALP:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT:%.*]], i32 0, i32 0
-// 32BITLE-NEXT:    [[AGG_RESULT_IMAGP:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BITLE-NEXT:    store double [[TMP0]], ptr [[AGG_RESULT_REALP]], align 8
-// 32BITLE-NEXT:    store double [[TMP1]], ptr [[AGG_RESULT_IMAGP]], align 8
-// 32BITLE-NEXT:    [[AGG_RESULT_REALP1:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
-// 32BITLE-NEXT:    [[AGG_RESULT_REAL:%.*]] = load double, ptr 
[[AGG_RESULT_REALP1]], align 8
-// 32BITLE-NEXT:    [[AGG_RESULT_IMAGP2:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BITLE-NEXT:    [[AGG_RESULT_IMAG:%.*]] = load double, ptr 
[[AGG_RESULT_IMAGP2]], align 8
-// 32BITLE-NEXT:    [[AGG_RESULT_REALP3:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
-// 32BITLE-NEXT:    [[AGG_RESULT_IMAGP4:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BITLE-NEXT:    store double [[AGG_RESULT_REAL]], ptr 
[[AGG_RESULT_REALP3]], align 8
-// 32BITLE-NEXT:    store double [[AGG_RESULT_IMAG]], ptr 
[[AGG_RESULT_IMAGP4]], align 8
-// 32BITLE-NEXT:    ret void
+// 32BIT-CLANG23-LABEL: @testcmplx(
+// 32BIT-CLANG23-NEXT:  entry:
+// 32BIT-CLANG23-NEXT:    [[RETVAL:%.*]] = alloca { double, double }, align 8
+// 32BIT-CLANG23-NEXT:    [[REAL_ADDR:%.*]] = alloca double, align 8
+// 32BIT-CLANG23-NEXT:    [[IMAG_ADDR:%.*]] = alloca double, align 8
+// 32BIT-CLANG23-NEXT:    store double [[REAL:%.*]], ptr [[REAL_ADDR]], align 8
+// 32BIT-CLANG23-NEXT:    store double [[IMAG:%.*]], ptr [[IMAG_ADDR]], align 8
+// 32BIT-CLANG23-NEXT:    [[TMP0:%.*]] = load double, ptr [[REAL_ADDR]], align 
8
+// 32BIT-CLANG23-NEXT:    [[TMP1:%.*]] = load double, ptr [[IMAG_ADDR]], align 
8
+// 32BIT-CLANG23-NEXT:    [[RETVAL_REALP:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[RETVAL]], i32 0, i32 0
+// 32BIT-CLANG23-NEXT:    [[RETVAL_IMAGP:%.*]] = getelementptr inbounds nuw { 
double, double }, ptr [[RETVAL]], i32 0, i32 1
+// 32BIT-CLANG23-NEXT:    store double [[TMP0]], ptr [[RETVAL_REALP]], align 8
+// 32BIT-CLANG23-NEXT:    store double [[TMP1]], ptr [[RETVAL_IMAGP]], align 8
+// 32BIT-CLANG23-NEXT:    [[TMP2:%.*]] = load [4 x i32], ptr [[RETVAL]], align 
8
+// 32BIT-CLANG23-NEXT:    ret [4 x i32] [[TMP2]]
+//
+// 32BITLE-CLANG22-LABEL: @testcmplx(
+// 32BITLE-CLANG22-NEXT:  entry:
+// 32BITLE-CLANG22-NEXT:    [[REAL_ADDR:%.*]] = alloca double, align 8
+// 32BITLE-CLANG22-NEXT:    [[IMAG_ADDR:%.*]] = alloca double, align 8
+// 32BITLE-CLANG22-NEXT:    store double [[REAL:%.*]], ptr [[REAL_ADDR]], 
align 8
+// 32BITLE-CLANG22-NEXT:    store double [[IMAG:%.*]], ptr [[IMAG_ADDR]], 
align 8
+// 32BITLE-CLANG22-NEXT:    [[TMP0:%.*]] = load double, ptr [[REAL_ADDR]], 
align 8
+// 32BITLE-CLANG22-NEXT:    [[TMP1:%.*]] = load double, ptr [[IMAG_ADDR]], 
align 8
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_REALP:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT:%.*]], i32 0, i32 0
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_IMAGP:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
+// 32BITLE-CLANG22-NEXT:    store double [[TMP0]], ptr [[AGG_RESULT_REALP]], 
align 8
+// 32BITLE-CLANG22-NEXT:    store double [[TMP1]], ptr [[AGG_RESULT_IMAGP]], 
align 8
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_REALP1:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_REAL:%.*]] = load double, ptr 
[[AGG_RESULT_REALP1]], align 8
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_IMAGP2:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_IMAG:%.*]] = load double, ptr 
[[AGG_RESULT_IMAGP2]], align 8
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_REALP3:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 0
+// 32BITLE-CLANG22-NEXT:    [[AGG_RESULT_IMAGP4:%.*]] = getelementptr inbounds 
nuw { double, double }, ptr [[AGG_RESULT]], i32 0, i32 1
+// 32BITLE-CLANG22-NEXT:    store double [[AGG_RESULT_REAL]], ptr 
[[AGG_RESULT_REALP3]], align 8
+// 32BITLE-CLANG22-NEXT:    store double [[AGG_RESULT_IMAG]], ptr 
[[AGG_RESULT_IMAGP4]], align 8
+// 32BITLE-CLANG22-NEXT:    ret void
+//
+// 32BITLE-CLANG23-LABEL: @testcmplx(
+// 32BITLE-CLANG23-NEXT:  entry:
+// 32BITLE-CLANG23-NEXT:    [[RETVAL:%.*]] = alloca { double, double }, align 8
+// 32BITLE-CLANG23-NEXT:    [[REAL_ADDR:%.*]] = alloca double, align 8
+// 32BITLE-CLANG23-NEXT:    [[IMAG_ADDR:%.*]] = alloca double, align 8
+// 32BITLE-CLANG23-NEXT:    store double [[REAL:%.*]], ptr [[REAL_ADDR]], 
align 8
+// 32BITLE-CLANG23-NEXT:    store double [[IMAG:%.*]], ptr [[IMAG_ADDR]], 
align 8
+// 32BITLE-CLANG23-NEXT:    [[TMP0:%.*]] = load double, ptr [[REAL_ADDR]], 
align 8
+// 32BITLE-CLANG23-NEXT:    [[TMP1:%.*]] = load double, ptr [[IMAG_ADDR]], 
align 8
+// 32BITLE-CLANG23-NEXT:    [[RETVAL_REALP:%.*]] = getelementptr inbounds nuw 
{ double, double }, ptr [[RETVAL]], i32 0, i32 0
+// 32BITLE-CLANG23-NEXT:    [[RETVAL_IMAGP:%.*]] = getelementptr inbounds nuw 
{ double, double }, ptr [[RETVAL]], i32 0, i32 1
+// 32BITLE-CLANG23-NEXT:    store double [[TMP0]], ptr [[RETVAL_REALP]], align 
8
+// 32BITLE-CLANG23-NEXT:    store double [[TMP1]], ptr [[RETVAL_IMAGP]], align 
8
+// 32BITLE-CLANG23-NEXT:    [[TMP2:%.*]] = load [4 x i32], ptr [[RETVAL]], 
align 8
+// 32BITLE-CLANG23-NEXT:    ret [4 x i32] [[TMP2]]
 //
 // 32BITAIX-LABEL: @testcmplx(
 // 32BITAIX-NEXT:  entry:
@@ -173,49 +209,81 @@ double _Complex testcmplx(double real, double imag) {
 // 64BITAIX-NEXT:    [[TMP2:%.*]] = load { float, float }, ptr [[RETVAL]], 
align 4
 // 64BITAIX-NEXT:    ret { float, float } [[TMP2]]
 //
-// 32BIT-LABEL: @testcmplxf(
-// 32BIT-NEXT:  entry:
-// 32BIT-NEXT:    [[REAL_ADDR:%.*]] = alloca float, align 4
-// 32BIT-NEXT:    [[IMAG_ADDR:%.*]] = alloca float, align 4
-// 32BIT-NEXT:    store float [[REAL:%.*]], ptr [[REAL_ADDR]], align 4
-// 32BIT-NEXT:    store float [[IMAG:%.*]], ptr [[IMAG_ADDR]], align 4
-// 32BIT-NEXT:    [[TMP0:%.*]] = load float, ptr [[REAL_ADDR]], align 4
-// 32BIT-NEXT:    [[TMP1:%.*]] = load float, ptr [[IMAG_ADDR]], align 4
-// 32BIT-NEXT:    [[AGG_RESULT_REALP:%.*]] = getelementptr inbounds nuw { 
float, float }, ptr [[AGG_RESULT:%.*]], i32 0, i32 0
-// 32BIT-NEXT:    [[AGG_RESULT_IMAGP:%.*]] = getelementptr inbounds nuw { 
float, float }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BIT-NEXT:    store float [[TMP0]], ptr [[AGG_RESULT_REALP]], align 4
-// 32BIT-NEXT:    store float [[TMP1]], ptr [[AGG_RESULT_IMAGP]], align 4
-// 32BIT-NEXT:    [[AGG_RESULT_REALP1:%.*]] = getelementptr inbounds nuw { 
float, float }, ptr [[AGG_RESULT]], i32 0, i32 0
-// 32BIT-NEXT:    [[AGG_RESULT_REAL:%.*]] = load float, ptr 
[[AGG_RESULT_REALP1]], align 4
-// 32BIT-NEXT:    [[AGG_RESULT_IMAGP2:%.*]] = getelementptr inbounds nuw { 
float, float }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BIT-NEXT:    [[AGG_RESULT_IMAG:%.*]] = load float, ptr 
[[AGG_RESULT_IMAGP2]], align 4
-// 32BIT-NEXT:    [[AGG_RESULT_REALP3:%.*]] = getelementptr inbounds nuw { 
float, float }, ptr [[AGG_RESULT]], i32 0, i32 0
-// 32BIT-NEXT:    [[AGG_RESULT_IMAGP4:%.*]] = getelementptr inbounds nuw { 
float, float }, ptr [[AGG_RESULT]], i32 0, i32 1
-// 32BIT-NEXT:    store float [[AGG_RESULT_REAL]], ptr [[AGG_RESULT_REALP3]], 
align 4
-// 32BIT-NEXT:    store float [[AGG_RESULT_IMAG]], ptr [[AGG_RESULT_IMAGP4]], 
align 4
-// 32BIT-NEXT:    ret void
+// 32BIT-CLANG22-LABEL: @testcmplxf(
+// 32BIT-CLANG22-NEXT:  entry:
+// 32BIT-CLANG22-NEXT:    [[REAL_ADDR:%.*]] = alloca float, align 4
+// 32BIT-CLANG22-NEXT:    [[IMAG_ADDR:%.*]] = alloca float, align 4
+// 32BIT-CLANG22-NEXT:    store float [[REAL:%.*]], ptr [[REAL_ADDR]], align 4
+// 32BIT-CLANG22-NEXT:    store float [[IMAG:%.*]], ptr [[IMAG...
[truncated]

``````````

</details>


https://github.com/llvm/llvm-project/pull/208917
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to