| 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_ESCAPE_ANALYSIS_H_ | 5 #ifndef V8_COMPILER_ESCAPE_ANALYSIS_H_ |
| 6 #define V8_COMPILER_ESCAPE_ANALYSIS_H_ | 6 #define V8_COMPILER_ESCAPE_ANALYSIS_H_ |
| 7 | 7 |
| 8 #include "src/base/flags.h" | |
| 9 #include "src/compiler/graph.h" | 8 #include "src/compiler/graph.h" |
| 10 | 9 |
| 11 namespace v8 { | 10 namespace v8 { |
| 12 namespace internal { | 11 namespace internal { |
| 13 namespace compiler { | 12 namespace compiler { |
| 14 | 13 |
| 15 // Forward declarations. | 14 // Forward declarations. |
| 16 class CommonOperatorBuilder; | 15 class CommonOperatorBuilder; |
| 17 class EscapeAnalysis; | 16 class EscapeStatusAnalysis; |
| 17 class MergeCache; |
| 18 class VirtualState; | 18 class VirtualState; |
| 19 class VirtualObject; | 19 class VirtualObject; |
| 20 | 20 |
| 21 // EscapeStatusAnalysis determines for each allocation whether it escapes. | |
| 22 class EscapeStatusAnalysis { | |
| 23 public: | |
| 24 typedef NodeId Alias; | |
| 25 ~EscapeStatusAnalysis(); | |
| 26 | |
| 27 enum Status { | |
| 28 kUnknown = 0u, | |
| 29 kTracked = 1u << 0, | |
| 30 kEscaped = 1u << 1, | |
| 31 kOnStack = 1u << 2, | |
| 32 kVisited = 1u << 3, | |
| 33 // A node is dangling, if it is a load of some kind, and does not have | |
| 34 // an effect successor. | |
| 35 kDanglingComputed = 1u << 4, | |
| 36 kDangling = 1u << 5, | |
| 37 // A node is is an effect branch point, if it has more than 2 non-dangling | |
| 38 // effect successors. | |
| 39 kBranchPointComputed = 1u << 6, | |
| 40 kBranchPoint = 1u << 7, | |
| 41 kInQueue = 1u << 8 | |
| 42 }; | |
| 43 typedef base::Flags<Status, uint16_t> StatusFlags; | |
| 44 | |
| 45 void RunStatusAnalysis(); | |
| 46 | |
| 47 bool IsVirtual(Node* node); | |
| 48 bool IsEscaped(Node* node); | |
| 49 bool IsAllocation(Node* node); | |
| 50 | |
| 51 bool IsInQueue(NodeId id); | |
| 52 void SetInQueue(NodeId id, bool on_stack); | |
| 53 | |
| 54 void DebugPrint(); | |
| 55 | |
| 56 EscapeStatusAnalysis(EscapeAnalysis* object_analysis, Graph* graph, | |
| 57 Zone* zone); | |
| 58 void EnqueueForStatusAnalysis(Node* node); | |
| 59 bool SetEscaped(Node* node); | |
| 60 bool IsEffectBranchPoint(Node* node); | |
| 61 bool IsDanglingEffectNode(Node* node); | |
| 62 void ResizeStatusVector(); | |
| 63 size_t GetStatusVectorSize(); | |
| 64 bool IsVirtual(NodeId id); | |
| 65 | |
| 66 Graph* graph() const { return graph_; } | |
| 67 Zone* zone() const { return zone_; } | |
| 68 void AssignAliases(); | |
| 69 Alias GetAlias(NodeId id) const { return aliases_[id]; } | |
| 70 const ZoneVector<Alias>& GetAliasMap() const { return aliases_; } | |
| 71 Alias AliasCount() const { return next_free_alias_; } | |
| 72 static const Alias kNotReachable; | |
| 73 static const Alias kUntrackable; | |
| 74 | |
| 75 bool IsNotReachable(Node* node); | |
| 76 | |
| 77 private: | |
| 78 void Process(Node* node); | |
| 79 void ProcessAllocate(Node* node); | |
| 80 void ProcessFinishRegion(Node* node); | |
| 81 void ProcessStoreField(Node* node); | |
| 82 void ProcessStoreElement(Node* node); | |
| 83 bool CheckUsesForEscape(Node* node, bool phi_escaping = false) { | |
| 84 return CheckUsesForEscape(node, node, phi_escaping); | |
| 85 } | |
| 86 bool CheckUsesForEscape(Node* node, Node* rep, bool phi_escaping = false); | |
| 87 void RevisitUses(Node* node); | |
| 88 void RevisitInputs(Node* node); | |
| 89 | |
| 90 Alias NextAlias() { return next_free_alias_++; } | |
| 91 | |
| 92 bool HasEntry(Node* node); | |
| 93 | |
| 94 bool IsAllocationPhi(Node* node); | |
| 95 | |
| 96 ZoneVector<Node*> stack_; | |
| 97 EscapeAnalysis* object_analysis_; | |
| 98 Graph* const graph_; | |
| 99 Zone* const zone_; | |
| 100 ZoneVector<StatusFlags> status_; | |
| 101 Alias next_free_alias_; | |
| 102 ZoneVector<Node*> status_stack_; | |
| 103 ZoneVector<Alias> aliases_; | |
| 104 | |
| 105 DISALLOW_COPY_AND_ASSIGN(EscapeStatusAnalysis); | |
| 106 }; | |
| 107 | |
| 108 DEFINE_OPERATORS_FOR_FLAGS(EscapeStatusAnalysis::StatusFlags) | |
| 109 | |
| 110 // Forward Declaration. | |
| 111 class MergeCache; | |
| 112 | |
| 113 // EscapeObjectAnalysis simulates stores to determine values of loads if | 21 // EscapeObjectAnalysis simulates stores to determine values of loads if |
| 114 // an object is virtual and eliminated. | 22 // an object is virtual and eliminated. |
| 115 class EscapeAnalysis { | 23 class EscapeAnalysis { |
| 116 public: | 24 public: |
| 117 using Alias = EscapeStatusAnalysis::Alias; | 25 typedef NodeId Alias; |
| 118 EscapeAnalysis(Graph* graph, CommonOperatorBuilder* common, Zone* zone); | 26 EscapeAnalysis(Graph* graph, CommonOperatorBuilder* common, Zone* zone); |
| 119 ~EscapeAnalysis(); | 27 ~EscapeAnalysis(); |
| 120 | 28 |
| 121 void Run(); | 29 void Run(); |
| 122 | 30 |
| 123 Node* GetReplacement(Node* node); | 31 Node* GetReplacement(Node* node); |
| 124 bool IsVirtual(Node* node); | 32 bool IsVirtual(Node* node); |
| 125 bool IsEscaped(Node* node); | 33 bool IsEscaped(Node* node); |
| 126 bool CompareVirtualObjects(Node* left, Node* right); | 34 bool CompareVirtualObjects(Node* left, Node* right); |
| 127 Node* GetOrCreateObjectState(Node* effect, Node* node); | 35 Node* GetOrCreateObjectState(Node* effect, Node* node); |
| (...skipping 29 matching lines...) Expand all Loading... |
| 157 Node* GetReplacement(NodeId id); | 65 Node* GetReplacement(NodeId id); |
| 158 bool SetReplacement(Node* node, Node* rep); | 66 bool SetReplacement(Node* node, Node* rep); |
| 159 bool UpdateReplacement(VirtualState* state, Node* node, Node* rep); | 67 bool UpdateReplacement(VirtualState* state, Node* node, Node* rep); |
| 160 | 68 |
| 161 VirtualObject* GetVirtualObject(VirtualState* state, Node* node); | 69 VirtualObject* GetVirtualObject(VirtualState* state, Node* node); |
| 162 | 70 |
| 163 void DebugPrint(); | 71 void DebugPrint(); |
| 164 void DebugPrintState(VirtualState* state); | 72 void DebugPrintState(VirtualState* state); |
| 165 void DebugPrintObject(VirtualObject* state, Alias id); | 73 void DebugPrintObject(VirtualObject* state, Alias id); |
| 166 | 74 |
| 167 Graph* graph() const { return status_analysis_.graph(); } | 75 Alias GetAlias(NodeId id) const; |
| 168 Zone* zone() const { return status_analysis_.zone(); } | 76 Alias AliasCount() const; |
| 77 |
| 78 Graph* graph() const; |
| 79 Zone* zone() const { return zone_; } |
| 169 CommonOperatorBuilder* common() const { return common_; } | 80 CommonOperatorBuilder* common() const { return common_; } |
| 170 bool IsEffectBranchPoint(Node* node) { | |
| 171 return status_analysis_.IsEffectBranchPoint(node); | |
| 172 } | |
| 173 bool IsDanglingEffectNode(Node* node) { | |
| 174 return status_analysis_.IsDanglingEffectNode(node); | |
| 175 } | |
| 176 bool IsNotReachable(Node* node) { | |
| 177 return status_analysis_.IsNotReachable(node); | |
| 178 } | |
| 179 Alias GetAlias(NodeId id) const { return status_analysis_.GetAlias(id); } | |
| 180 Alias AliasCount() const { return status_analysis_.AliasCount(); } | |
| 181 | 81 |
| 182 EscapeStatusAnalysis status_analysis_; | 82 Zone* const zone_; |
| 183 CommonOperatorBuilder* const common_; | 83 CommonOperatorBuilder* const common_; |
| 84 EscapeStatusAnalysis* status_analysis_; |
| 184 ZoneVector<VirtualState*> virtual_states_; | 85 ZoneVector<VirtualState*> virtual_states_; |
| 185 ZoneVector<Node*> replacements_; | 86 ZoneVector<Node*> replacements_; |
| 186 MergeCache* cache_; | 87 MergeCache* cache_; |
| 187 | 88 |
| 188 DISALLOW_COPY_AND_ASSIGN(EscapeAnalysis); | 89 DISALLOW_COPY_AND_ASSIGN(EscapeAnalysis); |
| 189 }; | 90 }; |
| 190 | 91 |
| 191 } // namespace compiler | 92 } // namespace compiler |
| 192 } // namespace internal | 93 } // namespace internal |
| 193 } // namespace v8 | 94 } // namespace v8 |
| 194 | 95 |
| 195 #endif // V8_COMPILER_ESCAPE_ANALYSIS_H_ | 96 #endif // V8_COMPILER_ESCAPE_ANALYSIS_H_ |
| OLD | NEW |