1 // Copyright 2013 the V8 project authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef V8_COMPILER_GRAPH_H_ 6 #define V8_COMPILER_GRAPH_H_ 7 8 #include "src/zone.h" 9 #include "src/zone-containers.h" 10 11 namespace v8 { 12 namespace internal { 13 namespace compiler { 14 15 // Forward declarations. 16 class GraphDecorator; 17 class Node; 18 class Operator; 19 20 21 // Marks are used during traversal of the graph to distinguish states of nodes. 22 // Each node has a mark which is a monotonically increasing integer, and a 23 // {NodeMarker} has a range of values that indicate states of a node. 24 typedef uint32_t Mark; 25 26 27 // NodeIds are identifying numbers for nodes that can be used to index auxiliary 28 // out-of-line data associated with each node. 29 typedef uint32_t NodeId; 30 31 32 class Graph : public ZoneObject { 33 public: 34 explicit Graph(Zone* zone); 35 36 // Base implementation used by all factory methods. 37 Node* NewNodeUnchecked(const Operator* op, int input_count, Node** inputs, 38 bool incomplete = false); 39 40 // Factory that checks the input count. 41 Node* NewNode(const Operator* op, int input_count, Node** inputs, 42 bool incomplete = false); 43 44 // Factories for nodes with static input counts. NewNode(const Operator * op)45 Node* NewNode(const Operator* op) { 46 return NewNode(op, 0, static_cast<Node**>(nullptr)); 47 } NewNode(const Operator * op,Node * n1)48 Node* NewNode(const Operator* op, Node* n1) { return NewNode(op, 1, &n1); } NewNode(const Operator * op,Node * n1,Node * n2)49 Node* NewNode(const Operator* op, Node* n1, Node* n2) { 50 Node* nodes[] = {n1, n2}; 51 return NewNode(op, arraysize(nodes), nodes); 52 } NewNode(const Operator * op,Node * n1,Node * n2,Node * n3)53 Node* NewNode(const Operator* op, Node* n1, Node* n2, Node* n3) { 54 Node* nodes[] = {n1, n2, n3}; 55 return NewNode(op, arraysize(nodes), nodes); 56 } NewNode(const Operator * op,Node * n1,Node * n2,Node * n3,Node * n4)57 Node* NewNode(const Operator* op, Node* n1, Node* n2, Node* n3, Node* n4) { 58 Node* nodes[] = {n1, n2, n3, n4}; 59 return NewNode(op, arraysize(nodes), nodes); 60 } NewNode(const Operator * op,Node * n1,Node * n2,Node * n3,Node * n4,Node * n5)61 Node* NewNode(const Operator* op, Node* n1, Node* n2, Node* n3, Node* n4, 62 Node* n5) { 63 Node* nodes[] = {n1, n2, n3, n4, n5}; 64 return NewNode(op, arraysize(nodes), nodes); 65 } NewNode(const Operator * op,Node * n1,Node * n2,Node * n3,Node * n4,Node * n5,Node * n6)66 Node* NewNode(const Operator* op, Node* n1, Node* n2, Node* n3, Node* n4, 67 Node* n5, Node* n6) { 68 Node* nodes[] = {n1, n2, n3, n4, n5, n6}; 69 return NewNode(op, arraysize(nodes), nodes); 70 } NewNode(const Operator * op,Node * n1,Node * n2,Node * n3,Node * n4,Node * n5,Node * n6,Node * n7)71 Node* NewNode(const Operator* op, Node* n1, Node* n2, Node* n3, Node* n4, 72 Node* n5, Node* n6, Node* n7) { 73 Node* nodes[] = {n1, n2, n3, n4, n5, n6, n7}; 74 return NewNode(op, arraysize(nodes), nodes); 75 } NewNode(const Operator * op,Node * n1,Node * n2,Node * n3,Node * n4,Node * n5,Node * n6,Node * n7,Node * n8)76 Node* NewNode(const Operator* op, Node* n1, Node* n2, Node* n3, Node* n4, 77 Node* n5, Node* n6, Node* n7, Node* n8) { 78 Node* nodes[] = {n1, n2, n3, n4, n5, n6, n7, n8}; 79 return NewNode(op, arraysize(nodes), nodes); 80 } NewNode(const Operator * op,Node * n1,Node * n2,Node * n3,Node * n4,Node * n5,Node * n6,Node * n7,Node * n8,Node * n9)81 Node* NewNode(const Operator* op, Node* n1, Node* n2, Node* n3, Node* n4, 82 Node* n5, Node* n6, Node* n7, Node* n8, Node* n9) { 83 Node* nodes[] = {n1, n2, n3, n4, n5, n6, n7, n8, n9}; 84 return NewNode(op, arraysize(nodes), nodes); 85 } 86 87 // Clone the {node}, and assign a new node id to the copy. 88 Node* CloneNode(const Node* node); 89 zone()90 Zone* zone() const { return zone_; } start()91 Node* start() const { return start_; } end()92 Node* end() const { return end_; } 93 SetStart(Node * start)94 void SetStart(Node* start) { start_ = start; } SetEnd(Node * end)95 void SetEnd(Node* end) { end_ = end; } 96 NodeCount()97 size_t NodeCount() const { return next_node_id_; } 98 99 void Decorate(Node* node); 100 void AddDecorator(GraphDecorator* decorator); 101 void RemoveDecorator(GraphDecorator* decorator); 102 103 private: 104 friend class NodeMarkerBase; 105 106 inline NodeId NextNodeId(); 107 108 Zone* const zone_; 109 Node* start_; 110 Node* end_; 111 Mark mark_max_; 112 NodeId next_node_id_; 113 ZoneVector<GraphDecorator*> decorators_; 114 115 DISALLOW_COPY_AND_ASSIGN(Graph); 116 }; 117 118 119 // A graph decorator can be used to add behavior to the creation of nodes 120 // in a graph. 121 class GraphDecorator : public ZoneObject { 122 public: ~GraphDecorator()123 virtual ~GraphDecorator() {} 124 virtual void Decorate(Node* node) = 0; 125 }; 126 127 } // namespace compiler 128 } // namespace internal 129 } // namespace v8 130 131 #endif // V8_COMPILER_GRAPH_H_ 132