@@ -1479,16 +1479,15 @@ mlir::Type lowerArrayType(cir::ArrayType type, bool hasValueSemantics,
1479
1479
mlir::TypeConverter prepareTypeConverter (mlir::DataLayout &dataLayout) {
1480
1480
mlir::TypeConverter converter;
1481
1481
converter.addConversion ([&](cir::PointerType type) -> mlir::Type {
1482
- auto pointeeType = type.getPointee ();
1483
- if (mlir::isa<cir::ArrayType>(pointeeType))
1484
- // A pointer to an array gives the array a reference semantics, lower to a
1485
- // memref.
1486
- return lowerArrayType (mlir::cast<cir::ArrayType>(pointeeType),
1487
- /* hasValueSemantics */ false , converter);
1488
- auto ty = convertTypeForMemory (converter, pointeeType);
1489
- // FIXME: The pointee type might not be converted (e.g. struct)
1482
+ auto ty = convertTypeForMemory (
1483
+ converter, type.getPointee ()); // FIXME: The pointee type might not be
1484
+ // converted (e.g. struct)
1490
1485
if (!ty)
1491
1486
return nullptr ;
1487
+ if (isa<cir::ArrayType>(type.getPointee ()))
1488
+ // An array is already lowered as a memref with reference semantics by
1489
+ // default
1490
+ return ty;
1492
1491
// Each level of pointer becomes a level of memref
1493
1492
return mlir::MemRefType::get ({}, ty);
1494
1493
});
@@ -1528,15 +1527,23 @@ mlir::TypeConverter prepareTypeConverter(mlir::DataLayout &dataLayout) {
1528
1527
return mlir::BFloat16Type::get (type.getContext ());
1529
1528
});
1530
1529
converter.addConversion ([&](cir::ArrayType type) -> mlir::Type {
1531
- // Assume we are in a class/struct/union context with value semantics, so
1532
- // lower as a tensor .
1533
- return lowerArrayType (type, /* hasValueSemantics */ true , converter);
1530
+ // Assume we are not in a class/struct/union context with value semantics,
1531
+ // so lower it as a memref to provide reference semantics .
1532
+ return lowerArrayType (type, /* hasValueSemantics */ false , converter);
1534
1533
});
1535
1534
converter.addConversion ([&](cir::VectorType type) -> mlir::Type {
1536
1535
auto ty = converter.convertType (type.getEltType ());
1537
1536
return mlir::VectorType::get (type.getSize (), ty);
1538
1537
});
1539
1538
converter.addConversion ([&](cir::StructType type) -> mlir::Type {
1539
+ auto convertWithValueSemanticsArray = [&](mlir::Type t) {
1540
+ if (mlir::isa<cir::ArrayType>(t))
1541
+ // Inside a class/struct/union, an array has value semantics and is
1542
+ // lowered as a tensor.
1543
+ return lowerArrayType (mlir::cast<cir::ArrayType>(t),
1544
+ /* hasValueSemantics */ true , converter);
1545
+ return converter.convertType (t);
1546
+ };
1540
1547
// FIXME(cir): create separate unions, struct, and classes types.
1541
1548
// Convert struct members.
1542
1549
llvm::SmallVector<mlir::Type> mlirMembers;
@@ -1545,13 +1552,13 @@ mlir::TypeConverter prepareTypeConverter(mlir::DataLayout &dataLayout) {
1545
1552
// TODO(cir): This should be properly validated.
1546
1553
case cir::StructType::Struct:
1547
1554
for (auto ty : type.getMembers ())
1548
- mlirMembers.push_back (converter. convertType (ty));
1555
+ mlirMembers.push_back (convertWithValueSemanticsArray (ty));
1549
1556
break ;
1550
1557
// Unions are lowered as only the largest member.
1551
1558
case cir::StructType::Union: {
1552
1559
auto largestMember = type.getLargestMember (dataLayout);
1553
1560
if (largestMember)
1554
- mlirMembers.push_back (converter. convertType (largestMember));
1561
+ mlirMembers.push_back (convertWithValueSemanticsArray (largestMember));
1555
1562
break ;
1556
1563
}
1557
1564
}
0 commit comments