diff --git a/flang/lib/Lower/ConvertExprToHLFIR.cpp b/flang/lib/Lower/ConvertExprToHLFIR.cpp index 04b63f92a1fb4..da21d407e927d 100644 --- a/flang/lib/Lower/ConvertExprToHLFIR.cpp +++ b/flang/lib/Lower/ConvertExprToHLFIR.cpp @@ -30,6 +30,7 @@ #include "flang/Optimizer/Builder/Runtime/Derived.h" #include "flang/Optimizer/Builder/Runtime/Pointer.h" #include "flang/Optimizer/Builder/Todo.h" +#include "flang/Optimizer/Dialect/FIRAttr.h" #include "flang/Optimizer/HLFIR/HLFIROps.h" #include "mlir/IR/IRMapping.h" #include "llvm/ADT/TypeSwitch.h" @@ -125,6 +126,19 @@ class HlfirDesignatorBuilder { hlfir::ElementalAddrOp convertVectorSubscriptedExprToElementalAddr( const Fortran::lower::SomeExpr &designatorExpr); + std::tuple + genComponentDesignatorTypeAndAttributes( + const Fortran::semantics::Symbol &componentSym, mlir::Type fieldType, + bool isVolatile) { + if (mayHaveNonDefaultLowerBounds(componentSym)) { + mlir::Type boxType = fir::BoxType::get(fieldType, isVolatile); + return std::make_tuple(boxType, + fir::FortranVariableFlagsEnum::contiguous); + } + auto refType = fir::ReferenceType::get(fieldType, isVolatile); + return std::make_tuple(refType, fir::FortranVariableFlagsEnum{}); + } + mlir::Value genComponentShape(const Fortran::semantics::Symbol &componentSym, mlir::Type fieldType) { // For pointers and allocatable components, the @@ -1863,8 +1877,9 @@ class HlfirBuilder { designatorBuilder.genComponentShape(sym, compType); const bool isDesignatorVolatile = fir::isa_volatile_type(baseOp.getType()); - mlir::Type designatorType = - builder.getRefType(compType, isDesignatorVolatile); + auto [designatorType, extraAttributeFlags] = + designatorBuilder.genComponentDesignatorTypeAndAttributes( + sym, compType, isDesignatorVolatile); mlir::Type fieldElemType = hlfir::getFortranElementType(compType); llvm::SmallVector typeParams; @@ -1884,7 +1899,8 @@ class HlfirBuilder { // Convert component symbol attributes to variable attributes. fir::FortranVariableFlagsAttr attrs = - Fortran::lower::translateSymbolAttributes(builder.getContext(), sym); + Fortran::lower::translateSymbolAttributes(builder.getContext(), sym, + extraAttributeFlags); // Get the component designator. auto lhs = builder.create( diff --git a/flang/test/Lower/HLFIR/designators-component-ref.f90 b/flang/test/Lower/HLFIR/designators-component-ref.f90 index 653e28e0a6018..935176becac75 100644 --- a/flang/test/Lower/HLFIR/designators-component-ref.f90 +++ b/flang/test/Lower/HLFIR/designators-component-ref.f90 @@ -126,6 +126,16 @@ subroutine test_array_comp_non_contiguous_slice(a) ! CHECK: %[[VAL_19:.*]] = hlfir.designate %[[VAL_1]]#0{"array_comp"} <%[[VAL_9]]> (%[[VAL_10]]:%[[VAL_11]]:%[[VAL_12]], %[[VAL_14]]:%[[VAL_15]]:%[[VAL_16]]) shape %[[VAL_18]] : (!fir.ref}>>, !fir.shape<2>, index, index, index, index, index, index, !fir.shape<2>) -> !fir.box> end subroutine +subroutine test_array_lbs_array_ctor() + use comp_ref + type(t_array_lbs) :: a(-1:1) + real :: array_comp(2:11,3:22) + a = (/ (t_array_lbs(i, array_comp), i=-1,1) /) +! CHECK: hlfir.designate %{{.+}}#0{"array_comp_lbs"} <%{{.+}}> shape %{{.+}} {fortran_attrs = #fir.var_attrs} +! CHECK-SAME: (!fir.ref}>>, !fir.shapeshift<2>, !fir.shapeshift<2>) +! CHECK-SAME: -> !fir.box> +end subroutine + subroutine test_array_lbs_comp_lbs_1(a) use comp_ref type(t_array_lbs) :: a