| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/intermediate_language.h" | 5 #include "vm/intermediate_language.h" |
| 6 | 6 |
| 7 #include "vm/bigint_operations.h" | 7 #include "vm/bigint_operations.h" |
| 8 #include "vm/bit_vector.h" | 8 #include "vm/bit_vector.h" |
| 9 #include "vm/dart_entry.h" | 9 #include "vm/dart_entry.h" |
| 10 #include "vm/flow_graph_allocator.h" | 10 #include "vm/flow_graph_allocator.h" |
| (...skipping 1498 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1509 } | 1509 } |
| 1510 | 1510 |
| 1511 | 1511 |
| 1512 Definition* UnboxUint32x4Instr::Canonicalize(FlowGraph* flow_graph) { | 1512 Definition* UnboxUint32x4Instr::Canonicalize(FlowGraph* flow_graph) { |
| 1513 // Fold away UnboxUint32x4(BoxUint32x4(v)). | 1513 // Fold away UnboxUint32x4(BoxUint32x4(v)). |
| 1514 BoxUint32x4Instr* defn = value()->definition()->AsBoxUint32x4(); | 1514 BoxUint32x4Instr* defn = value()->definition()->AsBoxUint32x4(); |
| 1515 return (defn != NULL) ? defn->value()->definition() : this; | 1515 return (defn != NULL) ? defn->value()->definition() : this; |
| 1516 } | 1516 } |
| 1517 | 1517 |
| 1518 | 1518 |
| 1519 Definition* BooleanNegateInstr::Canonicalize(FlowGraph* flow_graph) { |
| 1520 Definition* defn = value()->definition(); |
| 1521 if (defn->IsComparison() && |
| 1522 (value()->Type()->ToCid() == kBoolCid) && |
| 1523 defn->HasOnlyUse(value())) { |
| 1524 defn->AsComparison()->NegateComparison(); |
| 1525 return defn; |
| 1526 } |
| 1527 return this; |
| 1528 } |
| 1529 |
| 1530 |
| 1531 // Returns a replacement for a strict comparison and signals if the result has |
| 1532 // to be negated. |
| 1519 static Definition* CanonicalizeStrictCompare(StrictCompareInstr* compare, | 1533 static Definition* CanonicalizeStrictCompare(StrictCompareInstr* compare, |
| 1520 bool* negated) { | 1534 bool* negated) { |
| 1521 *negated = false; | 1535 *negated = false; |
| 1522 if (!compare->right()->BindsToConstant()) { | 1536 Object& constant = Object::Handle(); |
| 1537 Value* other = NULL; |
| 1538 if (compare->right()->BindsToConstant()) { |
| 1539 constant = compare->right()->BoundConstant().raw(); |
| 1540 other = compare->left(); |
| 1541 } else if (compare->left()->BindsToConstant()) { |
| 1542 constant = compare->left()->BoundConstant().raw(); |
| 1543 other = compare->right(); |
| 1544 } else { |
| 1523 return compare; | 1545 return compare; |
| 1524 } | 1546 } |
| 1525 const Object& right_constant = compare->right()->BoundConstant(); | |
| 1526 Definition* left_defn = compare->left()->definition(); | |
| 1527 | 1547 |
| 1528 // TODO(fschneider): Handle other cases: e === false and e !== true/false. | 1548 Definition* other_defn = other->definition(); |
| 1529 // Handles e === true. | 1549 Token::Kind kind = compare->kind(); |
| 1530 if ((compare->kind() == Token::kEQ_STRICT) && | 1550 // Handle e === true. |
| 1531 (right_constant.raw() == Bool::True().raw()) && | 1551 if ((kind == Token::kEQ_STRICT) && |
| 1532 (compare->left()->Type()->ToCid() == kBoolCid)) { | 1552 (constant.raw() == Bool::True().raw()) && |
| 1533 // Return left subexpression as the replacement for this instruction. | 1553 (other->Type()->ToCid() == kBoolCid)) { |
| 1534 return left_defn; | 1554 return other_defn; |
| 1535 } | 1555 } |
| 1536 // x = (a === b); y = x !== true; -> y = a !== b. | 1556 // Handle e !== false. |
| 1537 // In order to merge two strict compares, 'left_strict' must have only one | 1557 if ((kind == Token::kNE_STRICT) && |
| 1538 // use. Do not check left's cid as it is required to be a strict compare. | 1558 (constant.raw() == Bool::False().raw()) && |
| 1539 StrictCompareInstr* left_strict = left_defn->AsStrictCompare(); | 1559 (other->Type()->ToCid() == kBoolCid)) { |
| 1540 if ((compare->kind() == Token::kNE_STRICT) && | 1560 return other_defn; |
| 1541 (right_constant.raw() == Bool::True().raw()) && | 1561 } |
| 1542 (left_strict != NULL) && | 1562 // Handle e !== true |
| 1543 (left_strict->HasOnlyUse(compare->left()))) { | 1563 if ((kind == Token::kNE_STRICT) && |
| 1564 (constant.raw() == Bool::True().raw()) && |
| 1565 other_defn->IsComparison() && |
| 1566 (other->Type()->ToCid() == kBoolCid) && |
| 1567 other_defn->HasOnlyUse(other)) { |
| 1544 *negated = true; | 1568 *negated = true; |
| 1545 return left_strict; | 1569 return other_defn; |
| 1570 } |
| 1571 if ((kind == Token::kEQ_STRICT) && |
| 1572 (constant.raw() == Bool::False().raw()) && |
| 1573 other_defn->IsComparison() && |
| 1574 (other->Type()->ToCid() == kBoolCid) && |
| 1575 other_defn->HasOnlyUse(other)) { |
| 1576 *negated = true; |
| 1577 return other_defn; |
| 1546 } | 1578 } |
| 1547 return compare; | 1579 return compare; |
| 1548 } | 1580 } |
| 1549 | 1581 |
| 1550 | 1582 |
| 1551 Instruction* BranchInstr::Canonicalize(FlowGraph* flow_graph) { | 1583 Instruction* BranchInstr::Canonicalize(FlowGraph* flow_graph) { |
| 1552 // Only handle strict-compares. | 1584 // Only handle strict-compares. |
| 1553 if (comparison()->IsStrictCompare()) { | 1585 if (comparison()->IsStrictCompare()) { |
| 1554 bool negated = false; | 1586 bool negated = false; |
| 1555 Definition* replacement = | 1587 Definition* replacement = |
| (...skipping 1183 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2739 return kCosRuntimeEntry; | 2771 return kCosRuntimeEntry; |
| 2740 default: | 2772 default: |
| 2741 UNREACHABLE(); | 2773 UNREACHABLE(); |
| 2742 } | 2774 } |
| 2743 return kSinRuntimeEntry; | 2775 return kSinRuntimeEntry; |
| 2744 } | 2776 } |
| 2745 | 2777 |
| 2746 #undef __ | 2778 #undef __ |
| 2747 | 2779 |
| 2748 } // namespace dart | 2780 } // namespace dart |
| OLD | NEW |