blob: f46b287bd5d6edd4fa91a91e46cdb41174e49ebd [file] [log] [blame]
Mikhail Glushenkovb90cd832008-05-06 16:34:12 +00001//===--- CompilationGraph.h - The LLVM Compiler Driver ----------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open
6// Source License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// Compilation graph - definition.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_TOOLS_LLVMC2_COMPILATION_GRAPH_H
15#define LLVM_TOOLS_LLVMC2_COMPILATION_GRAPH_H
16
17#include "AutoGenerated.h"
18#include "Tool.h"
19
Mikhail Glushenkov0d08db02008-05-06 16:35:25 +000020#include "llvm/ADT/GraphTraits.h"
21#include "llvm/ADT/iterator"
22#include "llvm/ADT/SmallVector.h"
Mikhail Glushenkovb90cd832008-05-06 16:34:12 +000023#include "llvm/ADT/StringMap.h"
24#include "llvm/System/Path.h"
25
Mikhail Glushenkov0d08db02008-05-06 16:35:25 +000026#include <string>
27
Mikhail Glushenkovb90cd832008-05-06 16:34:12 +000028namespace llvmcc {
29
Mikhail Glushenkov0d08db02008-05-06 16:35:25 +000030 class CompilationGraph;
Mikhail Glushenkovb90cd832008-05-06 16:34:12 +000031
Mikhail Glushenkov0d08db02008-05-06 16:35:25 +000032 struct Node {
33 typedef llvm::SmallVector<std::string, 3> sequence_type;
Mikhail Glushenkovb90cd832008-05-06 16:34:12 +000034
Mikhail Glushenkov0d08db02008-05-06 16:35:25 +000035 Node() {}
36 Node(CompilationGraph* G) : OwningGraph(G) {}
37 Node(CompilationGraph* G, Tool* T) : OwningGraph(G), ToolPtr(T) {}
38
39 // Needed to implement NodeChildIterator/GraphTraits
40 CompilationGraph* OwningGraph;
41 // The corresponding Tool.
42 llvm::IntrusiveRefCntPtr<Tool> ToolPtr;
43 // Links to children.
44 sequence_type Children;
Mikhail Glushenkovb90cd832008-05-06 16:34:12 +000045 };
Mikhail Glushenkov0d08db02008-05-06 16:35:25 +000046
47 // This can be generalised to something like value_iterator for maps
48 class NodesIterator : public llvm::StringMap<Node>::iterator {
49 typedef llvm::StringMap<Node>::iterator super;
50 typedef NodesIterator ThisType;
51 typedef Node* pointer;
52 typedef Node& reference;
53
54 public:
55 NodesIterator(super I) : super(I) {}
56
57 inline reference operator*() const {
58 return super::operator->()->second;
59 }
60 inline pointer operator->() const {
61 return &super::operator->()->second;
62 }
63 };
64
65 class CompilationGraph {
66 typedef llvm::StringMap<Node> nodes_map_type;
67 typedef llvm::SmallVector<std::string, 3> tools_vector_type;
68 typedef llvm::StringMap<tools_vector_type> tools_map_type;
69
70 // Map from file extensions to language names.
71 LanguageMap ExtsToLangs;
72 // Map from language names to lists of tool names.
73 tools_map_type ToolsMap;
74 // Map from tool names to Tool objects.
75 nodes_map_type NodesMap;
76
77 public:
78
79 CompilationGraph();
80
81 // insertVertex - insert a new node into the graph.
82 void insertVertex(const llvm::IntrusiveRefCntPtr<Tool> T);
83
84 // insertEdge - Insert a new edge into the graph. This function
85 // assumes that both A and B have been already inserted.
86 void insertEdge(const std::string& A, const std::string& B);
87
88 // Build - Build the target(s) from the set of the input
89 // files. Command-line options are passed implicitly as global
90 // variables.
91 int Build(llvm::sys::Path const& tempDir) const;
92
93 /// viewGraph - This function is meant for use from the debugger.
94 /// You can just say 'call G->viewGraph()' and a ghostview window
95 /// should pop up from the program, displaying the compilation
96 /// graph. This depends on there being a 'dot' and 'gv' program
97 /// in your path.
98 void viewGraph();
99
100 /// Write a CompilationGraph.dot file.
101 void writeGraph();
102
103 // GraphTraits support
104
105 typedef NodesIterator nodes_iterator;
106
107 nodes_iterator nodes_begin() {
108 return NodesIterator(NodesMap.begin());
109 }
110
111 nodes_iterator nodes_end() {
112 return NodesIterator(NodesMap.end());
113 }
114
115 // Return a reference to the node correponding to the given tool
116 // name. Throws std::runtime_error in case of error.
117 Node& getNode(const std::string& ToolName);
118 const Node& getNode(const std::string& ToolName) const;
119
120 // Auto-generated function.
121 friend void PopulateCompilationGraph(CompilationGraph&);
122
123 private:
124 // Helper function - find out which language corresponds to the
125 // suffix of this file
126 const std::string& getLanguage(const llvm::sys::Path& File) const;
127
128 // Return a reference to the tool names list correponding to the
129 // given language name. Throws std::runtime_error in case of
130 // error.
131 const tools_vector_type& getToolsVector(const std::string& LangName) const;
132 };
133
134 // Auxiliary class needed to implement GraphTraits support.
135 class NodeChildIterator : public bidirectional_iterator<Node, ptrdiff_t> {
136 typedef NodeChildIterator ThisType;
137 typedef Node::sequence_type::iterator iterator;
138
139 CompilationGraph* OwningGraph;
140 iterator KeyIter;
141 public:
142 typedef Node* pointer;
143 typedef Node& reference;
144
145 NodeChildIterator(Node* N, iterator I) :
146 OwningGraph(N->OwningGraph), KeyIter(I) {}
147
148 const ThisType& operator=(const ThisType& I) {
149 assert(OwningGraph == I.OwningGraph);
150 KeyIter = I.KeyIter;
151 return *this;
152 }
153
154 inline bool operator==(const ThisType& I) const
155 { return KeyIter == I.KeyIter; }
156 inline bool operator!=(const ThisType& I) const
157 { return KeyIter != I.KeyIter; }
158
159 inline pointer operator*() const {
160 return &OwningGraph->getNode(*KeyIter);
161 }
162 inline pointer operator->() const {
163 return &OwningGraph->getNode(*KeyIter);
164 }
165
166 ThisType& operator++() { ++KeyIter; return *this; } // Preincrement
167 ThisType operator++(int) { // Postincrement
168 ThisType tmp = *this;
169 ++*this;
170 return tmp;
171 }
172
173 inline ThisType& operator--() { --KeyIter; return *this; } // Predecrement
174 inline ThisType operator--(int) { // Postdecrement
175 ThisType tmp = *this;
176 --*this;
177 return tmp;
178 }
179
180 };
181}
182
183namespace llvm {
184 template <>
185 struct GraphTraits<llvmcc::CompilationGraph*> {
186 typedef llvmcc::CompilationGraph GraphType;
187 typedef llvmcc::Node NodeType;
188 typedef llvmcc::NodeChildIterator ChildIteratorType;
189
190 static NodeType* getEntryNode(GraphType* G) {
191 return &G->getNode("root");
192 }
193
194 static ChildIteratorType child_begin(NodeType* N) {
195 return ChildIteratorType(N, N->Children.begin());
196 }
197 static ChildIteratorType child_end(NodeType* N) {
198 return ChildIteratorType(N, N->Children.end());
199 }
200
201 typedef GraphType::nodes_iterator nodes_iterator;
202 static nodes_iterator nodes_begin(GraphType *G) {
203 return G->nodes_begin();
204 }
205 static nodes_iterator nodes_end(GraphType *G) {
206 return G->nodes_end();
207 }
208 };
209
Mikhail Glushenkovb90cd832008-05-06 16:34:12 +0000210}
211
212#endif // LLVM_TOOLS_LLVMC2_COMPILATION_GRAPH_H