@@ -1331,63 +1331,36 @@ bool hlfir::elementalOpMustProduceTemp(hlfir::ElementalOp elemental) {
13311331std::pair<hlfir::Entity, mlir::Value>
13321332hlfir::createTempFromMold (mlir::Location loc, fir::FirOpBuilder &builder,
13331333 hlfir::Entity mold) {
1334+ assert (!mold.isAssumedRank () &&
1335+ " cannot create temporary from assumed-rank mold" );
13341336 llvm::SmallVector<mlir::Value> lenParams;
13351337 hlfir::genLengthParameters (loc, builder, mold, lenParams);
13361338 llvm::StringRef tmpName{" .tmp" };
1337- mlir::Value alloc;
1338- mlir::Value isHeapAlloc;
1339- mlir::Value shape{};
1340- fir::FortranVariableFlagsAttr declAttrs;
13411339
1342- if (mold.isPolymorphic ()) {
1343- // Create unallocated polymorphic temporary using the dynamic type
1344- // of the mold. The static type of the temporary matches
1345- // the static type of the mold, but then the dynamic type
1346- // of the mold is applied to the temporary's descriptor.
1347-
1348- if (mold.isArray ())
1349- hlfir::genShape (loc, builder, mold);
1350-
1351- // Create polymorphic allocatable box on the stack.
1352- mlir::Type boxHeapType = fir::HeapType::get (fir::unwrapRefType (
1353- mlir::cast<fir::BaseBoxType>(mold.getType ()).getEleTy ()));
1354- // The box must be initialized, because AllocatableApplyMold
1355- // may read its contents (e.g. for checking whether it is allocated).
1356- alloc = fir::factory::genNullBoxStorage (builder, loc,
1357- fir::ClassType::get (boxHeapType));
1358- // The temporary is unallocated even after AllocatableApplyMold below.
1359- // If the temporary is used as assignment LHS it will be automatically
1360- // allocated on the heap, as long as we use Assign family
1361- // runtime functions. So set MustFree to true.
1362- isHeapAlloc = builder.createBool (loc, true );
1363- declAttrs = fir::FortranVariableFlagsAttr::get (
1364- builder.getContext (), fir::FortranVariableFlagsEnum::allocatable);
1365- } else if (mold.isArray ()) {
1366- mlir::Type sequenceType =
1367- hlfir::getFortranElementOrSequenceType (mold.getType ());
1340+ mlir::Value shape{};
1341+ llvm::SmallVector<mlir::Value> extents;
1342+ if (mold.isArray ()) {
13681343 shape = hlfir::genShape (loc, builder, mold);
1369- auto extents = hlfir::getIndexExtents (loc, builder, shape);
1370- alloc = builder.createHeapTemporary (loc, sequenceType, tmpName, extents,
1371- lenParams);
1372- isHeapAlloc = builder.createBool (loc, true );
1373- } else {
1374- alloc = builder.createTemporary (loc, mold.getFortranElementType (), tmpName,
1375- /* shape=*/ std::nullopt , lenParams);
1376- isHeapAlloc = builder.createBool (loc, false );
1377- }
1378- auto declareOp =
1379- builder.create <hlfir::DeclareOp>(loc, alloc, tmpName, shape, lenParams,
1380- /* dummy_scope=*/ nullptr , declAttrs);
1381- if (mold.isPolymorphic ()) {
1382- int rank = mold.getRank ();
1383- // TODO: should probably read rank from the mold.
1384- if (rank < 0 )
1385- TODO (loc, " create temporary for assumed rank polymorphic" );
1386- fir::runtime::genAllocatableApplyMold (builder, loc, alloc,
1387- mold.getFirBase (), rank);
1344+ extents = hlfir::getExplicitExtentsFromShape (shape, builder);
13881345 }
13891346
1390- return {hlfir::Entity{declareOp.getBase ()}, isHeapAlloc};
1347+ bool useStack = !mold.isArray () && !mold.isPolymorphic ();
1348+ auto genTempDeclareOp =
1349+ [](fir::FirOpBuilder &builder, mlir::Location loc, mlir::Value memref,
1350+ llvm::StringRef name, mlir::Value shape,
1351+ llvm::ArrayRef<mlir::Value> typeParams,
1352+ fir::FortranVariableFlagsAttr attrs) -> mlir::Value {
1353+ auto declareOp =
1354+ builder.create <hlfir::DeclareOp>(loc, memref, name, shape, typeParams,
1355+ /* dummy_scope=*/ nullptr , attrs);
1356+ return declareOp.getBase ();
1357+ };
1358+
1359+ auto [base, isHeapAlloc] = builder.createAndDeclareTemp (
1360+ loc, mold.getElementOrSequenceType (), shape, extents, lenParams,
1361+ genTempDeclareOp, mold.isPolymorphic () ? mold.getBase () : nullptr ,
1362+ useStack, tmpName);
1363+ return {hlfir::Entity{base}, builder.createBool (loc, isHeapAlloc)};
13911364}
13921365
13931366hlfir::Entity hlfir::createStackTempFromMold (mlir::Location loc,
0 commit comments