[clang] bd0d28a - [CIR] Upstream basic support for ArrayType (#130502)
via cfe-commits
cfe-commits at lists.llvm.org
Thu Mar 13 10:46:34 PDT 2025
Author: Amr Hesham
Date: 2025-03-13T18:46:31+01:00
New Revision: bd0d28ac257d4df68ea7148e7a7c03910c22c1f3
URL: https://github.com/llvm/llvm-project/commit/bd0d28ac257d4df68ea7148e7a7c03910c22c1f3
DIFF: https://github.com/llvm/llvm-project/commit/bd0d28ac257d4df68ea7148e7a7c03910c22c1f3.diff
LOG: [CIR] Upstream basic support for ArrayType (#130502)
This change adds the basic support for ArrayType
Issue #130197
Added:
clang/test/CIR/CodeGen/array.cpp
clang/test/CIR/IR/array.cir
clang/test/CIR/Lowering/array.cpp
Modified:
clang/include/clang/CIR/Dialect/IR/CIRAttrs.h
clang/include/clang/CIR/Dialect/IR/CIRTypes.td
clang/include/clang/CIR/MissingFeatures.h
clang/lib/CIR/CodeGen/CIRGenBuilder.h
clang/lib/CIR/CodeGen/CIRGenTypes.cpp
clang/lib/CIR/Dialect/IR/CIRTypes.cpp
clang/lib/CIR/Lowering/DirectToLLVM/LowerToLLVM.cpp
Removed:
################################################################################
diff --git a/clang/include/clang/CIR/Dialect/IR/CIRAttrs.h b/clang/include/clang/CIR/Dialect/IR/CIRAttrs.h
index 438fb7d09608d..1451ea47c50c8 100644
--- a/clang/include/clang/CIR/Dialect/IR/CIRAttrs.h
+++ b/clang/include/clang/CIR/Dialect/IR/CIRAttrs.h
@@ -30,6 +30,10 @@ class VarDecl;
class RecordDecl;
} // namespace clang
+namespace cir {
+class ArrayType;
+} // namespace cir
+
#define GET_ATTRDEF_CLASSES
#include "clang/CIR/Dialect/IR/CIROpsAttributes.h.inc"
diff --git a/clang/include/clang/CIR/Dialect/IR/CIRTypes.td b/clang/include/clang/CIR/Dialect/IR/CIRTypes.td
index a78e5eae08e33..e285c0f28f113 100644
--- a/clang/include/clang/CIR/Dialect/IR/CIRTypes.td
+++ b/clang/include/clang/CIR/Dialect/IR/CIRTypes.td
@@ -280,6 +280,25 @@ def CIR_BoolType :
}];
}
+//===----------------------------------------------------------------------===//
+// ArrayType
+//===----------------------------------------------------------------------===//
+
+def CIR_ArrayType : CIR_Type<"Array", "array",
+ [DeclareTypeInterfaceMethods<DataLayoutTypeInterface>]> {
+
+ let summary = "CIR array type";
+ let description = [{
+ `CIR.array` represents C/C++ constant arrays.
+ }];
+
+ let parameters = (ins "mlir::Type":$eltType, "uint64_t":$size);
+
+ let assemblyFormat = [{
+ `<` $eltType `x` $size `>`
+ }];
+}
+
//===----------------------------------------------------------------------===//
// FuncType
//===----------------------------------------------------------------------===//
@@ -386,8 +405,8 @@ def VoidPtr : Type<
//===----------------------------------------------------------------------===//
def CIR_AnyType : AnyTypeOf<[
- CIR_VoidType, CIR_BoolType, CIR_IntType, CIR_AnyFloat, CIR_PointerType,
- CIR_FuncType
+ CIR_VoidType, CIR_BoolType, CIR_ArrayType, CIR_IntType, CIR_AnyFloat,
+ CIR_PointerType, CIR_FuncType
]>;
#endif // MLIR_CIR_DIALECT_CIR_TYPES
diff --git a/clang/include/clang/CIR/MissingFeatures.h b/clang/include/clang/CIR/MissingFeatures.h
index e8d3eff79d0b2..6c3d74cf96c64 100644
--- a/clang/include/clang/CIR/MissingFeatures.h
+++ b/clang/include/clang/CIR/MissingFeatures.h
@@ -84,6 +84,8 @@ struct MissingFeatures {
static bool astVarDeclInterface() { return false; }
static bool stackSaveOp() { return false; }
static bool aggValueSlot() { return false; }
+
+ static bool unsizedTypes() { return false; }
};
} // namespace cir
diff --git a/clang/lib/CIR/CodeGen/CIRGenBuilder.h b/clang/lib/CIR/CodeGen/CIRGenBuilder.h
index 01d56963883cc..260ee25719be1 100644
--- a/clang/lib/CIR/CodeGen/CIRGenBuilder.h
+++ b/clang/lib/CIR/CodeGen/CIRGenBuilder.h
@@ -12,6 +12,7 @@
#include "CIRGenTypeCache.h"
#include "clang/CIR/Dialect/Builder/CIRBaseBuilder.h"
+#include "clang/CIR/MissingFeatures.h"
namespace clang::CIRGen {
@@ -33,6 +34,15 @@ class CIRGenBuilderTy : public cir::CIRBaseBuilderTy {
llvm_unreachable("NYI: PPC double-double format for long double");
llvm_unreachable("Unsupported format for long double");
}
+
+ bool isSized(mlir::Type ty) {
+ if (mlir::isa<cir::PointerType, cir::ArrayType, cir::BoolType,
+ cir::IntType>(ty))
+ return true;
+
+ assert(!cir::MissingFeatures::unsizedTypes());
+ return false;
+ }
};
} // namespace clang::CIRGen
diff --git a/clang/lib/CIR/CodeGen/CIRGenTypes.cpp b/clang/lib/CIR/CodeGen/CIRGenTypes.cpp
index dcfaaedc2ef57..aaf3fe240f3c3 100644
--- a/clang/lib/CIR/CodeGen/CIRGenTypes.cpp
+++ b/clang/lib/CIR/CodeGen/CIRGenTypes.cpp
@@ -202,6 +202,14 @@ mlir::Type CIRGenTypes::convertType(QualType type) {
break;
}
+ case Type::ConstantArray: {
+ const ConstantArrayType *arrTy = cast<ConstantArrayType>(ty);
+ mlir::Type elemTy = convertTypeForMem(arrTy->getElementType());
+ resultType = cir::ArrayType::get(builder.getContext(), elemTy,
+ arrTy->getSize().getZExtValue());
+ break;
+ }
+
case Type::FunctionNoProto:
case Type::FunctionProto:
resultType = convertFunctionTypeInternal(type);
diff --git a/clang/lib/CIR/Dialect/IR/CIRTypes.cpp b/clang/lib/CIR/Dialect/IR/CIRTypes.cpp
index 8bdde54ad41f6..6291297492227 100644
--- a/clang/lib/CIR/Dialect/IR/CIRTypes.cpp
+++ b/clang/lib/CIR/Dialect/IR/CIRTypes.cpp
@@ -369,6 +369,22 @@ BoolType::getABIAlignment(const ::mlir::DataLayout &dataLayout,
return 1;
}
+//===----------------------------------------------------------------------===//
+// Definitions
+//===----------------------------------------------------------------------===//
+
+llvm::TypeSize
+ArrayType::getTypeSizeInBits(const ::mlir::DataLayout &dataLayout,
+ ::mlir::DataLayoutEntryListRef params) const {
+ return getSize() * dataLayout.getTypeSizeInBits(getEltType());
+}
+
+uint64_t
+ArrayType::getABIAlignment(const ::mlir::DataLayout &dataLayout,
+ ::mlir::DataLayoutEntryListRef params) const {
+ return dataLayout.getTypeABIAlignment(getEltType());
+}
+
//===----------------------------------------------------------------------===//
// PointerType Definitions
//===----------------------------------------------------------------------===//
diff --git a/clang/lib/CIR/Lowering/DirectToLLVM/LowerToLLVM.cpp b/clang/lib/CIR/Lowering/DirectToLLVM/LowerToLLVM.cpp
index 79ec0696eb180..0cd27ecf1a3bd 100644
--- a/clang/lib/CIR/Lowering/DirectToLLVM/LowerToLLVM.cpp
+++ b/clang/lib/CIR/Lowering/DirectToLLVM/LowerToLLVM.cpp
@@ -577,6 +577,11 @@ static void prepareTypeConverter(mlir::LLVMTypeConverter &converter,
return mlir::LLVM::LLVMPointerType::get(type.getContext(), targetAS);
});
+ converter.addConversion([&](cir::ArrayType type) -> mlir::Type {
+ mlir::Type ty =
+ convertTypeForMemory(converter, dataLayout, type.getEltType());
+ return mlir::LLVM::LLVMArrayType::get(ty, type.getSize());
+ });
converter.addConversion([&](cir::BoolType type) -> mlir::Type {
return mlir::IntegerType::get(type.getContext(), 1,
mlir::IntegerType::Signless);
diff --git a/clang/test/CIR/CodeGen/array.cpp b/clang/test/CIR/CodeGen/array.cpp
new file mode 100644
index 0000000000000..02ecdc11e1d94
--- /dev/null
+++ b/clang/test/CIR/CodeGen/array.cpp
@@ -0,0 +1,26 @@
+// RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux-gnu -fclangir -emit-cir %s -o - 2>&1 | FileCheck %s
+
+int a[10];
+// CHECK: cir.global external @a : !cir.array<!cir.int<s, 32> x 10>
+
+int aa[10][5];
+// CHECK: cir.global external @aa : !cir.array<!cir.array<!cir.int<s, 32> x 5> x 10>
+
+extern int b[10];
+// CHECK: cir.global external @b : !cir.array<!cir.int<s, 32> x 10>
+
+extern int bb[10][5];
+// CHECK: cir.global external @bb : !cir.array<!cir.array<!cir.int<s, 32> x 5> x 10>
+
+void f() {
+ int l[10];
+ // CHECK: %[[ARR:.*]] = cir.alloca !cir.array<!cir.int<s, 32> x 10>, !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>, ["l"]
+}
+
+void f2(int p[10]) {}
+// CHECK: cir.func @f2(%arg0: !cir.ptr<!cir.int<s, 32>>
+// CHECK: cir.alloca !cir.ptr<!cir.int<s, 32>>, !cir.ptr<!cir.ptr<!cir.int<s, 32>>>, ["p", init]
+
+void f3(int pp[10][5]) {}
+// CHECK: cir.func @f3(%arg0: !cir.ptr<!cir.array<!cir.int<s, 32> x 5>>
+// CHECK: cir.alloca !cir.ptr<!cir.array<!cir.int<s, 32> x 5>>, !cir.ptr<!cir.ptr<!cir.array<!cir.int<s, 32> x 5>>>
diff --git a/clang/test/CIR/IR/array.cir b/clang/test/CIR/IR/array.cir
new file mode 100644
index 0000000000000..293a202d18a92
--- /dev/null
+++ b/clang/test/CIR/IR/array.cir
@@ -0,0 +1,51 @@
+// RUN: cir-opt %s | FileCheck %s
+
+module {
+
+cir.global external @a : !cir.array<!cir.int<s, 32> x 10>
+// CHECK: cir.global external @a : !cir.array<!cir.int<s, 32> x 10>
+
+cir.global external @aa : !cir.array<!cir.array<!cir.int<s, 32> x 10> x 10>
+// CHECK: cir.global external @aa : !cir.array<!cir.array<!cir.int<s, 32> x 10> x 10>
+
+cir.global external @b : !cir.array<!cir.int<s, 32> x 10>
+// CHECK: cir.global external @b : !cir.array<!cir.int<s, 32> x 10>
+
+cir.global external @bb : !cir.array<!cir.array<!cir.int<s, 32> x 10> x 10>
+// CHECK: cir.global external @bb : !cir.array<!cir.array<!cir.int<s, 32> x 10> x 10>
+
+cir.func @f() {
+ %0 = cir.alloca !cir.array<!cir.int<s, 32> x 10>, !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>, ["l"] {alignment = 4 : i64}
+ cir.return
+}
+
+// CHECK: cir.func @f() {
+// CHECK: %0 = cir.alloca !cir.array<!cir.int<s, 32> x 10>, !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>, ["l"] {alignment = 4 : i64}
+// CHECK: cir.return
+// CHECK: }
+
+cir.func @f2(%arg0: !cir.ptr<!cir.int<s, 32>>) {
+ %0 = cir.alloca !cir.ptr<!cir.int<s, 32>>, !cir.ptr<!cir.ptr<!cir.int<s, 32>>>, ["p", init] {alignment = 8 : i64}
+ cir.store %arg0, %0 : !cir.ptr<!cir.int<s, 32>>, !cir.ptr<!cir.ptr<!cir.int<s, 32>>>
+ cir.return
+}
+
+// CHECK: cir.func @f2(%arg0: !cir.ptr<!cir.int<s, 32>>) {
+// CHECK: %0 = cir.alloca !cir.ptr<!cir.int<s, 32>>, !cir.ptr<!cir.ptr<!cir.int<s, 32>>>, ["p", init] {alignment = 8 : i64}
+// CHECK: cir.store %arg0, %0 : !cir.ptr<!cir.int<s, 32>>, !cir.ptr<!cir.ptr<!cir.int<s, 32>>>
+// CHECK: cir.return
+// CHECK: }
+
+cir.func @f3(%arg0: !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>) {
+ %0 = cir.alloca !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>, !cir.ptr<!cir.ptr<!cir.array<!cir.int<s, 32> x 10>>>, ["pp", init] {alignment = 8 : i64}
+ cir.store %arg0, %0 : !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>, !cir.ptr<!cir.ptr<!cir.array<!cir.int<s, 32> x 10>>>
+ cir.return
+}
+
+// CHECK: cir.func @f3(%arg0: !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>) {
+// CHECK: %0 = cir.alloca !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>, !cir.ptr<!cir.ptr<!cir.array<!cir.int<s, 32> x 10>>>, ["pp", init] {alignment = 8 : i64}
+// CHECK: cir.store %arg0, %0 : !cir.ptr<!cir.array<!cir.int<s, 32> x 10>>, !cir.ptr<!cir.ptr<!cir.array<!cir.int<s, 32> x 10>>>
+// CHECK: cir.return
+// CHECK: }
+
+}
diff --git a/clang/test/CIR/Lowering/array.cpp b/clang/test/CIR/Lowering/array.cpp
new file mode 100644
index 0000000000000..42208a81caea2
--- /dev/null
+++ b/clang/test/CIR/Lowering/array.cpp
@@ -0,0 +1,27 @@
+// RUN: %clang_cc1 -std=c++20 -triple x86_64-unknown-linux-gnu -fclangir -emit-llvm %s -o - 2>&1 | FileCheck %s
+
+int a[10];
+// CHECK: @a = external dso_local global [10 x i32]
+
+int aa[10][5];
+// CHECK: @aa = external dso_local global [10 x [5 x i32]]
+
+extern int b[10];
+// CHECK: @b = external dso_local global [10 x i32]
+
+extern int bb[10][5];
+// CHECK: @bb = external dso_local global [10 x [5 x i32]]
+
+void f() {
+ int l[10];
+}
+// CHECK: define void @f()
+// CHECK-NEXT: alloca [10 x i32], i64 1, align 16
+
+void f2(int p[10]) {}
+// CHECK: define void @f2(ptr {{%.*}})
+// CHECK-NEXT: alloca ptr, i64 1, align 8
+
+void f3(int pp[10][5]) {}
+// CHECK: define void @f3(ptr {{%.*}})
+// CHECK-NEXT: alloca ptr, i64 1, align 8
More information about the cfe-commits
mailing list