diff --git a/clang/include/clang/Basic/TargetInfo.h b/clang/include/clang/Basic/TargetInfo.h --- a/clang/include/clang/Basic/TargetInfo.h +++ b/clang/include/clang/Basic/TargetInfo.h @@ -96,6 +96,7 @@ unsigned char LongAccumScale; unsigned char SuitableAlign; + unsigned char GuaranteedAlign; unsigned char DefaultAlignForAttributeAligned; unsigned char MinGlobalAlign; @@ -581,10 +582,16 @@ /// Determine whether constrained floating point is supported on this target. virtual bool hasStrictFP() const { return HasStrictFP; } - /// Return the alignment that is suitable for storing any - /// object with a fundamental alignment requirement. + /// Return the alignment that is the largest alignment ever used for any + /// scalar/SIMD data type on the target machine you are compiling for + /// (including types with an extended alignment requirement). unsigned getSuitableAlign() const { return SuitableAlign; } + /// Return the alignment is meant to be the biggest alignment guaranteed by + /// the memory allocation facilities of the system. In other words, + /// the fundamental alignment. + unsigned getGuaranteedAlign() const { return GuaranteedAlign; } + /// Return the default alignment for __attribute__((aligned)) on /// this target, to be used if no alignment value is specified. unsigned getDefaultAlignForAttributeAligned() const { diff --git a/clang/lib/Basic/TargetInfo.cpp b/clang/lib/Basic/TargetInfo.cpp --- a/clang/lib/Basic/TargetInfo.cpp +++ b/clang/lib/Basic/TargetInfo.cpp @@ -61,7 +61,7 @@ AccumScale = 15; LongAccumScale = 31; - SuitableAlign = 64; + GuaranteedAlign = SuitableAlign = 64; DefaultAlignForAttributeAligned = 128; MinGlobalAlign = 0; // From the glibc documentation, on GNU systems, malloc guarantees 16-byte diff --git a/clang/lib/Basic/Targets/AArch64.cpp b/clang/lib/Basic/Targets/AArch64.cpp --- a/clang/lib/Basic/Targets/AArch64.cpp +++ b/clang/lib/Basic/Targets/AArch64.cpp @@ -67,7 +67,7 @@ MaxAtomicInlineWidth = 128; MaxAtomicPromoteWidth = 128; - LongDoubleWidth = LongDoubleAlign = SuitableAlign = 128; + LongDoubleWidth = LongDoubleAlign = GuaranteedAlign = SuitableAlign = 128; LongDoubleFormat = &llvm::APFloat::IEEEquad(); BFloat16Width = BFloat16Align = 16; @@ -835,7 +835,7 @@ WCharType = SignedInt; UseSignedCharForObjCBool = false; - LongDoubleWidth = LongDoubleAlign = SuitableAlign = 64; + LongDoubleWidth = LongDoubleAlign = GuaranteedAlign = SuitableAlign = 64; LongDoubleFormat = &llvm::APFloat::IEEEdouble(); UseZeroLengthBitfieldAlignment = false; diff --git a/clang/lib/Basic/Targets/ARC.h b/clang/lib/Basic/Targets/ARC.h --- a/clang/lib/Basic/Targets/ARC.h +++ b/clang/lib/Basic/Targets/ARC.h @@ -27,7 +27,7 @@ : TargetInfo(Triple) { NoAsmVariants = true; LongLongAlign = 32; - SuitableAlign = 32; + GuaranteedAlign = SuitableAlign = 32; DoubleAlign = LongDoubleAlign = 32; SizeType = UnsignedInt; PtrDiffType = SignedInt; diff --git a/clang/lib/Basic/Targets/ARM.cpp b/clang/lib/Basic/Targets/ARM.cpp --- a/clang/lib/Basic/Targets/ARM.cpp +++ b/clang/lib/Basic/Targets/ARM.cpp @@ -24,7 +24,8 @@ void ARMTargetInfo::setABIAAPCS() { IsAAPCS = true; - DoubleAlign = LongLongAlign = LongDoubleAlign = SuitableAlign = 64; + DoubleAlign = LongLongAlign = LongDoubleAlign = GuaranteedAlign = + SuitableAlign = 64; BFloat16Width = BFloat16Align = 16; BFloat16Format = &llvm::APFloat::BFloat(); @@ -74,9 +75,11 @@ IsAAPCS = false; if (IsAAPCS16) - DoubleAlign = LongLongAlign = LongDoubleAlign = SuitableAlign = 64; + DoubleAlign = LongLongAlign = LongDoubleAlign = GuaranteedAlign = + SuitableAlign = 64; else - DoubleAlign = LongLongAlign = LongDoubleAlign = SuitableAlign = 32; + DoubleAlign = LongLongAlign = LongDoubleAlign = GuaranteedAlign = + SuitableAlign = 32; BFloat16Width = BFloat16Align = 16; BFloat16Format = &llvm::APFloat::BFloat(); diff --git a/clang/lib/Basic/Targets/AVR.h b/clang/lib/Basic/Targets/AVR.h --- a/clang/lib/Basic/Targets/AVR.h +++ b/clang/lib/Basic/Targets/AVR.h @@ -35,7 +35,7 @@ LongAlign = 8; LongLongWidth = 64; LongLongAlign = 8; - SuitableAlign = 8; + GuaranteedAlign = SuitableAlign = 8; DefaultAlignForAttributeAligned = 8; HalfWidth = 16; HalfAlign = 8; diff --git a/clang/lib/Basic/Targets/MSP430.h b/clang/lib/Basic/Targets/MSP430.h --- a/clang/lib/Basic/Targets/MSP430.h +++ b/clang/lib/Basic/Targets/MSP430.h @@ -39,7 +39,7 @@ DoubleAlign = LongDoubleAlign = 16; PointerWidth = 16; PointerAlign = 16; - SuitableAlign = 16; + GuaranteedAlign = SuitableAlign = 16; SizeType = UnsignedInt; IntMaxType = SignedLongLong; IntPtrType = SignedInt; diff --git a/clang/lib/Basic/Targets/Mips.h b/clang/lib/Basic/Targets/Mips.h --- a/clang/lib/Basic/Targets/Mips.h +++ b/clang/lib/Basic/Targets/Mips.h @@ -125,7 +125,7 @@ PointerWidth = PointerAlign = 32; PtrDiffType = SignedInt; SizeType = UnsignedInt; - SuitableAlign = 64; + GuaranteedAlign = SuitableAlign = 64; } void setN32N64ABITypes() { @@ -136,7 +136,7 @@ LongDoubleFormat = &llvm::APFloat::IEEEdouble(); } MaxAtomicPromoteWidth = MaxAtomicInlineWidth = 64; - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; } void setN64ABITypes() { diff --git a/clang/lib/Basic/Targets/PPC.h b/clang/lib/Basic/Targets/PPC.h --- a/clang/lib/Basic/Targets/PPC.h +++ b/clang/lib/Basic/Targets/PPC.h @@ -78,7 +78,7 @@ public: PPCTargetInfo(const llvm::Triple &Triple, const TargetOptions &) : TargetInfo(Triple) { - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; SimdDefaultAlign = 128; LongDoubleWidth = LongDoubleAlign = 128; LongDoubleFormat = &llvm::APFloat::PPCDoubleDouble(); @@ -370,7 +370,7 @@ SizeType = UnsignedLong; PtrDiffType = SignedLong; IntPtrType = SignedLong; - SuitableAlign = 64; + GuaranteedAlign = 64; LongDoubleWidth = 64; LongDoubleAlign = DoubleAlign = 32; LongDoubleFormat = &llvm::APFloat::IEEEdouble(); @@ -409,7 +409,7 @@ if (Triple.isOSAIX()) { // TODO: Set appropriate ABI for AIX platform. DataLayout = "E-m:a-i64:64-n32:64"; - SuitableAlign = 64; + GuaranteedAlign = 64; LongDoubleWidth = 64; LongDoubleAlign = DoubleAlign = 32; LongDoubleFormat = &llvm::APFloat::IEEEdouble(); diff --git a/clang/lib/Basic/Targets/RISCV.h b/clang/lib/Basic/Targets/RISCV.h --- a/clang/lib/Basic/Targets/RISCV.h +++ b/clang/lib/Basic/Targets/RISCV.h @@ -39,7 +39,7 @@ LongDoubleWidth = 128; LongDoubleAlign = 128; LongDoubleFormat = &llvm::APFloat::IEEEquad(); - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; WCharType = SignedInt; WIntType = UnsignedInt; } diff --git a/clang/lib/Basic/Targets/Sparc.h b/clang/lib/Basic/Targets/Sparc.h --- a/clang/lib/Basic/Targets/Sparc.h +++ b/clang/lib/Basic/Targets/Sparc.h @@ -214,7 +214,7 @@ // aligned. The SPARCv9 SCD 2.4.1 says 16-byte aligned. LongDoubleWidth = 128; LongDoubleAlign = 128; - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; LongDoubleFormat = &llvm::APFloat::IEEEquad(); MaxAtomicPromoteWidth = MaxAtomicInlineWidth = 64; } diff --git a/clang/lib/Basic/Targets/TCE.h b/clang/lib/Basic/Targets/TCE.h --- a/clang/lib/Basic/Targets/TCE.h +++ b/clang/lib/Basic/Targets/TCE.h @@ -58,7 +58,7 @@ IntAlign = 32; LongAlign = LongLongAlign = 32; PointerAlign = 32; - SuitableAlign = 32; + GuaranteedAlign = SuitableAlign = 32; SizeType = UnsignedInt; IntMaxType = SignedLong; IntPtrType = SignedInt; diff --git a/clang/lib/Basic/Targets/WebAssembly.h b/clang/lib/Basic/Targets/WebAssembly.h --- a/clang/lib/Basic/Targets/WebAssembly.h +++ b/clang/lib/Basic/Targets/WebAssembly.h @@ -46,7 +46,7 @@ explicit WebAssemblyTargetInfo(const llvm::Triple &T, const TargetOptions &) : TargetInfo(T) { NoAsmVariants = true; - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; LargeArrayMinWidth = 128; LargeArrayAlign = 128; SimdDefaultAlign = 128; diff --git a/clang/lib/Basic/Targets/X86.h b/clang/lib/Basic/Targets/X86.h --- a/clang/lib/Basic/Targets/X86.h +++ b/clang/lib/Basic/Targets/X86.h @@ -381,7 +381,7 @@ DoubleAlign = LongLongAlign = 32; LongDoubleWidth = 96; LongDoubleAlign = 32; - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; resetDataLayout(Triple.isOSBinFormatMachO() ? "e-m:o-p:32:32-p270:32:32-p271:32:32-p272:64:64-f64:32:64-" "f80:32-n8:16:32-S128" : @@ -481,7 +481,7 @@ : DarwinTargetInfo(Triple, Opts) { LongDoubleWidth = 128; LongDoubleAlign = 128; - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; MaxVectorAlign = 256; // The watchOS simulator uses the builtin bool type for Objective-C. llvm::Triple T = llvm::Triple(Triple); @@ -655,7 +655,7 @@ LongDoubleAlign = 128; LargeArrayMinWidth = 128; LargeArrayAlign = 128; - SuitableAlign = 128; + GuaranteedAlign = SuitableAlign = 128; SizeType = IsX32 ? UnsignedInt : UnsignedLong; PtrDiffType = IsX32 ? SignedInt : SignedLong; IntPtrType = IsX32 ? SignedInt : SignedLong; @@ -893,7 +893,7 @@ public: AndroidX86_32TargetInfo(const llvm::Triple &Triple, const TargetOptions &Opts) : LinuxTargetInfo(Triple, Opts) { - SuitableAlign = 32; + GuaranteedAlign = SuitableAlign = 32; LongDoubleWidth = 64; LongDoubleFormat = &llvm::APFloat::IEEEdouble(); } diff --git a/clang/lib/Basic/Targets/XCore.h b/clang/lib/Basic/Targets/XCore.h --- a/clang/lib/Basic/Targets/XCore.h +++ b/clang/lib/Basic/Targets/XCore.h @@ -29,7 +29,7 @@ : TargetInfo(Triple) { NoAsmVariants = true; LongLongAlign = 32; - SuitableAlign = 32; + GuaranteedAlign = SuitableAlign = 32; DoubleAlign = LongDoubleAlign = 32; SizeType = UnsignedInt; PtrDiffType = SignedInt; diff --git a/clang/lib/Frontend/InitPreprocessor.cpp b/clang/lib/Frontend/InitPreprocessor.cpp --- a/clang/lib/Frontend/InitPreprocessor.cpp +++ b/clang/lib/Frontend/InitPreprocessor.cpp @@ -882,7 +882,7 @@ // Define __BIGGEST_ALIGNMENT__ to be compatible with gcc. Builder.defineMacro("__BIGGEST_ALIGNMENT__", - Twine(TI.getSuitableAlign() / TI.getCharWidth()) ); + Twine(TI.getGuaranteedAlign() / TI.getCharWidth())); if (!LangOpts.CharIsSigned) Builder.defineMacro("__CHAR_UNSIGNED__"); diff --git a/clang/test/CodeGen/aix_alloca_align.c b/clang/test/CodeGen/aix_alloca_align.c new file mode 100644 --- /dev/null +++ b/clang/test/CodeGen/aix_alloca_align.c @@ -0,0 +1,22 @@ +// RUN: %clang_cc1 -triple=powerpc-ibm-aix-xcoff -S -emit-llvm < %s | \ +// RUN: FileCheck -check-prefix 32BIT %s + +// RUN: %clang_cc1 -triple=powerpc64-ibm-aix-xcoff -S -emit-llvm < %s | \ +// RUN: FileCheck -check-prefix 64BIT %s + +typedef long unsigned int size_t; +extern void *alloca(size_t __size) __attribute__((__nothrow__)); + +void foo() { + char *ptr1 = (char *)alloca(sizeof(char) * 9); + int *ptr2 = (int *)alloca(sizeof(int) * 9); + double *ptr3 = (double *)alloca(sizeof(double) * 9); +} + +// 32BIT: %0 = alloca i8, i32 9, align 16 +// 32BIT: %1 = alloca i8, i32 36, align 16 +// 32BIT: %3 = alloca i8, i32 72, align 16 + +// 64BIT: %0 = alloca i8, i64 9, align 16 +// 64BIT: %1 = alloca i8, i64 36, align 16 +// 64BIT: %3 = alloca i8, i64 72, align 16