comparison graal/GraalCompiler/src/com/sun/c1x/debug/IdealGraphPrinter.java @ 2684:ed36daed4c43

Add new option PrintIdealGraphToFile and another printer/observer pair to generate a graph representation that can be visualized and inspected with the ideal graph visualizer
author Peter Hofer <peter.hofer@jku.at>
date Mon, 16 May 2011 17:31:53 +0200
parents
children 79590d6b4a7c
comparison
equal deleted inserted replaced
2683:026b21a81651 2684:ed36daed4c43
1 /*
2 * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23 package com.sun.c1x.debug;
24
25 import java.io.*;
26 import java.util.*;
27
28 import com.oracle.graal.graph.*;
29
30 /**
31 * Generates a representation of {@link Graph Graphs} that can be visualized and inspected with the <a
32 * href="http://kenai.com/projects/igv">Ideal Graph Visualizer</a>.
33 */
34 public class IdealGraphPrinter {
35
36 private static class Edge {
37 final int from;
38 final int to;
39 final int index;
40
41 Edge(int from, int to, int index) {
42 this.from = from;
43 this.to = to;
44 this.index = index;
45 }
46 }
47
48 private final HashSet<Class<?>> omittedClasses = new HashSet<Class<?>>();
49 private final PrintStream stream;
50
51 /**
52 * Creates a new {@link IdealGraphPrinter} that writes to the specified output stream.
53 */
54 public IdealGraphPrinter(OutputStream stream) {
55 this.stream = new PrintStream(stream);
56 }
57
58 /**
59 * Adds a node class that is omitted in the output.
60 */
61 public void addOmittedClass(Class<?> clazz) {
62 omittedClasses.add(clazz);
63 }
64
65 /**
66 * Starts a new graph document containing a single group of graphs with the given name, short name and byte code
67 * index (BCI) as properties.
68 */
69 public void begin(String name, String shortName, int bci) {
70 stream.println("<graphDocument><group>");
71 stream.printf(" <properties><p name='name'>%s</p></properties>%n", escape(name));
72 stream.printf(" <method name='%s' shortName='%s' bci='%d'/>%n", escape(name), escape(shortName), bci);
73 }
74
75 /**
76 * Finishes the graph document.
77 */
78 public void end() {
79 stream.println("</group></graphDocument>");
80 stream.flush();
81 }
82
83 /**
84 * Prints an entire {@link Graph} with the specified title, optionally using short names for nodes.
85 */
86 public void print(Graph graph, String title, boolean shortNames) {
87 stream.printf(" <graph name='%s'>%n", escape(title));
88
89 stream.println(" <nodes>");
90 List<Edge> edges = printNodes(graph.getNodes(), shortNames);
91 stream.println(" </nodes>");
92
93 stream.println(" <edges>");
94 for (Edge edge : edges) {
95 printEdge(edge);
96 }
97 stream.println(" </edges>");
98
99 stream.println(" </graph>");
100 }
101
102 private List<Edge> printNodes(Collection<Node> nodes, boolean shortNames) {
103 ArrayList<Edge> edges = new ArrayList<Edge>();
104
105 for (Node node : nodes) {
106 if (node == Node.Null || omittedClasses.contains(node)) {
107 continue;
108 }
109
110 String name;
111 if (shortNames) {
112 name = node.shortName();
113 } else {
114 name = node.toString();
115 }
116
117 stream.printf(" <node id='%d'><properties>", node.id());
118 stream.printf("<p name='idx'>%d</p>", node.id());
119 stream.printf("<p name='name'>%s</p>", escape(name));
120 stream.println("</properties></node>");
121
122 int index = 0;
123 for (Node predecessor : node.predecessors()) {
124 if (predecessor != Node.Null && !omittedClasses.contains(predecessor.getClass())) {
125 edges.add(new Edge(predecessor.id(), node.id(), index));
126 }
127 index++;
128 }
129 for (Node input : node.inputs()) {
130 if (input != Node.Null && !omittedClasses.contains(input.getClass())) {
131 edges.add(new Edge(input.id(), node.id(), index));
132 }
133 index++;
134 }
135 }
136
137 return edges;
138 }
139
140 private void printEdge(Edge edge) {
141 stream.printf(" <edge from='%d' to='%d' index='%d'/>%n", edge.from, edge.to, edge.index);
142 }
143
144 private String escape(String s) {
145 s = s.replace("&", "&amp;");
146 s = s.replace("<", "&lt;");
147 s = s.replace(">", "&gt;");
148 s = s.replace("\"", "&quot;");
149 s = s.replace("'", "&apos;");
150 return s;
151 }
152 }