CIRCT 23.0.0git
Loading...
Searching...
No Matches
SVTraceIVerilog.cpp
Go to the documentation of this file.
1//===- SVTraceIVerilog.cpp - Generator Callout Pass -----------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This pass adds the necessary instrumentation to a HWModule to trigger
10// tracing in an iverilog simulation.
11//
12//===----------------------------------------------------------------------===//
13
18#include "mlir/IR/Builders.h"
19#include "mlir/Pass/Pass.h"
20#include "llvm/Support/Path.h"
21#include "llvm/Support/Process.h"
22
23namespace circt {
24namespace sv {
25#define GEN_PASS_DEF_SVTRACEIVERILOG
26#include "circt/Dialect/SV/SVPasses.h.inc"
27} // namespace sv
28} // namespace circt
29
30using namespace circt;
31using namespace sv;
32using namespace hw;
33
34//===----------------------------------------------------------------------===//
35// SVTraceIVerilogPass
36//===----------------------------------------------------------------------===//
37
38namespace {
39
40struct SVTraceIVerilogPass
41 : public circt::sv::impl::SVTraceIVerilogBase<SVTraceIVerilogPass> {
42 using Base::Base;
43 void runOnOperation() override;
44};
45
46} // end anonymous namespace
47
48void SVTraceIVerilogPass::runOnOperation() {
49 mlir::ModuleOp mod = getOperation();
50
51 if (topOnly) {
52 auto &graph = getAnalysis<InstanceGraph>();
53 auto topLevelNodes = graph.getInferredTopLevelNodes();
54 if (failed(topLevelNodes) || topLevelNodes->size() != 1) {
55 mod.emitError("Expected exactly one top level node");
56 return signalPassFailure();
57 }
58 hw::HWModuleOp top =
59 dyn_cast_or_null<hw::HWModuleOp>(*topLevelNodes->front()->getModule());
60 if (!top) {
61 mod.emitError("top module is not a HWModuleOp");
62 return signalPassFailure();
63 }
64 targetModuleName.setValue(top.getName().str());
65 }
66
67 for (auto hwmod : mod.getOps<hw::HWModuleOp>()) {
68 if (!targetModuleName.empty() &&
69 hwmod.getName() != targetModuleName.getValue())
70 continue;
71 OpBuilder builder(hwmod.getBodyBlock(), hwmod.getBodyBlock()->begin());
72 std::string traceMacro;
73 llvm::raw_string_ostream ss(traceMacro);
74 auto modName = hwmod.getName();
75 ss << "initial begin\n $dumpfile (\"" << directoryName.getValue()
76 << modName << ".vcd\");\n $dumpvars (0, " << modName
77 << ");\n #1;\nend\n";
78 sv::VerbatimOp::create(builder, hwmod.getLoc(), ss.str());
79 }
80}
The InstanceGraph op interface, see InstanceGraphInterface.td for more details.
Definition hw.py:1
Definition sv.py:1