@@ -336,7 +336,7 @@ static void genDeclareDataOperandOperationsWithModifier(
336336template <typename EntryOp, typename ExitOp>
337337static void genDataExitOperations (fir::FirOpBuilder &builder,
338338 llvm::SmallVector<mlir::Value> operands,
339- bool structured, bool implicit ) {
339+ bool structured) {
340340 for (mlir::Value operand : operands) {
341341 auto entryOp = mlir::dyn_cast_or_null<EntryOp>(operand.getDefiningOp ());
342342 assert (entryOp && " data entry op expected" );
@@ -346,7 +346,7 @@ static void genDataExitOperations(fir::FirOpBuilder &builder,
346346 varPtr = entryOp.getVarPtr ();
347347 builder.create <ExitOp>(entryOp.getLoc (), entryOp.getAccPtr (), varPtr,
348348 entryOp.getBounds (), entryOp.getDataClause (),
349- structured, implicit ,
349+ structured, entryOp. getImplicit () ,
350350 builder.getStringAttr (*entryOp.getName ()));
351351 }
352352}
@@ -1872,9 +1872,24 @@ createComputeOp(Fortran::lower::AbstractConverter &converter,
18721872 } else if (const auto *reductionClause =
18731873 std::get_if<Fortran::parser::AccClause::Reduction>(
18741874 &clause.u )) {
1875- if (!outerCombined)
1875+ // A reduction clause on a combined construct is treated as if it appeared
1876+ // on the loop construct. So don't generate a reduction clause when it is
1877+ // combined - delay it to the loop. However, a reduction clause on a
1878+ // combined construct implies a copy clause so issue an implicit copy
1879+ // instead.
1880+ if (!outerCombined) {
18761881 genReductions (reductionClause->v , converter, semanticsContext, stmtCtx,
18771882 reductionOperands, reductionRecipes);
1883+ } else {
1884+ auto crtDataStart = dataClauseOperands.size ();
1885+ genDataOperandOperations<mlir::acc::CopyinOp>(
1886+ std::get<Fortran::parser::AccObjectList>(reductionClause->v .t ),
1887+ converter, semanticsContext, stmtCtx, dataClauseOperands,
1888+ mlir::acc::DataClause::acc_reduction,
1889+ /* structured=*/ true , /* implicit=*/ true );
1890+ copyEntryOperands.append (dataClauseOperands.begin () + crtDataStart,
1891+ dataClauseOperands.end ());
1892+ }
18781893 } else if (const auto *defaultClause =
18791894 std::get_if<Fortran::parser::AccClause::Default>(
18801895 &clause.u )) {
@@ -1944,13 +1959,13 @@ createComputeOp(Fortran::lower::AbstractConverter &converter,
19441959
19451960 // Create the exit operations after the region.
19461961 genDataExitOperations<mlir::acc::CopyinOp, mlir::acc::CopyoutOp>(
1947- builder, copyEntryOperands, /* structured=*/ true , /* implicit= */ false );
1962+ builder, copyEntryOperands, /* structured=*/ true );
19481963 genDataExitOperations<mlir::acc::CreateOp, mlir::acc::CopyoutOp>(
1949- builder, copyoutEntryOperands, /* structured=*/ true , /* implicit= */ false );
1964+ builder, copyoutEntryOperands, /* structured=*/ true );
19501965 genDataExitOperations<mlir::acc::AttachOp, mlir::acc::DetachOp>(
1951- builder, attachEntryOperands, /* structured=*/ true , /* implicit= */ false );
1966+ builder, attachEntryOperands, /* structured=*/ true );
19521967 genDataExitOperations<mlir::acc::CreateOp, mlir::acc::DeleteOp>(
1953- builder, createEntryOperands, /* structured=*/ true , /* implicit= */ false );
1968+ builder, createEntryOperands, /* structured=*/ true );
19541969
19551970 builder.restoreInsertionPoint (insPt);
19561971 return computeOp;
@@ -2099,13 +2114,13 @@ static void genACCDataOp(Fortran::lower::AbstractConverter &converter,
20992114
21002115 // Create the exit operations after the region.
21012116 genDataExitOperations<mlir::acc::CopyinOp, mlir::acc::CopyoutOp>(
2102- builder, copyEntryOperands, /* structured=*/ true , /* implicit= */ false );
2117+ builder, copyEntryOperands, /* structured=*/ true );
21032118 genDataExitOperations<mlir::acc::CreateOp, mlir::acc::CopyoutOp>(
2104- builder, copyoutEntryOperands, /* structured=*/ true , /* implicit= */ false );
2119+ builder, copyoutEntryOperands, /* structured=*/ true );
21052120 genDataExitOperations<mlir::acc::AttachOp, mlir::acc::DetachOp>(
2106- builder, attachEntryOperands, /* structured=*/ true , /* implicit= */ false );
2121+ builder, attachEntryOperands, /* structured=*/ true );
21072122 genDataExitOperations<mlir::acc::CreateOp, mlir::acc::DeleteOp>(
2108- builder, createEntryOperands, /* structured=*/ true , /* implicit= */ false );
2123+ builder, createEntryOperands, /* structured=*/ true );
21092124
21102125 builder.restoreInsertionPoint (insPt);
21112126}
@@ -2415,11 +2430,11 @@ genACCExitDataOp(Fortran::lower::AbstractConverter &converter,
24152430 exitDataOp.setFinalizeAttr (builder.getUnitAttr ());
24162431
24172432 genDataExitOperations<mlir::acc::GetDevicePtrOp, mlir::acc::CopyoutOp>(
2418- builder, copyoutOperands, /* structured=*/ false , /* implicit= */ false );
2433+ builder, copyoutOperands, /* structured=*/ false );
24192434 genDataExitOperations<mlir::acc::GetDevicePtrOp, mlir::acc::DeleteOp>(
2420- builder, deleteOperands, /* structured=*/ false , /* implicit= */ false );
2435+ builder, deleteOperands, /* structured=*/ false );
24212436 genDataExitOperations<mlir::acc::GetDevicePtrOp, mlir::acc::DetachOp>(
2422- builder, detachOperands, /* structured=*/ false , /* implicit= */ false );
2437+ builder, detachOperands, /* structured=*/ false );
24232438}
24242439
24252440template <typename Op>
@@ -2594,7 +2609,7 @@ genACCUpdateOp(Fortran::lower::AbstractConverter &converter,
25942609 builder, currentLocation, operands, operandSegments);
25952610
25962611 genDataExitOperations<mlir::acc::GetDevicePtrOp, mlir::acc::UpdateHostOp>(
2597- builder, updateHostOperands, /* structured=*/ false , /* implicit= */ false );
2612+ builder, updateHostOperands, /* structured=*/ false );
25982613
25992614 if (addAsyncAttr)
26002615 updateOp.setAsyncAttr (builder.getUnitAttr ());
@@ -3054,17 +3069,14 @@ genDeclareInFunction(Fortran::lower::AbstractConverter &converter,
30543069 builder.setInsertionPointAfter (declareOp);
30553070 }
30563071 genDataExitOperations<mlir::acc::CreateOp, mlir::acc::DeleteOp>(
3057- builder, createEntryOperands, /* structured=*/ true ,
3058- /* implicit=*/ false );
3072+ builder, createEntryOperands, /* structured=*/ true );
30593073 genDataExitOperations<mlir::acc::DeclareDeviceResidentOp,
30603074 mlir::acc::DeleteOp>(
3061- builder, deviceResidentEntryOperands, /* structured=*/ true ,
3062- /* implicit=*/ false );
3075+ builder, deviceResidentEntryOperands, /* structured=*/ true );
30633076 genDataExitOperations<mlir::acc::CopyinOp, mlir::acc::CopyoutOp>(
3064- builder, copyEntryOperands, /* structured=*/ true , /* implicit= */ false );
3077+ builder, copyEntryOperands, /* structured=*/ true );
30653078 genDataExitOperations<mlir::acc::CreateOp, mlir::acc::CopyoutOp>(
3066- builder, copyoutEntryOperands, /* structured=*/ true ,
3067- /* implicit=*/ false );
3079+ builder, copyoutEntryOperands, /* structured=*/ true );
30683080 });
30693081}
30703082
0 commit comments