[clang] [Clang][AArch64] Fixed incorrect _BitInt alignment (PR #90602)

via cfe-commits cfe-commits at lists.llvm.org
Thu May 9 02:45:05 PDT 2024


https://github.com/Lukacma updated https://github.com/llvm/llvm-project/pull/90602

>From dfb8a9de874f233c9d3964569f3d5201fd717c16 Mon Sep 17 00:00:00 2001
From: Marian Lukac <Marian.Lukac at arm.com>
Date: Tue, 30 Apr 2024 12:46:48 +0000
Subject: [PATCH 1/4] [Clang][AArch64] Fixed incorrect _BitInt alignment

---
 clang/include/clang/Basic/TargetInfo.h |  8 ++++
 clang/lib/AST/ASTContext.cpp           |  5 +-
 clang/lib/Basic/Targets/AArch64.cpp    |  6 ++-
 clang/lib/Basic/Targets/AArch64.h      |  3 ++
 clang/test/CodeGen/aapcs64-align.cpp   | 64 +++++++++++++++++++++++++-
 5 files changed, 81 insertions(+), 5 deletions(-)

diff --git a/clang/include/clang/Basic/TargetInfo.h b/clang/include/clang/Basic/TargetInfo.h
index 3ced2e7397a75..1b5efa488b6de 100644
--- a/clang/include/clang/Basic/TargetInfo.h
+++ b/clang/include/clang/Basic/TargetInfo.h
@@ -518,6 +518,14 @@ class TargetInfo : public TransferrableTargetInfo,
   /// getInt128Align() - Returns the alignment of Int128.
   unsigned getInt128Align() const { return Int128Align; }
 
+  /// getBitIntAlign/Width - Return aligned size of '_BitInt' and 
+  /// 'unsigned _BitInt' for this target, in bits.
+  unsigned getBitIntWidth(unsigned NumBits) const {
+    return llvm::alignTo(NumBits, getBitIntAlign(NumBits));}
+  virtual unsigned getBitIntAlign(unsigned NumBits) const {
+    return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(), 
+                                getLongLongAlign());}
+
   /// getShortAccumWidth/Align - Return the size of 'signed short _Accum' and
   /// 'unsigned short _Accum' for this target, in bits.
   unsigned getShortAccumWidth() const { return ShortAccumWidth; }
diff --git a/clang/lib/AST/ASTContext.cpp b/clang/lib/AST/ASTContext.cpp
index cbf4932aff9a6..f440af50e08a4 100644
--- a/clang/lib/AST/ASTContext.cpp
+++ b/clang/lib/AST/ASTContext.cpp
@@ -2263,9 +2263,8 @@ TypeInfo ASTContext::getTypeInfoImpl(const Type *T) const {
   }
   case Type::BitInt: {
     const auto *EIT = cast<BitIntType>(T);
-    Align = std::clamp<unsigned>(llvm::PowerOf2Ceil(EIT->getNumBits()),
-                                 getCharWidth(), Target->getLongLongAlign());
-    Width = llvm::alignTo(EIT->getNumBits(), Align);
+    Align = Target->getBitIntAlign(EIT->getNumBits());
+    Width = Target->getBitIntWidth(EIT->getNumBits());
     break;
   }
   case Type::Record:
diff --git a/clang/lib/Basic/Targets/AArch64.cpp b/clang/lib/Basic/Targets/AArch64.cpp
index c8d243a8fb7ae..9a6c197ff77b5 100644
--- a/clang/lib/Basic/Targets/AArch64.cpp
+++ b/clang/lib/Basic/Targets/AArch64.cpp
@@ -1473,6 +1473,10 @@ bool AArch64TargetInfo::validatePointerAuthKey(
 
 bool AArch64TargetInfo::hasInt128Type() const { return true; }
 
+unsigned AArch64TargetInfo::getBitIntAlign(unsigned NumBits) const{
+        return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(), 
+                                    getInt128Align());}
+
 AArch64leTargetInfo::AArch64leTargetInfo(const llvm::Triple &Triple,
                                          const TargetOptions &Opts)
     : AArch64TargetInfo(Triple, Opts) {}
@@ -1674,4 +1678,4 @@ void RenderScript64TargetInfo::getTargetDefines(const LangOptions &Opts,
                                                 MacroBuilder &Builder) const {
   Builder.defineMacro("__RENDERSCRIPT__");
   AArch64leTargetInfo::getTargetDefines(Opts, Builder);
-}
+}
\ No newline at end of file
diff --git a/clang/lib/Basic/Targets/AArch64.h b/clang/lib/Basic/Targets/AArch64.h
index 12fb50286f751..d8cdc814b2a9a 100644
--- a/clang/lib/Basic/Targets/AArch64.h
+++ b/clang/lib/Basic/Targets/AArch64.h
@@ -202,6 +202,9 @@ class LLVM_LIBRARY_VISIBILITY AArch64TargetInfo : public TargetInfo {
   bool hasBitIntType() const override { return true; }
 
   bool validateTarget(DiagnosticsEngine &Diags) const override;
+
+  unsigned getBitIntAlign(unsigned NumBits) const override;
+ 
 };
 
 class LLVM_LIBRARY_VISIBILITY AArch64leTargetInfo : public AArch64TargetInfo {
diff --git a/clang/test/CodeGen/aapcs64-align.cpp b/clang/test/CodeGen/aapcs64-align.cpp
index de231f2123b97..7a8151022852e 100644
--- a/clang/test/CodeGen/aapcs64-align.cpp
+++ b/clang/test/CodeGen/aapcs64-align.cpp
@@ -1,7 +1,7 @@
 // REQUIRES: arm-registered-target
 // RUN: %clang_cc1 -triple aarch64-none-elf \
 // RUN:   -O2 \
-// RUN:   -emit-llvm -o - %s | FileCheck %s
+// RUN:   -emit-llvm -fexperimental-max-bitint-width=1024 -o - %s | FileCheck %s
 
 extern "C" {
 
@@ -100,4 +100,66 @@ void f5m(int, int, int, int, int, P16);
 // CHECK: declare void @f5(i32 noundef, [2 x i64])
 // CHECK: declare void @f5m(i32 noundef, i32 noundef, i32 noundef, i32 noundef, i32 noundef, [2 x i64])
 
+//BitInt alignment
+struct BITINT129 {
+    char ch;
+    unsigned _BitInt(129) v;
+};
+
+int test_bitint129(){
+  return __builtin_offsetof(struct BITINT129, v);
 }
+// CHECK:  ret i32 16 
+
+struct BITINT127 {
+    char ch;
+    _BitInt(127) v;
+};
+
+int test_bitint127(){
+  return __builtin_offsetof(struct BITINT127, v);
+}
+// CHECK:  ret i32 16 
+
+struct BITINT63 {
+    char ch;
+    _BitInt(63) v;
+};
+
+int test_bitint63(){
+  return __builtin_offsetof(struct BITINT63, v);
+}
+// CHECK:  ret i32 8 
+
+struct BITINT32 {
+    char ch;
+    unsigned _BitInt(32) v;
+};
+
+int test_bitint32(){
+  return __builtin_offsetof(struct BITINT32, v);
+}
+// CHECK:  ret i32 4
+
+struct BITINT9 {
+    char ch;
+    unsigned _BitInt(9) v;
+};
+
+int test_bitint9(){
+  return __builtin_offsetof(struct BITINT9, v);
+}
+// CHECK:  ret i32 2
+
+struct BITINT8 {
+    char ch;
+    unsigned _BitInt(8) v;
+};
+
+int test_bitint8(){
+  return __builtin_offsetof(struct BITINT8, v);
+}
+// CHECK:  ret i32 1
+
+}
+

>From 908693b105980253eadb10b18f8b4c0d52f73415 Mon Sep 17 00:00:00 2001
From: Marian Lukac <Marian.Lukac at arm.com>
Date: Tue, 30 Apr 2024 13:02:05 +0000
Subject: [PATCH 2/4] Fix formatting

---
 clang/include/clang/Basic/TargetInfo.h | 10 ++++++----
 clang/lib/Basic/Targets/AArch64.cpp    |  7 ++++---
 clang/lib/Basic/Targets/AArch64.h      |  1 -
 3 files changed, 10 insertions(+), 8 deletions(-)

diff --git a/clang/include/clang/Basic/TargetInfo.h b/clang/include/clang/Basic/TargetInfo.h
index 1b5efa488b6de..488b166a95af7 100644
--- a/clang/include/clang/Basic/TargetInfo.h
+++ b/clang/include/clang/Basic/TargetInfo.h
@@ -518,13 +518,15 @@ class TargetInfo : public TransferrableTargetInfo,
   /// getInt128Align() - Returns the alignment of Int128.
   unsigned getInt128Align() const { return Int128Align; }
 
-  /// getBitIntAlign/Width - Return aligned size of '_BitInt' and 
+  /// getBitIntAlign/Width - Return aligned size of '_BitInt' and
   /// 'unsigned _BitInt' for this target, in bits.
   unsigned getBitIntWidth(unsigned NumBits) const {
-    return llvm::alignTo(NumBits, getBitIntAlign(NumBits));}
+    return llvm::alignTo(NumBits, getBitIntAlign(NumBits));
+  }
   virtual unsigned getBitIntAlign(unsigned NumBits) const {
-    return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(), 
-                                getLongLongAlign());}
+    return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(),
+                                getLongLongAlign());
+  }
 
   /// getShortAccumWidth/Align - Return the size of 'signed short _Accum' and
   /// 'unsigned short _Accum' for this target, in bits.
diff --git a/clang/lib/Basic/Targets/AArch64.cpp b/clang/lib/Basic/Targets/AArch64.cpp
index 9a6c197ff77b5..cc0ae0e2856fd 100644
--- a/clang/lib/Basic/Targets/AArch64.cpp
+++ b/clang/lib/Basic/Targets/AArch64.cpp
@@ -1473,9 +1473,10 @@ bool AArch64TargetInfo::validatePointerAuthKey(
 
 bool AArch64TargetInfo::hasInt128Type() const { return true; }
 
-unsigned AArch64TargetInfo::getBitIntAlign(unsigned NumBits) const{
-        return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(), 
-                                    getInt128Align());}
+unsigned AArch64TargetInfo::getBitIntAlign(unsigned NumBits) const {
+  return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(),
+                              getInt128Align());
+}
 
 AArch64leTargetInfo::AArch64leTargetInfo(const llvm::Triple &Triple,
                                          const TargetOptions &Opts)
diff --git a/clang/lib/Basic/Targets/AArch64.h b/clang/lib/Basic/Targets/AArch64.h
index d8cdc814b2a9a..be6435007a600 100644
--- a/clang/lib/Basic/Targets/AArch64.h
+++ b/clang/lib/Basic/Targets/AArch64.h
@@ -204,7 +204,6 @@ class LLVM_LIBRARY_VISIBILITY AArch64TargetInfo : public TargetInfo {
   bool validateTarget(DiagnosticsEngine &Diags) const override;
 
   unsigned getBitIntAlign(unsigned NumBits) const override;
- 
 };
 
 class LLVM_LIBRARY_VISIBILITY AArch64leTargetInfo : public AArch64TargetInfo {

>From e82b8a78269f28c513d46cef8f18842191aebcb7 Mon Sep 17 00:00:00 2001
From: Marian Lukac <Marian.Lukac at arm.com>
Date: Wed, 8 May 2024 14:47:06 +0000
Subject: [PATCH 3/4] add optional BitIntMaxAlign parameter to TargetInfo

---
 clang/include/clang/Basic/TargetInfo.h | 14 ++++++++++++--
 clang/lib/Basic/Targets/AArch64.cpp    |  6 +-----
 clang/lib/Basic/Targets/AArch64.h      |  2 --
 3 files changed, 13 insertions(+), 9 deletions(-)

diff --git a/clang/include/clang/Basic/TargetInfo.h b/clang/include/clang/Basic/TargetInfo.h
index 488b166a95af7..8a6511b9ced83 100644
--- a/clang/include/clang/Basic/TargetInfo.h
+++ b/clang/include/clang/Basic/TargetInfo.h
@@ -97,6 +97,10 @@ struct TransferrableTargetInfo {
   unsigned char LongLongWidth, LongLongAlign;
   unsigned char Int128Align;
 
+  // This is an optional parameter for targets that
+  // don't use 'LongLongAlign' for '_BitInt' max alignment
+  std::optional<unsigned> BitIntMaxAlign;
+
   // Fixed point bit widths
   unsigned char ShortAccumWidth, ShortAccumAlign;
   unsigned char AccumWidth, AccumAlign;
@@ -518,14 +522,20 @@ class TargetInfo : public TransferrableTargetInfo,
   /// getInt128Align() - Returns the alignment of Int128.
   unsigned getInt128Align() const { return Int128Align; }
 
+  /// getBitIntMaxAlign() - Returns the maximum possible alignment of
+  /// '_BitInt' and 'unsigned _BitInt'.
+  unsigned getBitIntMaxAlign() const {
+    return BitIntMaxAlign.value_or(LongLongAlign);
+  }
+
   /// getBitIntAlign/Width - Return aligned size of '_BitInt' and
   /// 'unsigned _BitInt' for this target, in bits.
   unsigned getBitIntWidth(unsigned NumBits) const {
     return llvm::alignTo(NumBits, getBitIntAlign(NumBits));
   }
-  virtual unsigned getBitIntAlign(unsigned NumBits) const {
+  unsigned getBitIntAlign(unsigned NumBits) const {
     return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(),
-                                getLongLongAlign());
+                                getBitIntMaxAlign());
   }
 
   /// getShortAccumWidth/Align - Return the size of 'signed short _Accum' and
diff --git a/clang/lib/Basic/Targets/AArch64.cpp b/clang/lib/Basic/Targets/AArch64.cpp
index cc0ae0e2856fd..00c5180f70b58 100644
--- a/clang/lib/Basic/Targets/AArch64.cpp
+++ b/clang/lib/Basic/Targets/AArch64.cpp
@@ -154,6 +154,7 @@ AArch64TargetInfo::AArch64TargetInfo(const llvm::Triple &Triple,
   else
     LongWidth = LongAlign = PointerWidth = PointerAlign = 32;
 
+  BitIntMaxAlign = 128;
   MaxVectorAlign = 128;
   MaxAtomicInlineWidth = 128;
   MaxAtomicPromoteWidth = 128;
@@ -1473,11 +1474,6 @@ bool AArch64TargetInfo::validatePointerAuthKey(
 
 bool AArch64TargetInfo::hasInt128Type() const { return true; }
 
-unsigned AArch64TargetInfo::getBitIntAlign(unsigned NumBits) const {
-  return std::clamp<unsigned>(llvm::PowerOf2Ceil(NumBits), getCharWidth(),
-                              getInt128Align());
-}
-
 AArch64leTargetInfo::AArch64leTargetInfo(const llvm::Triple &Triple,
                                          const TargetOptions &Opts)
     : AArch64TargetInfo(Triple, Opts) {}
diff --git a/clang/lib/Basic/Targets/AArch64.h b/clang/lib/Basic/Targets/AArch64.h
index be6435007a600..12fb50286f751 100644
--- a/clang/lib/Basic/Targets/AArch64.h
+++ b/clang/lib/Basic/Targets/AArch64.h
@@ -202,8 +202,6 @@ class LLVM_LIBRARY_VISIBILITY AArch64TargetInfo : public TargetInfo {
   bool hasBitIntType() const override { return true; }
 
   bool validateTarget(DiagnosticsEngine &Diags) const override;
-
-  unsigned getBitIntAlign(unsigned NumBits) const override;
 };
 
 class LLVM_LIBRARY_VISIBILITY AArch64leTargetInfo : public AArch64TargetInfo {

>From 22db03bbfba9a340dc6166db5c8fcd7e23b36fcc Mon Sep 17 00:00:00 2001
From: Lukacma <Marian.Lukac at arm.com>
Date: Wed, 8 May 2024 16:01:40 +0100
Subject: [PATCH 4/4] Update AArch64.cpp

---
 clang/lib/Basic/Targets/AArch64.cpp | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/clang/lib/Basic/Targets/AArch64.cpp b/clang/lib/Basic/Targets/AArch64.cpp
index 00c5180f70b58..c14f705cb430b 100644
--- a/clang/lib/Basic/Targets/AArch64.cpp
+++ b/clang/lib/Basic/Targets/AArch64.cpp
@@ -1675,4 +1675,4 @@ void RenderScript64TargetInfo::getTargetDefines(const LangOptions &Opts,
                                                 MacroBuilder &Builder) const {
   Builder.defineMacro("__RENDERSCRIPT__");
   AArch64leTargetInfo::getTargetDefines(Opts, Builder);
-}
\ No newline at end of file
+}



More information about the cfe-commits mailing list