Index: src/hydrogen-instructions.cc |
diff --git a/src/hydrogen-instructions.cc b/src/hydrogen-instructions.cc |
index b353cdb2cc514acd7f31bc1752c92faff3f10ff7..d78feab266eb7f94baf609801716a9621787d406 100644 |
--- a/src/hydrogen-instructions.cc |
+++ b/src/hydrogen-instructions.cc |
@@ -524,6 +524,17 @@ const char* HValue::Mnemonic() const { |
} |
+bool HValue::IsInteger32Constant() { |
+ return IsConstant() && HConstant::cast(this)->HasInteger32Value(); |
+} |
+ |
+ |
+int32_t HValue::GetInteger32Constant() { |
+ ASSERT(IsInteger32Constant()); |
+ return HConstant::cast(this)->Integer32Value(); |
+} |
+ |
+ |
void HValue::SetOperandAt(int index, HValue* value) { |
RegisterUse(index, value); |
InternalSetOperandAt(index, value); |
@@ -690,6 +701,14 @@ void HInstruction::PrintMnemonicTo(StringStream* stream) { |
} |
+HValue* HValue::AddNumericConstraint(HInstruction* insertion_point, |
+ HValue* related_value, |
+ NumericRelation relation) { |
+ return HNumericConstraint::New( |
+ insertion_point, this, related_value, relation); |
+} |
+ |
+ |
void HInstruction::Unlink() { |
ASSERT(IsLinked()); |
ASSERT(!IsControlInstruction()); // Must never move control instructions. |
@@ -794,6 +813,27 @@ void HInstruction::Verify() { |
#endif |
+HNumericConstraint* HNumericConstraint::New(HInstruction* insertion_point, |
+ HValue* constrained_value, |
+ HValue* related_value, |
+ NumericRelation relation) { |
+ HNumericConstraint* result = |
+ new(insertion_point->block()->zone()) HNumericConstraint( |
+ constrained_value, related_value, relation); |
+ result->InsertAfter(insertion_point); |
+ return result; |
+} |
+ |
+ |
+void HNumericConstraint::PrintDataTo(StringStream* stream) { |
+ stream->Add("("); |
+ constrained_value()->PrintNameTo(stream); |
+ stream->Add(" %s ", relation().Mnemonic()); |
+ related_value()->PrintNameTo(stream); |
+ stream->Add(")"); |
+} |
+ |
+ |
void HDummyUse::PrintDataTo(StringStream* stream) { |
value()->PrintNameTo(stream); |
} |
@@ -815,6 +855,18 @@ void HBinaryCall::PrintDataTo(StringStream* stream) { |
} |
+bool HBoundsCheck::CheckRelation(NumericRelation relation, |
+ HValue* related_value) { |
+ if (related_value == length()) { |
+ return NumericRelation::Lt().Implies(relation); |
+ } else if (related_value == block()->graph()->GetConstant0()) { |
+ return NumericRelation::Ge().Implies(relation); |
+ } else { |
+ return false; |
+ } |
+} |
+ |
+ |
void HBoundsCheck::PrintDataTo(StringStream* stream) { |
index()->PrintNameTo(stream); |
stream->Add(" "); |
@@ -1475,6 +1527,31 @@ Range* HMod::InferRange(Zone* zone) { |
} |
+void HPhi::AddInformativeDefinitions() { |
+ HValue* induction_base = NULL; |
+ NumericRelation relation = NumericRelation::None(); |
+ if (OperandCount() == 2) { |
+ if (OperandAt(0)->IsRelationTrue(NumericRelation::Ge(), this)) { |
+ induction_base = OperandAt(1); |
+ relation = NumericRelation::Ge(); |
+ } else if (OperandAt(0)->IsRelationTrue(NumericRelation::Le(), this)) { |
+ induction_base = OperandAt(1); |
+ relation = NumericRelation::Ge(); |
+ } else if (OperandAt(1)->IsRelationTrue(NumericRelation::Ge(), this)) { |
+ induction_base = OperandAt(0); |
+ relation = NumericRelation::Ge(); |
+ } else if (OperandAt(1)->IsRelationTrue(NumericRelation::Le(), this)) { |
+ induction_base = OperandAt(0); |
+ relation = NumericRelation::Ge(); |
+ } |
+ } |
+ |
+ if (induction_base == NULL) return; |
+ |
+ AddNumericConstraint(block()->first(), induction_base, relation); |
+} |
+ |
+ |
Range* HMathMinMax::InferRange(Zone* zone) { |
if (representation().IsInteger32()) { |
Range* a = left()->range(); |
@@ -1888,6 +1965,23 @@ Range* HShr::InferRange(Zone* zone) { |
} |
+bool HShr::CheckRelation(NumericRelation relation, HValue* other) { |
+ if (right()->IsInteger32Constant()) { |
+ HValue* base = left(); |
+ int32_t bits = right()->GetInteger32Constant(); |
+ if (relation.IsExtendable(-bits) && |
+ base->IsRelationTrue(NumericRelation::Ge(), |
+ block()->graph()->GetConstant0())) { |
+ return base->IsRelationTrue(relation, other); |
+ } else { |
+ return false; |
+ } |
+ } else { |
+ return false; |
+ } |
+} |
+ |
+ |
Range* HShl::InferRange(Zone* zone) { |
if (right()->IsConstant()) { |
HConstant* c = HConstant::cast(right()); |
@@ -1904,6 +1998,23 @@ Range* HShl::InferRange(Zone* zone) { |
} |
+bool HShl::CheckRelation(NumericRelation relation, HValue* other) { |
+ if (right()->IsInteger32Constant()) { |
+ HValue* base = left(); |
+ int32_t bits = right()->GetInteger32Constant(); |
+ if (relation.IsExtendable(bits) && |
+ base->IsRelationTrue(NumericRelation::Ge(), |
+ block()->graph()->GetConstant0())) { |
+ return base->IsRelationTrue(relation, other); |
+ } else { |
+ return false; |
+ } |
+ } else { |
+ return false; |
+ } |
+} |
+ |
+ |
Range* HLoadKeyed::InferRange(Zone* zone) { |
switch (elements_kind()) { |
case EXTERNAL_PIXEL_ELEMENTS: |
@@ -1936,6 +2047,15 @@ void HStringCompareAndBranch::PrintDataTo(StringStream* stream) { |
} |
+void HCompareIDAndBranch::AddInformativeDefinitions() { |
+ NumericRelation r = NumericRelation::FromToken(token()); |
+ if (r == NumericRelation::None()) return; |
+ |
+ left()->AddNumericConstraint(SuccessorAt(0)->first(), right(), r.Reversed()); |
Jakob Kummerow
2013/02/12 15:10:42
s/.Reversed()/
Massi
2013/02/13 11:56:42
Done.
|
+ left()->AddNumericConstraint(SuccessorAt(1)->first(), right(), r); |
Jakob Kummerow
2013/02/12 15:10:42
and here you need r.Negated(), which is notably no
Massi
2013/02/13 11:56:42
Done.
|
+} |
+ |
+ |
void HCompareIDAndBranch::PrintDataTo(StringStream* stream) { |
stream->Add(Token::Name(token())); |
stream->Add(" "); |