OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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 #include "src/compiler/value-numbering-reducer.h" | 5 #include "src/compiler/value-numbering-reducer.h" |
6 | 6 |
7 #include <cstring> | 7 #include <cstring> |
8 | 8 |
9 #include "src/base/functional.h" | 9 #include "src/base/functional.h" |
10 #include "src/compiler/node.h" | 10 #include "src/compiler/node.h" |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
81 // Have to insert a new entry. | 81 // Have to insert a new entry. |
82 entries_[i] = node; | 82 entries_[i] = node; |
83 size_++; | 83 size_++; |
84 | 84 |
85 // Resize to keep load factor below 1/kCapacityToSizeRatio. | 85 // Resize to keep load factor below 1/kCapacityToSizeRatio. |
86 if (size_ * kCapacityToSizeRatio >= capacity_) Grow(); | 86 if (size_ * kCapacityToSizeRatio >= capacity_) Grow(); |
87 } | 87 } |
88 DCHECK(size_ * kCapacityToSizeRatio < capacity_); | 88 DCHECK(size_ * kCapacityToSizeRatio < capacity_); |
89 return NoChange(); | 89 return NoChange(); |
90 } | 90 } |
| 91 |
91 if (entry == node) { | 92 if (entry == node) { |
92 return NoChange(); | 93 // We need to check for a certain class of collisions here. Imagine the |
| 94 // following scenario: |
| 95 // |
| 96 // 1. We insert node1 with op1 and certain inputs at index i. |
| 97 // 2. We insert node2 with op2 and certain inputs at index i+1. |
| 98 // 3. Some other reducer changes node1 to op2 and the inputs from node2. |
| 99 // |
| 100 // Now we are called again to reduce node1, and we would return NoChange |
| 101 // in this case because we find node1 first, but what we should actually |
| 102 // do is return Replace(node2) instead. |
| 103 for (size_t j = (i + 1) & mask;; j = (j + 1) & mask) { |
| 104 Node* entry = entries_[j]; |
| 105 if (!entry) { |
| 106 // No collision, {node} is fine. |
| 107 return NoChange(); |
| 108 } |
| 109 if (entry->IsDead()) { |
| 110 continue; |
| 111 } |
| 112 if (Equals(entry, node)) { |
| 113 // Overwrite the colliding entry with the actual entry. |
| 114 entries_[i] = entry; |
| 115 return Replace(entry); |
| 116 } |
| 117 } |
93 } | 118 } |
94 | 119 |
95 // Skip dead entries, but remember their indices so we can reuse them. | 120 // Skip dead entries, but remember their indices so we can reuse them. |
96 if (entry->IsDead()) { | 121 if (entry->IsDead()) { |
97 dead = i; | 122 dead = i; |
98 continue; | 123 continue; |
99 } | 124 } |
100 if (Equals(entry, node)) { | 125 if (Equals(entry, node)) { |
101 return Replace(entry); | 126 return Replace(entry); |
102 } | 127 } |
(...skipping 27 matching lines...) Expand all Loading... |
130 size_++; | 155 size_++; |
131 break; | 156 break; |
132 } | 157 } |
133 } | 158 } |
134 } | 159 } |
135 } | 160 } |
136 | 161 |
137 } // namespace compiler | 162 } // namespace compiler |
138 } // namespace internal | 163 } // namespace internal |
139 } // namespace v8 | 164 } // namespace v8 |
OLD | NEW |