slang-netlist  0.12.0
Loading...
Searching...
No Matches
NetlistDot.hpp
Go to the documentation of this file.
1#pragma once
2
5
7
8#include <string>
9#include <unordered_set>
10
11namespace slang::netlist {
12
14struct NetlistDot {
15
17 static auto render(NetlistGraph const &netlist, FormatBuffer &buffer) {
18 renderImpl(netlist, buffer, nullptr);
19 }
20
24 static auto render(NetlistGraph const &netlist, FormatBuffer &buffer,
25 std::unordered_set<NetlistNode const *> const &nodes) {
26 renderImpl(netlist, buffer, &nodes);
27 }
28
29private:
33 static auto escapeLabel(std::string_view text) -> std::string {
34 constexpr std::string_view metacharacters = "|<>{}\"\\";
35 std::string result;
36 result.reserve(text.size());
37 for (char c : text) {
38 if (metacharacters.find(c) != std::string_view::npos) {
39 result.push_back('\\');
40 }
41 result.push_back(c);
42 }
43 return result;
44 }
45
46 static void writeNode(FormatBuffer &buffer, NetlistNode const &node) {
47 switch (node.kind) {
48 case NodeKind::Port: {
49 auto const &portNode = node.as<Port>();
50 buffer.format(" N{} [label=\"{} port {}\"]\n", node.ID,
51 toString(portNode.direction), escapeLabel(portNode.name));
52 break;
53 }
54 case NodeKind::Variable: {
55 auto const &varNode = node.as<Variable>();
56 buffer.format(" N{} [label=\"Variable {}\"]\n", node.ID,
57 escapeLabel(varNode.name));
58 break;
59 }
61 buffer.format(" N{} [label=\"Assignment\"]\n", node.ID);
62 break;
63 }
64 case NodeKind::Case: {
65 buffer.format(" N{} [label=\"Case\"]\n", node.ID);
66 break;
67 }
69 buffer.format(" N{} [label=\"Conditional\"]\n", node.ID);
70 break;
71 }
72 case NodeKind::Merge: {
73 buffer.format(" N{} [label=\"Merge\"]\n", node.ID);
74 break;
75 }
76 case NodeKind::State: {
77 auto const &state = node.as<State>();
78 buffer.format(" N{} [label=\"{} {}\"]\n", node.ID,
79 escapeLabel(state.name), toString(state.bounds));
80 break;
81 }
82 case NodeKind::Constant: {
83 auto const &constNode = node.as<Constant>();
84 buffer.format(" N{} [label=\"Const {}\"]\n", node.ID,
85 escapeLabel(constNode.value.toString()));
86 break;
87 }
89 auto const &opNode = node.as<Operation>();
90 // The kind name rather than the symbol, which is ambiguous: `&` is
91 // both bitwise and reduction AND, `-` both negation and subtraction.
92 buffer.format(" N{} [label=\"Op {} [{}]\"]\n", node.ID,
93 escapeLabel(toString(opNode.op)), opNode.width);
94 break;
95 }
96 default:
97 SLANG_UNREACHABLE;
98 }
99 }
100
101 static void
102 renderImpl(NetlistGraph const &netlist, FormatBuffer &buffer,
103 std::unordered_set<NetlistNode const *> const *filter) {
104 auto included = [&](NetlistNode const &node) {
105 return filter == nullptr || filter->count(&node) != 0;
106 };
107
108 buffer.append("digraph {\n");
109 buffer.append(" node [shape=record];\n");
110 for (auto const &node : netlist) {
111 if (!included(*node)) {
112 continue;
113 }
114 writeNode(buffer, *node);
115 }
116 for (auto const &node : netlist) {
117 if (!included(*node)) {
118 continue;
119 }
120 for (auto const &edge : node->getOutEdges()) {
121 if (edge->disabled) {
122 continue;
123 }
124 if (!included(edge->getTargetNode())) {
125 continue;
126 }
127 if (edge->symbol != nullptr && !edge->symbol->empty()) {
128 buffer.format(" N{} -> N{} [label=\"{}{}\"]\n", node->ID,
129 edge->getTargetNode().ID,
130 escapeLabel(edge->symbol->name),
131 toString(edge->bounds));
132 } else {
133 buffer.format(" N{} -> N{}\n", node->ID, edge->getTargetNode().ID);
134 }
135 }
136 }
137 buffer.append("}\n");
138 }
139};
140
141} // namespace slang::netlist
Definition FormatBuffer.hpp:13
Represent the netlist connectivity of an elaborated design.
Definition NetlistGraph.hpp:44
Definition FormatBuffer.hpp:9
auto toString(OperationKind kind) -> std::string_view
The stable identifier for kind, as used in the serialised format.
@ Case
Definition NetlistNode.hpp:25
@ Operation
Definition NetlistNode.hpp:29
@ State
Definition NetlistNode.hpp:27
@ Variable
Definition NetlistNode.hpp:22
@ Port
Definition NetlistNode.hpp:21
@ Merge
Definition NetlistNode.hpp:26
@ Conditional
Definition NetlistNode.hpp:24
@ Constant
Definition NetlistNode.hpp:28
@ Assignment
Definition NetlistNode.hpp:23
A utility class for rendering a netlist graph in DOT format.
Definition NetlistDot.hpp:14
static auto render(NetlistGraph const &netlist, FormatBuffer &buffer)
Render the whole netlist graph.
Definition NetlistDot.hpp:17
static auto render(NetlistGraph const &netlist, FormatBuffer &buffer, std::unordered_set< NetlistNode const * > const &nodes)
Definition NetlistDot.hpp:24