Co-authored-by: Mike Urbach <mikeurbach@gmail.com>
This commit is contained in:
Deborah Soung 2023-10-20 09:53:39 -07:00 committed by GitHub
parent a9a07b70d2
commit c725e9cfc8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 48 additions and 31 deletions

View File

@ -165,9 +165,20 @@ struct ArrayGetOpConversion : public ConvertOpToLLVMPattern<hw::ArrayGetOp> {
op->getLoc(), IntegerType::get(rewriter.getContext(), 32),
rewriter.getI32IntegerAttr(0));
auto zextIndex = zextByOne(op->getLoc(), rewriter, op.getIndex());
auto gep = rewriter.create<LLVM::GEPOp>(
op->getLoc(), LLVM::LLVMPointerType::get(elemTy), arrPtr,
ArrayRef<Value>({zeroC, zextIndex}));
// During the ongoing migration to opaque types, use the constructor that
// accepts an element type when the array pointer type is opaque, and
// otherwise use the typed pointer constructor.
LLVM::GEPOp gep;
if (cast<LLVM::LLVMPointerType>(arrPtr.getType()).isOpaque())
gep = rewriter.create<LLVM::GEPOp>(
op->getLoc(), LLVM::LLVMPointerType::get(rewriter.getContext()),
elemTy, arrPtr, ArrayRef<Value>({zeroC, zextIndex}));
else
gep = rewriter.create<LLVM::GEPOp>(
op->getLoc(), LLVM::LLVMPointerType::get(elemTy), arrPtr,
ArrayRef<Value>({zeroC, zextIndex}));
rewriter.replaceOpWithNewOp<LLVM::LoadOp>(op, elemTy, gep);
return success();
@ -205,9 +216,18 @@ struct ArraySliceOpConversion
auto zextIndex = zextByOne(op->getLoc(), rewriter, op.getLowIndex());
auto gep = rewriter.create<LLVM::GEPOp>(
op->getLoc(), LLVM::LLVMPointerType::get(elemTy), arrPtr,
ArrayRef<Value>({zeroC, zextIndex}));
// During the ongoing migration to opaque types, use the constructor that
// accepts an element type when the array pointer type is opaque, and
// otherwise use the typed pointer constructor.
LLVM::GEPOp gep;
if (cast<LLVM::LLVMPointerType>(arrPtr.getType()).isOpaque())
gep = rewriter.create<LLVM::GEPOp>(
op->getLoc(), LLVM::LLVMPointerType::get(rewriter.getContext()),
elemTy, arrPtr, ArrayRef<Value>({zeroC, zextIndex}));
else
gep = rewriter.create<LLVM::GEPOp>(
op->getLoc(), LLVM::LLVMPointerType::get(elemTy), arrPtr,
ArrayRef<Value>({zeroC, zextIndex}));
auto cast = rewriter.create<LLVM::BitcastOp>(
op->getLoc(), LLVM::LLVMPointerType::get(dstTy), gep);

2
llvm

@ -1 +1 @@
Subproject commit cc3d2533cc2e4ea06981b86ede5087fbf801e789
Subproject commit 5f5faf407b42342708ce31a1ca3095ddff10dad8

View File

@ -98,30 +98,30 @@ func.func @convertArray(%arg0 : i1, %arg1: !hw.array<2xi32>, %arg2: i32, %arg3:
// CHECK: @convertConstArray
func.func @convertConstArray(%arg0 : i1) {
// COM: Test: simple constant array converted to constant global
// CHECK: %[[VAL_2:.*]] = llvm.mlir.addressof @[[GLOB1]] : !llvm.ptr<array<2 x i32>>
// CHECK-NEXT: %[[VAL_3:.*]] = llvm.load %[[VAL_2]] : !llvm.ptr<array<2 x i32>>
// CHECK: %[[VAL_2:.*]] = llvm.mlir.addressof @[[GLOB1]] : !llvm.ptr
// CHECK-NEXT: %[[VAL_3:.*]] = llvm.load %[[VAL_2]] : !llvm.ptr -> !llvm.array<2 x i32>
%0 = hw.aggregate_constant [0 : i32, 1 : i32] : !hw.array<2xi32>
// COM: Test: when the array argument is already a load from a pointer,
// COM: then don't allocate on the stack again but take that pointer directly as a shortcut
// CHECK-NEXT: %[[VAL_4:.*]] = llvm.mlir.constant(0 : i32) : i32
// CHECK-NEXT: %[[VAL_5:.*]] = llvm.zext %arg0 : i1 to i2
// CHECK-NEXT: %[[VAL_6:.*]] = llvm.getelementptr %[[VAL_2]][%[[VAL_4]], %[[VAL_5]]] : (!llvm.ptr<array<2 x i32>>, i32, i2) -> !llvm.ptr<i32>
// CHECK-NEXT: %{{.+}} = llvm.load %[[VAL_6]] : !llvm.ptr<i32>
// CHECK-NEXT: %[[VAL_6:.*]] = llvm.getelementptr %[[VAL_2]][%[[VAL_4]], %[[VAL_5]]] : (!llvm.ptr, i32, i2) -> !llvm.ptr, i32
// CHECK-NEXT: %{{.+}} = llvm.load %[[VAL_6]] : !llvm.ptr -> i32
%1 = hw.array_get %0[%arg0] : !hw.array<2xi32>, i1
// COM: Test: nested constant array can also converted to a constant global
// CHECK: %[[VAL_7:.*]] = llvm.mlir.addressof @[[GLOB2]] : !llvm.ptr<array<2 x array<2 x i32>>>
// CHECK-NEXT: %{{.+}} = llvm.load %[[VAL_7]] : !llvm.ptr<array<2 x array<2 x i32>>>
// CHECK: %[[VAL_7:.*]] = llvm.mlir.addressof @[[GLOB2]] : !llvm.ptr
// CHECK-NEXT: %{{.+}} = llvm.load %[[VAL_7]] : !llvm.ptr -> !llvm.array<2 x array<2 x i32>>
%2 = hw.aggregate_constant [[0 : i32, 1 : i32], [2 : i32, 3 : i32]] : !hw.array<2x!hw.array<2xi32>>
// COM: the same constants only create one global (note: even if they are in different functions).
// CHECK: %[[VAL_8:.*]] = llvm.mlir.addressof @[[GLOB2]] : !llvm.ptr<array<2 x array<2 x i32>>>
// CHECK-NEXT: %{{.+}} = llvm.load %[[VAL_8]] : !llvm.ptr<array<2 x array<2 x i32>>>
// CHECK: %[[VAL_8:.*]] = llvm.mlir.addressof @[[GLOB2]] : !llvm.ptr
// CHECK-NEXT: %{{.+}} = llvm.load %[[VAL_8]] : !llvm.ptr -> !llvm.array<2 x array<2 x i32>>
%3 = hw.aggregate_constant [[0 : i32, 1 : i32], [2 : i32, 3 : i32]] : !hw.array<2x!hw.array<2xi32>>
// CHECK: %[[VAL_9:.+]] = llvm.mlir.addressof @[[GLOB3]] : !llvm.ptr<array<2 x struct<(i1, i32)>>>
// CHECK-NEXT: {{%.+}} = llvm.load %[[VAL_9]] : !llvm.ptr<array<2 x struct<(i1, i32)>>>
// CHECK: %[[VAL_9:.+]] = llvm.mlir.addressof @[[GLOB3]] : !llvm.ptr
// CHECK-NEXT: {{%.+}} = llvm.load %[[VAL_9]] : !llvm.ptr -> !llvm.array<2 x struct<(i1, i32)>>
%4 = hw.aggregate_constant [[0 : i32, 1 : i1], [2 : i32, 0 : i1]] : !hw.array<2x!hw.struct<a: i32, b: i1>>
return
@ -138,8 +138,8 @@ func.func @convertConstArray(%arg0 : i1) {
// CHECK: @convertConstStruct
func.func @convertConstStruct() {
// CHECK-NEXT: [[V0:%.+]] = llvm.mlir.addressof @[[GLOB4]] : !llvm.ptr<struct<(i2, i32)>>
// CHECK-NEXT: [[V1:%.+]] = llvm.load [[V0]] : !llvm.ptr<struct<(i2, i32)>>
// CHECK-NEXT: [[V0:%.+]] = llvm.mlir.addressof @[[GLOB4]] : !llvm.ptr
// CHECK-NEXT: [[V1:%.+]] = llvm.load [[V0]] : !llvm.ptr -> !llvm.struct<(i2, i32)>
%0 = hw.aggregate_constant [0 : i32, 1 : i2] : !hw.struct<a: i32, b: i2>
// CHECK-NEXT: {{%.+}} = llvm.mlir.constant(0 : i32) : i32
%1 = hw.struct_extract %0["a"] : !hw.struct<a: i32, b: i2>

View File

@ -64,8 +64,8 @@ llhd.entity @convert_prb (%sI1 : !llhd.sig<i1>, %sArr : !llhd.sig<!hw.array<3xi5
// CHECK: %[[VAL_6:.*]] = llvm.getelementptr %[[VAL_2]]{{\[}}%[[VAL_5]]] : (!llvm.ptr<struct<(ptr, i64, i64, i64)>>, i32) -> !llvm.ptr<struct<(ptr, i64, i64, i64)>>
// CHECK: %[[VAL_7:.*]] = llvm.mlir.constant(false) : i1
// CHECK: %[[VAL_8:.*]] = llvm.mlir.constant(0 : i5) : i5
// CHECK: %[[VAL_9:.*]] = llvm.mlir.addressof @{{.+}} : !llvm.ptr<array<3 x i5>>
// CHECK: %[[VAL_10:.*]] = llvm.load %[[VAL_9]] : !llvm.ptr<array<3 x i5>>
// CHECK: %[[VAL_9:.*]] = llvm.mlir.addressof @{{.+}} : !llvm.ptr
// CHECK: %[[VAL_10:.*]] = llvm.load %[[VAL_9]] : !llvm.ptr
// CHECK: %[[VAL_13:.*]] = llvm.mlir.constant(dense<[1000, 0, 0]> : tensor<3xi64>) : !llvm.array<3 x i64>
// CHECK: %[[VAL_14:.*]] = llvm.mlir.constant(1 : i64) : i64
// CHECK: %[[VAL_15:.*]] = llvm.mlir.constant(1 : i32) : i32

View File

@ -10,13 +10,11 @@ llhd.entity @root() -> () {
llhd.entity @initSig () -> () {
%1 = hw.aggregate_constant [ 0 : i1, 1 : i1] : !hw.array<2xi1>
%2 = hw.aggregate_constant [ 0 : i1, 1 : i5] : !hw.struct<f1: i1, f2: i5>
// CHECK: [[V0:%.+]] = llvm.mlir.addressof @{{.+}} : !llvm.ptr<array<2 x i1>>
// CHECK: [[V1:%.+]] = llvm.load [[V0]] : !llvm.ptr<array<2 x i1>>
// CHECK: llvm.store [[V1]], {{%.+}} : !llvm.ptr<array<2 x i1>>
// CHECK: [[V0:%.+]] = llvm.mlir.addressof @{{.+}} : !llvm.ptr
// CHECK: [[V1:%.+]] = llvm.load [[V0]] : !llvm.ptr
%3 = llhd.sig "sig1" %1 : !hw.array<2xi1>
// CHECK: [[V2:%.+]] = llvm.mlir.addressof @{{.+}} : !llvm.ptr<struct<(i5, i1)>>
// CHECK: [[V3:%.+]] = llvm.load [[V2]] : !llvm.ptr<struct<(i5, i1)>>
// CHECK: llvm.store [[V3]], {{%.+}} : !llvm.ptr<struct<(i5, i1)>>
// CHECK: [[V2:%.+]] = llvm.mlir.addressof @{{.+}} : !llvm.ptr
// CHECK: [[V3:%.+]] = llvm.load [[V2]] : !llvm.ptr
%4 = llhd.sig "sig2" %2 : !hw.struct<f1: i1, f2: i5>
}
@ -38,7 +36,6 @@ func.func @getInitValue() -> (i32, i32, i32) {
// CHECK: [[E1:%.+]] = llvm.extractvalue [[RETURN]][0] : !llvm.struct<(i32, i32, i32)>
// CHECK: [[E2:%.+]] = llvm.extractvalue [[RETURN]][1] : !llvm.struct<(i32, i32, i32)>
// CHECK: [[E3:%.+]] = llvm.extractvalue [[RETURN]][2] : !llvm.struct<(i32, i32, i32)>
// CHECK: llvm.store [[E2]], {{%.+}} : !llvm.ptr<i32>
llhd.entity @initMultipleResults () -> () {
%0, %1, %2 = func.call @getInitValue() : () -> (i32, i32, i32)
%3 = llhd.sig "sig" %1 : i32

View File

@ -436,7 +436,7 @@ firrtl.module @X(in %a : !firrtl.uint<4>) {
firrtl.circuit "BadPort" {
firrtl.module @BadPort(in %a : !firrtl.uint<1>) {
// expected-error @+1 {{'firrtl.attach' op operand #0 must be analog type, but got '!firrtl.uint<1>'}}
// expected-error @+1 {{'firrtl.attach' op operand #0 must be variadic of analog type, but got '!firrtl.uint<1>'}}
firrtl.attach %a, %a : !firrtl.uint<1>, !firrtl.uint<1>
}
}

View File

@ -2,7 +2,7 @@
hw.module @signlessOperands() {
%c1_1 = arith.constant 1 : i1
// expected-error @+1 {{'hwarith.add' op operand #0 must be an arbitrary precision integer with signedness semantics, but got 'i1'}}
// expected-error @+1 {{'hwarith.add' op operand #0 must be variadic of an arbitrary precision integer with signedness semantics, but got 'i1'}}
%0 = hwarith.add %c1_1, %c1_1 : (i1, i1) -> i2
}

View File

@ -407,7 +407,7 @@ systemc.module @sensitivityNotInCtor() {
systemc.module @sensitivityNoChannelType() {
systemc.ctor {
%var = systemc.cpp.variable : i1
// expected-error @+1 {{operand #0 must be a SystemC sc_in<T> type or a SystemC sc_inout<T> type or a SystemC sc_out<T> type or a SystemC sc_signal<T> type, but got 'i1'}}
// expected-error @+1 {{operand #0 must be variadic of a SystemC sc_in<T> type or a SystemC sc_inout<T> type or a SystemC sc_out<T> type or a SystemC sc_signal<T> type, but got 'i1'}}
systemc.sensitive %var : i1
}
}