OLD | NEW |
1 // Copyright 2015 the V8 project authors. All rights reserved. | 1 // Copyright 2015 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef V8_COMPILER_LIVENESS_ANAYZER_H_ | 5 #ifndef V8_COMPILER_LIVENESS_ANAYZER_H_ |
6 #define V8_COMPILER_LIVENESS_ANAYZER_H_ | 6 #define V8_COMPILER_LIVENESS_ANAYZER_H_ |
7 | 7 |
8 #include "src/bit-vector.h" | 8 #include "src/bit-vector.h" |
9 #include "src/compiler/node.h" | 9 #include "src/compiler/node.h" |
10 #include "src/globals.h" | 10 #include "src/globals.h" |
11 #include "src/zone/zone-containers.h" | 11 #include "src/zone/zone-containers.h" |
12 | 12 |
13 namespace v8 { | 13 namespace v8 { |
14 namespace internal { | 14 namespace internal { |
15 namespace compiler { | 15 namespace compiler { |
16 | 16 |
17 class LivenessAnalyzerBlock; | 17 class LivenessAnalyzerBlock; |
18 class Node; | 18 class Node; |
19 class StateValuesCache; | 19 class StateValuesCache; |
20 | 20 |
21 | |
22 class NonLiveFrameStateSlotReplacer { | 21 class NonLiveFrameStateSlotReplacer { |
23 public: | 22 public: |
24 void ClearNonLiveFrameStateSlots(Node* frame_state, BitVector* liveness); | 23 void ClearNonLiveFrameStateSlots(Node* frame_state, BitVector* liveness); |
25 NonLiveFrameStateSlotReplacer(StateValuesCache* state_values_cache, | 24 NonLiveFrameStateSlotReplacer(StateValuesCache* state_values_cache, |
26 Node* replacement, size_t local_count, | 25 Node* replacement, size_t local_count, |
27 Zone* local_zone) | 26 bool has_accumulator, Zone* local_zone) |
28 : replacement_node_(replacement), | 27 : replacement_node_(replacement), |
29 state_values_cache_(state_values_cache), | 28 state_values_cache_(state_values_cache), |
30 local_zone_(local_zone), | 29 local_zone_(local_zone), |
31 permanently_live_(local_count == 0 ? 1 : static_cast<int>(local_count), | 30 permanently_live_( |
32 local_zone), | 31 static_cast<int>(local_count) + (has_accumulator ? 1 : 0), |
33 inputs_buffer_(local_zone) {} | 32 local_zone), |
| 33 inputs_buffer_(local_zone), |
| 34 has_accumulator_(has_accumulator) {} |
34 | 35 |
| 36 // TODO(leszeks): Not used by bytecode, remove once AST graph builder is gone. |
35 void MarkPermanentlyLive(int var) { permanently_live_.Add(var); } | 37 void MarkPermanentlyLive(int var) { permanently_live_.Add(var); } |
36 | 38 |
37 private: | 39 private: |
38 Node* ClearNonLiveStateValues(Node* frame_state, BitVector* liveness); | 40 Node* ClearNonLiveStateValues(Node* frame_state, BitVector* liveness); |
39 | 41 |
40 StateValuesCache* state_values_cache() { return state_values_cache_; } | 42 StateValuesCache* state_values_cache() { return state_values_cache_; } |
41 Zone* local_zone() { return local_zone_; } | 43 Zone* local_zone() { return local_zone_; } |
42 | 44 |
43 // Node that replaces dead values. | 45 // Node that replaces dead values. |
44 Node* replacement_node_; | 46 Node* replacement_node_; |
45 // Reference to state values cache so that we can create state values | 47 // Reference to state values cache so that we can create state values |
46 // nodes. | 48 // nodes. |
47 StateValuesCache* state_values_cache_; | 49 StateValuesCache* state_values_cache_; |
48 | 50 |
49 Zone* local_zone_; | 51 Zone* local_zone_; |
50 BitVector permanently_live_; | 52 BitVector permanently_live_; |
51 NodeVector inputs_buffer_; | 53 NodeVector inputs_buffer_; |
| 54 |
| 55 bool has_accumulator_; |
52 }; | 56 }; |
53 | 57 |
54 class V8_EXPORT_PRIVATE LivenessAnalyzer { | 58 class V8_EXPORT_PRIVATE LivenessAnalyzer { |
55 public: | 59 public: |
56 LivenessAnalyzer(size_t local_count, Zone* zone); | 60 LivenessAnalyzer(size_t local_count, bool has_accumulator, Zone* zone); |
57 | 61 |
58 LivenessAnalyzerBlock* NewBlock(); | 62 LivenessAnalyzerBlock* NewBlock(); |
59 LivenessAnalyzerBlock* NewBlock(LivenessAnalyzerBlock* predecessor); | 63 LivenessAnalyzerBlock* NewBlock(LivenessAnalyzerBlock* predecessor); |
60 | 64 |
61 void Run(NonLiveFrameStateSlotReplacer* relaxer); | 65 void Run(NonLiveFrameStateSlotReplacer* relaxer); |
62 | 66 |
63 Zone* zone() { return zone_; } | 67 Zone* zone() { return zone_; } |
64 | 68 |
65 void Print(std::ostream& os); | 69 void Print(std::ostream& os); |
66 | 70 |
67 size_t local_count() { return local_count_; } | 71 size_t local_count() { return local_count_; } |
68 | 72 |
69 private: | 73 private: |
70 void Queue(LivenessAnalyzerBlock* block); | 74 void Queue(LivenessAnalyzerBlock* block); |
71 | 75 |
72 Zone* zone_; | 76 Zone* zone_; |
73 ZoneDeque<LivenessAnalyzerBlock*> blocks_; | 77 ZoneDeque<LivenessAnalyzerBlock*> blocks_; |
74 size_t local_count_; | 78 size_t local_count_; |
75 | 79 |
| 80 // TODO(leszeks): Always true for bytecode, remove once AST graph builder is |
| 81 // gone. |
| 82 bool has_accumulator_; |
| 83 |
76 ZoneQueue<LivenessAnalyzerBlock*> queue_; | 84 ZoneQueue<LivenessAnalyzerBlock*> queue_; |
77 }; | 85 }; |
78 | 86 |
79 | 87 |
80 class LivenessAnalyzerBlock { | 88 class LivenessAnalyzerBlock { |
81 public: | 89 public: |
82 friend class LivenessAnalyzer; | 90 friend class LivenessAnalyzer; |
83 | 91 |
84 void Lookup(int var) { entries_.push_back(Entry(Entry::kLookup, var)); } | 92 void Lookup(int var) { entries_.push_back(Entry(Entry::kLookup, var)); } |
85 void Bind(int var) { entries_.push_back(Entry(Entry::kBind, var)); } | 93 void Bind(int var) { entries_.push_back(Entry(Entry::kBind, var)); } |
| 94 void LookupAccumulator() { |
| 95 DCHECK(has_accumulator_); |
| 96 // The last entry is the accumulator entry. |
| 97 entries_.push_back(Entry(Entry::kLookup, live_.length() - 1)); |
| 98 } |
| 99 void BindAccumulator() { |
| 100 DCHECK(has_accumulator_); |
| 101 // The last entry is the accumulator entry. |
| 102 entries_.push_back(Entry(Entry::kBind, live_.length() - 1)); |
| 103 } |
| 104 |
86 void Checkpoint(Node* node) { entries_.push_back(Entry(node)); } | 105 void Checkpoint(Node* node) { entries_.push_back(Entry(node)); } |
87 void AddPredecessor(LivenessAnalyzerBlock* b) { predecessors_.push_back(b); } | 106 void AddPredecessor(LivenessAnalyzerBlock* b) { predecessors_.push_back(b); } |
88 LivenessAnalyzerBlock* GetPredecessor() { | 107 LivenessAnalyzerBlock* GetPredecessor() { |
89 DCHECK(predecessors_.size() == 1); | 108 DCHECK(predecessors_.size() == 1); |
90 return predecessors_[0]; | 109 return predecessors_[0]; |
91 } | 110 } |
92 | 111 |
93 private: | 112 private: |
94 class Entry { | 113 class Entry { |
95 public: | 114 public: |
(...skipping 13 matching lines...) Expand all Loading... |
109 Entry(Kind kind, int var) : kind_(kind), var_(var), node_(nullptr) { | 128 Entry(Kind kind, int var) : kind_(kind), var_(var), node_(nullptr) { |
110 DCHECK(kind != kCheckpoint); | 129 DCHECK(kind != kCheckpoint); |
111 } | 130 } |
112 | 131 |
113 private: | 132 private: |
114 Kind kind_; | 133 Kind kind_; |
115 int var_; | 134 int var_; |
116 Node* node_; | 135 Node* node_; |
117 }; | 136 }; |
118 | 137 |
119 LivenessAnalyzerBlock(size_t id, size_t local_count, Zone* zone); | 138 LivenessAnalyzerBlock(size_t id, size_t local_count, bool has_accumulator, |
| 139 Zone* zone); |
120 void Process(BitVector* result, NonLiveFrameStateSlotReplacer* relaxer); | 140 void Process(BitVector* result, NonLiveFrameStateSlotReplacer* relaxer); |
121 bool UpdateLive(BitVector* working_area); | 141 bool UpdateLive(BitVector* working_area); |
122 | 142 |
123 void SetQueued() { queued_ = true; } | 143 void SetQueued() { queued_ = true; } |
124 bool IsQueued() { return queued_; } | 144 bool IsQueued() { return queued_; } |
125 | 145 |
126 ZoneDeque<LivenessAnalyzerBlock*>::const_iterator pred_begin() { | 146 ZoneDeque<LivenessAnalyzerBlock*>::const_iterator pred_begin() { |
127 return predecessors_.begin(); | 147 return predecessors_.begin(); |
128 } | 148 } |
129 ZoneDeque<LivenessAnalyzerBlock*>::const_iterator pred_end() { | 149 ZoneDeque<LivenessAnalyzerBlock*>::const_iterator pred_end() { |
130 return predecessors_.end(); | 150 return predecessors_.end(); |
131 } | 151 } |
132 | 152 |
133 size_t id() { return id_; } | 153 size_t id() { return id_; } |
134 void Print(std::ostream& os); | 154 void Print(std::ostream& os); |
135 | 155 |
136 ZoneDeque<Entry> entries_; | 156 ZoneDeque<Entry> entries_; |
137 ZoneDeque<LivenessAnalyzerBlock*> predecessors_; | 157 ZoneDeque<LivenessAnalyzerBlock*> predecessors_; |
138 | 158 |
139 BitVector live_; | 159 BitVector live_; |
140 bool queued_; | 160 bool queued_; |
| 161 bool has_accumulator_; |
141 | 162 |
142 size_t id_; | 163 size_t id_; |
143 }; | 164 }; |
144 | 165 |
145 | 166 |
146 } // namespace compiler | 167 } // namespace compiler |
147 } // namespace internal | 168 } // namespace internal |
148 } // namespace v8 | 169 } // namespace v8 |
149 | 170 |
150 #endif // V8_COMPILER_AST_GRAPH_BUILDER_H_ | 171 #endif // V8_COMPILER_AST_GRAPH_BUILDER_H_ |
OLD | NEW |