Chromium Code Reviews| Index: src/hydrogen.cc |
| diff --git a/src/hydrogen.cc b/src/hydrogen.cc |
| index 3ce4a5b179831570f4bbba9034c181ce4e8234a6..cf19773cac598fac391fea7f982f756eef7b1216 100644 |
| --- a/src/hydrogen.cc |
| +++ b/src/hydrogen.cc |
| @@ -1850,6 +1850,8 @@ void HGraph::InsertRepresentationChangeForUse(HValue* value, |
| // change instructions for them. |
| HInstruction* new_value = NULL; |
| bool is_truncating = use_value->CheckFlag(HValue::kTruncatingToInt32); |
| + bool deoptimize_on_undefined = |
| + use_value->CheckFlag(HValue::kDeoptimizeOnUndefined); |
| if (value->IsConstant()) { |
| HConstant* constant = HConstant::cast(value); |
| // Try to create a new copy of the constant with the new representation. |
| @@ -1859,8 +1861,10 @@ void HGraph::InsertRepresentationChangeForUse(HValue* value, |
| } |
| if (new_value == NULL) { |
| + |
|
William Hesse
2011/06/08 14:30:30
Removed.
|
| new_value = |
| - new(zone()) HChange(value, value->representation(), to, is_truncating); |
| + new(zone()) HChange(value, value->representation(), to, |
| + is_truncating, deoptimize_on_undefined); |
|
William Hesse
2011/06/08 14:30:30
Reformatted.
|
| } |
| new_value->InsertBefore(next); |
| @@ -1942,6 +1946,38 @@ void HGraph::InsertRepresentationChanges() { |
| } |
| +void HGraph::RecursivelyMarkPhiDeoptimizeOnUndefined(HPhi* phi) { |
| + if (phi->CheckFlag(HValue::kDeoptimizeOnUndefined)) return; |
| + phi->SetFlag(HValue::kDeoptimizeOnUndefined); |
| + for (int i = 0; i < phi->OperandCount(); ++i) { |
| + HValue* input = phi->OperandAt(i); |
| + if (input->IsPhi()) { |
| + RecursivelyMarkPhiDeoptimizeOnUndefined(HPhi::cast(input)); |
| + } |
| + } |
| +} |
| + |
| + |
| +void HGraph::MarkDeoptimizeOnUndefined() { |
| + HPhase phase("MarkDeoptimizeOnUndefined", this); |
| + // Compute deoptimization on undefined flag for phis. |
| + // Any phi that can reach a Compare with input representation double |
| + // has this flag set, since an HChange tagged->double that feeds into |
| + // a Compare must not convert undefined to NaN, which it normally does. |
| + for (int i = 0; i < phi_list()->length(); i++) { |
| + HPhi* phi = phi_list()->at(i); |
| + if (phi->representation().IsDouble()) { |
| + for (HUseIterator it(phi->uses()); !it.Done(); it.Advance()) { |
| + if (it.value()->CheckFlag(HValue::kDeoptimizeOnUndefined)) { |
| + RecursivelyMarkPhiDeoptimizeOnUndefined(phi); |
| + break; |
| + } |
| + } |
| + } |
| + } |
| +} |
| + |
| + |
| void HGraph::ComputeMinusZeroChecks() { |
| BitVector visited(GetMaximumValueID()); |
| for (int i = 0; i < blocks_.length(); ++i) { |
| @@ -2248,6 +2284,7 @@ HGraph* HGraphBuilder::CreateGraph() { |
| graph()->InitializeInferredTypes(); |
| graph()->Canonicalize(); |
| + graph()->MarkDeoptimizeOnUndefined(); |
| graph()->InsertRepresentationChanges(); |
| graph()->ComputeMinusZeroChecks(); |