Skip to content

Commit 36aa670

Browse files
committed
[Sim] Improve cleanup logic in ProceduralizeSim, NFC
Replace the convergence loop for pruning leftover operations with a reverse-topologically-ordered erasure. Emit a warning for operations that are not dead outside of the TriggeredOp.
1 parent 20e590b commit 36aa670

2 files changed

Lines changed: 34 additions & 33 deletions

File tree

lib/Dialect/Sim/Transforms/ProceduralizeSim.cpp

Lines changed: 17 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
#include "circt/Dialect/Sim/SimOps.h"
1717
#include "circt/Dialect/Sim/SimTypes.h"
1818
#include "circt/Support/Debug.h"
19+
#include "circt/Support/SparseOpSCC.h"
1920
#include "mlir/Dialect/SCF/IR/SCF.h"
2021
#include "mlir/Pass/Pass.h"
2122
#include "llvm/ADT/IndexedMap.h"
@@ -232,7 +233,6 @@ LogicalResult ProceduralizeSimPass::proceduralizePrintOps(
232233
mapping.map(getFileOp.getResult(), clonedGetFile.getResult());
233234

234235
cleanupList.push_back(getFileOp);
235-
cleanupList.push_back(getFileOp.getFileName().getDefiningOp());
236236
}
237237

238238
// Materialize print inputs before creating any conditional blocks.
@@ -269,45 +269,29 @@ LogicalResult ProceduralizeSimPass::proceduralizePrintOps(
269269

270270
PrintFormattedProcOp::create(builder, printOp.getLoc(), procPrintInput,
271271
procPrintStream);
272-
cleanupList.push_back(printOp.getInput().getDefiningOp());
273-
printOp.erase();
272+
cleanupList.push_back(printOp);
274273
}
275274
return success();
276275
}
277276

278277
// Prune the DAGs of formatting fragments left outside of the newly created
279278
// TriggeredOps.
280279
void ProceduralizeSimPass::cleanup() {
281-
SmallVector<Operation *> cleanupNextList;
282-
SmallDenseSet<Operation *> erasedOps;
283-
284-
bool noChange = true;
285-
while (!cleanupList.empty() || !cleanupNextList.empty()) {
286-
287-
if (cleanupList.empty()) {
288-
if (noChange)
289-
break;
290-
cleanupList = std::move(cleanupNextList);
291-
cleanupNextList = {};
292-
noChange = true;
293-
}
294-
295-
auto *opToErase = cleanupList.pop_back_val();
296-
if (erasedOps.contains(opToErase))
297-
continue;
298-
299-
if (opToErase->getUses().empty()) {
300-
// Remove a dead op. If it is a concat remove its operands, too.
301-
if (auto concat = dyn_cast<FormatStringConcatOp>(opToErase))
302-
for (auto operand : concat.getInputs())
303-
cleanupNextList.push_back(operand.getDefiningOp());
304-
opToErase->erase();
305-
erasedOps.insert(opToErase);
306-
noChange = false;
307-
} else {
308-
// Op still has uses, revisit later.
309-
cleanupNextList.push_back(opToErase);
310-
}
280+
SparseOpSCC<OpSCCDirection::Backward> sccs([](Operation *op,
281+
OpOperand &operand) {
282+
return isa<FormatStringType, OutputStreamType>(operand.get().getType()) &&
283+
isa_and_present<SimDialect>(op->getDialect());
284+
});
285+
sccs.visit(cleanupList);
286+
assert(sccs.getNumCyclicSCCs() == 0 &&
287+
"Cyclic graph should have been rejected");
288+
for (auto scc : sccs.reverseTopological()) {
289+
auto *op = cast<Operation *>(scc);
290+
if (op->use_empty())
291+
op->erase();
292+
else
293+
op->emitWarning("Operation has remaining (transitive) users outside of "
294+
"procedural regions.");
311295
}
312296
}
313297

test/Dialect/Sim/proceduralize-sim-errors.mlir

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,3 +18,20 @@ hw.module @stream_block_arg_unsupported(
1818
// expected-error @below {{proceduralization requires stream to be produced by sim.get_file, block arguments are unsupported}}
1919
sim.print %msg on %clk if %en to %stream
2020
}
21+
22+
// -----
23+
24+
hw.module @leftover_value(
25+
in %clk : !seq.clock,
26+
in %en : i1,
27+
in %v : i8,
28+
out lit : !sim.fstring) {
29+
// expected-warning @below {{Operation has remaining (transitive) users outside of procedural regions.}}
30+
%foo = sim.fmt.literal "foo"
31+
// expected-warning @below {{Operation has remaining (transitive) users outside of procedural regions.}}
32+
%fmt = sim.fmt.hex %v, isUpper false specifierWidth 8 : i8
33+
// expected-warning @below {{Operation has remaining (transitive) users outside of procedural regions.}}
34+
%cat = sim.fmt.concat (%foo, %fmt)
35+
sim.print %cat on %clk if %en
36+
hw.output %cat : !sim.fstring
37+
}

0 commit comments

Comments
 (0)