@@ -180,26 +180,46 @@ void hlfir::AssignOp::getEffects(
180180// DeclareOp
181181// ===----------------------------------------------------------------------===//
182182
183- // / Given a FIR memory type, and information about non default lower bounds, get
184- // / the related HLFIR variable type.
185- mlir::Type hlfir::DeclareOp::getHLFIRVariableType (mlir::Type inputType,
186- bool hasExplicitLowerBounds) {
183+ static std::pair<mlir::Type, mlir::Type>
184+ getDeclareOutputTypes (mlir::Type inputType, bool hasExplicitLowerBounds) {
185+ // Drop pointer/allocatable attribute of descriptor values. Only descriptor
186+ // addresses are ALLOCATABLE/POINTER. The HLFIR box result of an hlfir.declare
187+ // without those attributes should not have these attributes set.
188+ if (auto baseBoxType = mlir::dyn_cast<fir::BaseBoxType>(inputType))
189+ if (baseBoxType.isPointerOrAllocatable ()) {
190+ mlir::Type boxWithoutAttributes =
191+ baseBoxType.getBoxTypeWithNewAttr (fir::BaseBoxType::Attribute::None);
192+ return {boxWithoutAttributes, boxWithoutAttributes};
193+ }
187194 mlir::Type type = fir::unwrapRefType (inputType);
188195 if (mlir::isa<fir::BaseBoxType>(type))
189- return inputType;
196+ return { inputType, inputType} ;
190197 if (auto charType = mlir::dyn_cast<fir::CharacterType>(type))
191- if (charType.hasDynamicLen ())
192- return fir::BoxCharType::get (charType.getContext (), charType.getFKind ());
198+ if (charType.hasDynamicLen ()) {
199+ mlir::Type hlfirType =
200+ fir::BoxCharType::get (charType.getContext (), charType.getFKind ());
201+ return {hlfirType, inputType};
202+ }
193203
194204 auto seqType = mlir::dyn_cast<fir::SequenceType>(type);
195205 bool hasDynamicExtents =
196206 seqType && fir::sequenceWithNonConstantShape (seqType);
197207 mlir::Type eleType = seqType ? seqType.getEleTy () : type;
198208 bool hasDynamicLengthParams = fir::characterWithDynamicLen (eleType) ||
199209 fir::isRecordWithTypeParameters (eleType);
200- if (hasExplicitLowerBounds || hasDynamicExtents || hasDynamicLengthParams)
201- return fir::BoxType::get (type, fir::isa_volatile_type (inputType));
202- return inputType;
210+ if (hasExplicitLowerBounds || hasDynamicExtents || hasDynamicLengthParams) {
211+ mlir::Type boxType =
212+ fir::BoxType::get (type, fir::isa_volatile_type (inputType));
213+ return {boxType, inputType};
214+ }
215+ return {inputType, inputType};
216+ }
217+
218+ // / Given a FIR memory type, and information about non default lower bounds, get
219+ // / the related HLFIR variable type.
220+ mlir::Type hlfir::DeclareOp::getHLFIRVariableType (mlir::Type inputType,
221+ bool hasExplicitLowerBounds) {
222+ return getDeclareOutputTypes (inputType, hasExplicitLowerBounds).first ;
203223}
204224
205225static bool hasExplicitLowerBounds (mlir::Value shape) {
@@ -256,17 +276,18 @@ void hlfir::DeclareOp::build(mlir::OpBuilder &builder,
256276 std::tie (inputType, memref) = updateDeclaredInputTypeWithVolatility (
257277 inputType, memref, builder, flags);
258278 }
259- mlir::Type hlfirVariableType =
260- getHLFIRVariableType (inputType, hasExplicitLbs);
261- build (builder, result, {hlfirVariableType, inputType }, memref, shape,
279+ auto [ hlfirVariableType, firVarType] =
280+ getDeclareOutputTypes (inputType, hasExplicitLbs);
281+ build (builder, result, {hlfirVariableType, firVarType }, memref, shape,
262282 typeparams, dummy_scope, nameAttr, fortran_attrs, data_attr);
263283}
264284
265285llvm::LogicalResult hlfir::DeclareOp::verify () {
266- if (getMemref ().getType () != getResult (1 ).getType ())
267- return emitOpError (" second result type must match input memref type" );
268- mlir::Type hlfirVariableType = getHLFIRVariableType (
286+ auto [hlfirVariableType, firVarType] = getDeclareOutputTypes (
269287 getMemref ().getType (), hasExplicitLowerBounds (getShape ()));
288+ if (firVarType != getResult (1 ).getType ())
289+ return emitOpError (" second result type must match input memref type, "
290+ " unless it is a box with heap or pointer attribute" );
270291 if (hlfirVariableType != getResult (0 ).getType ())
271292 return emitOpError (" first result type is inconsistent with variable "
272293 " properties: expected " )
@@ -1608,7 +1629,7 @@ void hlfir::AssociateOp::build(
16081629 mlir::Type firVarType;
16091630 auto sourceExprType = mlir::dyn_cast<hlfir::ExprType>(source.getType ());
16101631 if (sourceExprType && sourceExprType.isPolymorphic ())
1611- firVarType = fir::ClassType::get (fir::HeapType::get ( dataType) );
1632+ firVarType = fir::ClassType::get (dataType);
16121633 else
16131634 firVarType = fir::ReferenceType::get (dataType);
16141635
0 commit comments