pattern_compiler/cfg/
generate_dot.rs1use std::io::Write;
2
3use ::petgraph::Direction;
4use ::petgraph::visit::EdgeRef;
5
6use ::cfg::{ PatternCfg, CfgNodeKind };
7use ::pattern::PatternProvider;
8
9const DOT_BREAK: &str = "<br align=\"left\" />";
10
11fn format_label(label: &str) -> String {
12 label.replace("{", "\\{").replace("}", "\\}").replace("\n", DOT_BREAK)
13}
14
15impl<P> PatternCfg<P> where P: PatternProvider {
16
17 pub fn to_dot(&self, w: &mut Write) -> ::std::io::Result<()> {
18
19 write!(w, "digraph g {{\n")?;
20 write!(w, "node [labeljust=\"l\", shape=record, fontname=\"Courier New\"]\n")?;
21 write!(w, "edge [fontname=\"Courier New\" ]\n\n")?;
22
23 for index in self.graph.node_indices() {
24 let node = &self.graph[index];
25 println!("{:?}", node);
26
27 let label = format_label(&format!("{:?}", node));
28 write!(w, "node_{} [ label=<{}: {}", index.index(), index.index(), label)?;
29
30 if let CfgNodeKind::Leaf(leaf_id) = *node {
31 let bindings = &self.leaf_bindings[&self.leaves[&leaf_id]];
32 write!(w, "{} {}", DOT_BREAK, format_label(&format!("{:#?}", bindings)))?;
33 }
34
35 write!(w, "> ]\n")?;
36
37 for edge in self.graph.edges_directed(index, Direction::Outgoing) {
38 let label = format_label(&format!("{:?}", edge.weight()));
39 write!(w, "node_{} -> node_{} [ label=<{}> ]\n",
40 edge.source().index(), edge.target().index(), label)?;
41 }
42
43 write!(w, "\n")?;
44 }
45
46 write!(w, "}}\n")?;
47 Ok(())
48 }
49
50}
51