|
59 | 59 | #include "mlir/Dialect/Func/IR/FuncOps.h" |
60 | 60 | #include "mlir/Dialect/OpenACC/Analysis/OpenACCSupport.h" |
61 | 61 | #include "mlir/Dialect/OpenACC/OpenACC.h" |
| 62 | +#include "mlir/Dialect/OpenACC/OpenACCUtilsLoop.h" |
62 | 63 | #include "mlir/Dialect/SCF/IR/SCF.h" |
63 | 64 | #include "mlir/IR/Builders.h" |
64 | 65 | #include "mlir/IR/IRMapping.h" |
@@ -215,22 +216,28 @@ void ACCIfClauseLowering::lowerIfClauseForComputeConstruct( |
215 | 216 | scf::YieldOp::create(rewriter, computeConstructOp.getLoc()); |
216 | 217 |
|
217 | 218 | // Host execution path (false branch) |
218 | | - if (!computeConstructOp.getRegion().hasOneBlock()) { |
219 | | - accSupport->emitNYI(computeConstructOp.getLoc(), |
220 | | - "region with multiple blocks"); |
221 | | - return; |
222 | | - } |
223 | | - |
224 | | - // Don't need to clone original ops, just take them and legalize for host |
225 | | - ifOp.getElseRegion().takeBody(computeConstructOp.getRegion()); |
226 | | - |
227 | | - // Swap acc yield for scf yield |
228 | | - Block &elseBlock = ifOp.getElseRegion().front(); |
229 | | - elseBlock.getTerminator()->erase(); |
230 | | - rewriter.setInsertionPointToEnd(&elseBlock); |
231 | | - scf::YieldOp::create(rewriter, computeConstructOp.getLoc()); |
| 219 | + Region &hostRegion = computeConstructOp.getRegion(); |
| 220 | + if (hostRegion.hasOneBlock()) { |
| 221 | + // Don't need to clone original ops, just take them and legalize for host. |
| 222 | + ifOp.getElseRegion().takeBody(hostRegion); |
| 223 | + |
| 224 | + // Swap acc yield for scf yield. |
| 225 | + Block &elseBlock = ifOp.getElseRegion().front(); |
| 226 | + elseBlock.getTerminator()->erase(); |
| 227 | + rewriter.setInsertionPointToEnd(&elseBlock); |
| 228 | + scf::YieldOp::create(rewriter, computeConstructOp.getLoc()); |
232 | 229 |
|
233 | | - convertHostRegion(computeConstructOp, ifOp.getElseRegion()); |
| 230 | + convertHostRegion(computeConstructOp, ifOp.getElseRegion()); |
| 231 | + } else { |
| 232 | + // scf.if regions must stay single-block. Wrap the original multi-block ACC |
| 233 | + // body in scf.execute_region so it can be hosted in the else branch. |
| 234 | + Block &elseBlock = ifOp.getElseRegion().front(); |
| 235 | + rewriter.setInsertionPoint(elseBlock.getTerminator()); |
| 236 | + IRMapping hostMapping; |
| 237 | + auto hostExecuteRegion = wrapMultiBlockRegionWithSCFExecuteRegion( |
| 238 | + hostRegion, hostMapping, computeConstructOp.getLoc(), rewriter); |
| 239 | + convertHostRegion(computeConstructOp, hostExecuteRegion.getRegion()); |
| 240 | + } |
234 | 241 |
|
235 | 242 | // The original op is now empty and can be erased |
236 | 243 | eraseOps.push_back(computeConstructOp); |
|
0 commit comments