OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 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 | 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/hydrogen-range-analysis.h" | 5 #include "src/hydrogen-range-analysis.h" |
6 | 6 |
7 namespace v8 { | 7 namespace v8 { |
8 namespace internal { | 8 namespace internal { |
9 | 9 |
10 | 10 |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
57 for (HInstructionIterator it(block); !it.Done(); it.Advance()) { | 57 for (HInstructionIterator it(block); !it.Done(); it.Advance()) { |
58 HValue* value = it.Current(); | 58 HValue* value = it.Current(); |
59 InferRange(value); | 59 InferRange(value); |
60 | 60 |
61 // Compute the bailout-on-minus-zero flag. | 61 // Compute the bailout-on-minus-zero flag. |
62 if (value->IsChange()) { | 62 if (value->IsChange()) { |
63 HChange* instr = HChange::cast(value); | 63 HChange* instr = HChange::cast(value); |
64 // Propagate flags for negative zero checks upwards from conversions | 64 // Propagate flags for negative zero checks upwards from conversions |
65 // int32-to-tagged and int32-to-double. | 65 // int32-to-tagged and int32-to-double. |
66 Representation from = instr->value()->representation(); | 66 Representation from = instr->value()->representation(); |
67 ASSERT(from.Equals(instr->from())); | 67 DCHECK(from.Equals(instr->from())); |
68 if (from.IsSmiOrInteger32()) { | 68 if (from.IsSmiOrInteger32()) { |
69 ASSERT(instr->to().IsTagged() || | 69 DCHECK(instr->to().IsTagged() || |
70 instr->to().IsDouble() || | 70 instr->to().IsDouble() || |
71 instr->to().IsSmiOrInteger32()); | 71 instr->to().IsSmiOrInteger32()); |
72 PropagateMinusZeroChecks(instr->value()); | 72 PropagateMinusZeroChecks(instr->value()); |
73 } | 73 } |
74 } else if (value->IsCompareMinusZeroAndBranch()) { | 74 } else if (value->IsCompareMinusZeroAndBranch()) { |
75 HCompareMinusZeroAndBranch* instr = | 75 HCompareMinusZeroAndBranch* instr = |
76 HCompareMinusZeroAndBranch::cast(value); | 76 HCompareMinusZeroAndBranch::cast(value); |
77 if (instr->value()->representation().IsSmiOrInteger32()) { | 77 if (instr->value()->representation().IsSmiOrInteger32()) { |
78 PropagateMinusZeroChecks(instr->value()); | 78 PropagateMinusZeroChecks(instr->value()); |
79 } | 79 } |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
114 HInstruction* instr = it.Current(); | 114 HInstruction* instr = it.Current(); |
115 if (instr->HasRange()) instr->PoisonRange(); | 115 if (instr->HasRange()) instr->PoisonRange(); |
116 } | 116 } |
117 } | 117 } |
118 #endif | 118 #endif |
119 } | 119 } |
120 | 120 |
121 | 121 |
122 void HRangeAnalysisPhase::InferControlFlowRange(HCompareNumericAndBranch* test, | 122 void HRangeAnalysisPhase::InferControlFlowRange(HCompareNumericAndBranch* test, |
123 HBasicBlock* dest) { | 123 HBasicBlock* dest) { |
124 ASSERT((test->FirstSuccessor() == dest) == (test->SecondSuccessor() != dest)); | 124 DCHECK((test->FirstSuccessor() == dest) == (test->SecondSuccessor() != dest)); |
125 if (test->representation().IsSmiOrInteger32()) { | 125 if (test->representation().IsSmiOrInteger32()) { |
126 Token::Value op = test->token(); | 126 Token::Value op = test->token(); |
127 if (test->SecondSuccessor() == dest) { | 127 if (test->SecondSuccessor() == dest) { |
128 op = Token::NegateCompareOp(op); | 128 op = Token::NegateCompareOp(op); |
129 } | 129 } |
130 Token::Value inverted_op = Token::ReverseCompareOp(op); | 130 Token::Value inverted_op = Token::ReverseCompareOp(op); |
131 UpdateControlFlowRange(op, test->left(), test->right()); | 131 UpdateControlFlowRange(op, test->left(), test->right()); |
132 UpdateControlFlowRange(inverted_op, test->right(), test->left()); | 132 UpdateControlFlowRange(inverted_op, test->right(), test->left()); |
133 } | 133 } |
134 } | 134 } |
(...skipping 28 matching lines...) Expand all Loading... |
163 } | 163 } |
164 } | 164 } |
165 | 165 |
166 if (new_range != NULL && !new_range->IsMostGeneric()) { | 166 if (new_range != NULL && !new_range->IsMostGeneric()) { |
167 AddRange(value, new_range); | 167 AddRange(value, new_range); |
168 } | 168 } |
169 } | 169 } |
170 | 170 |
171 | 171 |
172 void HRangeAnalysisPhase::InferRange(HValue* value) { | 172 void HRangeAnalysisPhase::InferRange(HValue* value) { |
173 ASSERT(!value->HasRange()); | 173 DCHECK(!value->HasRange()); |
174 if (!value->representation().IsNone()) { | 174 if (!value->representation().IsNone()) { |
175 value->ComputeInitialRange(graph()->zone()); | 175 value->ComputeInitialRange(graph()->zone()); |
176 Range* range = value->range(); | 176 Range* range = value->range(); |
177 TraceRange("Initial inferred range of %d (%s) set to [%d,%d]\n", | 177 TraceRange("Initial inferred range of %d (%s) set to [%d,%d]\n", |
178 value->id(), | 178 value->id(), |
179 value->Mnemonic(), | 179 value->Mnemonic(), |
180 range->lower(), | 180 range->lower(), |
181 range->upper()); | 181 range->upper()); |
182 } | 182 } |
183 } | 183 } |
184 | 184 |
185 | 185 |
186 void HRangeAnalysisPhase::RollBackTo(int index) { | 186 void HRangeAnalysisPhase::RollBackTo(int index) { |
187 ASSERT(index <= changed_ranges_.length()); | 187 DCHECK(index <= changed_ranges_.length()); |
188 for (int i = index; i < changed_ranges_.length(); ++i) { | 188 for (int i = index; i < changed_ranges_.length(); ++i) { |
189 changed_ranges_[i]->RemoveLastAddedRange(); | 189 changed_ranges_[i]->RemoveLastAddedRange(); |
190 } | 190 } |
191 changed_ranges_.Rewind(index); | 191 changed_ranges_.Rewind(index); |
192 } | 192 } |
193 | 193 |
194 | 194 |
195 void HRangeAnalysisPhase::AddRange(HValue* value, Range* range) { | 195 void HRangeAnalysisPhase::AddRange(HValue* value, Range* range) { |
196 Range* original_range = value->range(); | 196 Range* original_range = value->range(); |
197 value->AddNewRange(range, graph()->zone()); | 197 value->AddNewRange(range, graph()->zone()); |
198 changed_ranges_.Add(value, zone()); | 198 changed_ranges_.Add(value, zone()); |
199 Range* new_range = value->range(); | 199 Range* new_range = value->range(); |
200 TraceRange("Updated range of %d set to [%d,%d]\n", | 200 TraceRange("Updated range of %d set to [%d,%d]\n", |
201 value->id(), | 201 value->id(), |
202 new_range->lower(), | 202 new_range->lower(), |
203 new_range->upper()); | 203 new_range->upper()); |
204 if (original_range != NULL) { | 204 if (original_range != NULL) { |
205 TraceRange("Original range was [%d,%d]\n", | 205 TraceRange("Original range was [%d,%d]\n", |
206 original_range->lower(), | 206 original_range->lower(), |
207 original_range->upper()); | 207 original_range->upper()); |
208 } | 208 } |
209 TraceRange("New information was [%d,%d]\n", | 209 TraceRange("New information was [%d,%d]\n", |
210 range->lower(), | 210 range->lower(), |
211 range->upper()); | 211 range->upper()); |
212 } | 212 } |
213 | 213 |
214 | 214 |
215 void HRangeAnalysisPhase::PropagateMinusZeroChecks(HValue* value) { | 215 void HRangeAnalysisPhase::PropagateMinusZeroChecks(HValue* value) { |
216 ASSERT(worklist_.is_empty()); | 216 DCHECK(worklist_.is_empty()); |
217 ASSERT(in_worklist_.IsEmpty()); | 217 DCHECK(in_worklist_.IsEmpty()); |
218 | 218 |
219 AddToWorklist(value); | 219 AddToWorklist(value); |
220 while (!worklist_.is_empty()) { | 220 while (!worklist_.is_empty()) { |
221 value = worklist_.RemoveLast(); | 221 value = worklist_.RemoveLast(); |
222 | 222 |
223 if (value->IsPhi()) { | 223 if (value->IsPhi()) { |
224 // For phis, we must propagate the check to all of its inputs. | 224 // For phis, we must propagate the check to all of its inputs. |
225 HPhi* phi = HPhi::cast(value); | 225 HPhi* phi = HPhi::cast(value); |
226 for (int i = 0; i < phi->OperandCount(); ++i) { | 226 for (int i = 0; i < phi->OperandCount(); ++i) { |
227 AddToWorklist(phi->OperandAt(i)); | 227 AddToWorklist(phi->OperandAt(i)); |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
275 AddToWorklist(instr->left()); | 275 AddToWorklist(instr->left()); |
276 } | 276 } |
277 } else if (value->IsMathMinMax()) { | 277 } else if (value->IsMathMinMax()) { |
278 HMathMinMax* instr = HMathMinMax::cast(value); | 278 HMathMinMax* instr = HMathMinMax::cast(value); |
279 AddToWorklist(instr->right()); | 279 AddToWorklist(instr->right()); |
280 AddToWorklist(instr->left()); | 280 AddToWorklist(instr->left()); |
281 } | 281 } |
282 } | 282 } |
283 | 283 |
284 in_worklist_.Clear(); | 284 in_worklist_.Clear(); |
285 ASSERT(in_worklist_.IsEmpty()); | 285 DCHECK(in_worklist_.IsEmpty()); |
286 ASSERT(worklist_.is_empty()); | 286 DCHECK(worklist_.is_empty()); |
287 } | 287 } |
288 | 288 |
289 | 289 |
290 } } // namespace v8::internal | 290 } } // namespace v8::internal |
OLD | NEW |