| 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/flow_graph_optimizer.h" | 5 #include "vm/flow_graph_optimizer.h" |
| 6 | 6 |
| 7 #include "vm/bit_vector.h" | 7 #include "vm/bit_vector.h" |
| 8 #include "vm/cha.h" | 8 #include "vm/cha.h" |
| 9 #include "vm/dart_entry.h" | 9 #include "vm/dart_entry.h" |
| 10 #include "vm/flow_graph_builder.h" | 10 #include "vm/flow_graph_builder.h" |
| (...skipping 1489 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1500 return false; | 1500 return false; |
| 1501 } | 1501 } |
| 1502 AddCheckClass(call->ArgumentAt(0), | 1502 AddCheckClass(call->ArgumentAt(0), |
| 1503 ICData::ZoneHandle( | 1503 ICData::ZoneHandle( |
| 1504 call->ic_data()->AsUnaryClassChecksForArgNr(0)), | 1504 call->ic_data()->AsUnaryClassChecksForArgNr(0)), |
| 1505 call->deopt_id(), | 1505 call->deopt_id(), |
| 1506 call->env(), | 1506 call->env(), |
| 1507 call); | 1507 call); |
| 1508 intptr_t mask = 0; | 1508 intptr_t mask = 0; |
| 1509 if (getter == MethodRecognizer::kFloat32x4Shuffle) { | 1509 if (getter == MethodRecognizer::kFloat32x4Shuffle) { |
| 1510 // Extract shuffle mask. |
| 1510 ASSERT(call->ArgumentCount() == 2); | 1511 ASSERT(call->ArgumentCount() == 2); |
| 1511 // Extract shuffle mask. | |
| 1512 Definition* mask_definition = call->ArgumentAt(1); | 1512 Definition* mask_definition = call->ArgumentAt(1); |
| 1513 if (!mask_definition->IsConstant()) { | 1513 if (!mask_definition->IsConstant()) { |
| 1514 // Not a constant. | 1514 // Not a constant. |
| 1515 return false; | 1515 return false; |
| 1516 } | 1516 } |
| 1517 ASSERT(mask_definition->IsConstant()); | 1517 ASSERT(mask_definition->IsConstant()); |
| 1518 ConstantInstr* constant_instruction = mask_definition->AsConstant(); | 1518 ConstantInstr* constant_instruction = mask_definition->AsConstant(); |
| 1519 const Object& constant_mask = constant_instruction->value(); | 1519 const Object& constant_mask = constant_instruction->value(); |
| 1520 if (!constant_mask.IsSmi()) { | 1520 if (!constant_mask.IsSmi()) { |
| 1521 // Not a smi. | 1521 // Not a smi. |
| 1522 return false; | 1522 return false; |
| 1523 } | 1523 } |
| 1524 ASSERT(constant_mask.IsSmi()); | 1524 ASSERT(constant_mask.IsSmi()); |
| 1525 mask = Smi::Cast(constant_mask).Value(); | 1525 mask = Smi::Cast(constant_mask).Value(); |
| 1526 if (mask < 0 || mask > 255) { | 1526 if (mask < 0 || mask > 255) { |
| 1527 // Not a valid mask. | 1527 // Not a valid mask. |
| 1528 return false; | 1528 return false; |
| 1529 } | 1529 } |
| 1530 } | 1530 } |
| 1531 Float32x4ShuffleInstr* instr = new Float32x4ShuffleInstr( | 1531 if (getter == MethodRecognizer::kFloat32x4GetSignMask) { |
| 1532 getter, | 1532 Simd32x4GetSignMaskInstr* instr = new Simd32x4GetSignMaskInstr( |
| 1533 new Value(call->ArgumentAt(0)), | 1533 getter, |
| 1534 mask, | 1534 new Value(call->ArgumentAt(0)), |
| 1535 call->deopt_id()); | 1535 call->deopt_id()); |
| 1536 ReplaceCall(call, instr); | 1536 ReplaceCall(call, instr); |
| 1537 return true; | 1537 return true; |
| 1538 } else { |
| 1539 ASSERT((getter == MethodRecognizer::kFloat32x4Shuffle) || |
| 1540 (getter == MethodRecognizer::kFloat32x4ShuffleX) || |
| 1541 (getter == MethodRecognizer::kFloat32x4ShuffleY) || |
| 1542 (getter == MethodRecognizer::kFloat32x4ShuffleZ) || |
| 1543 (getter == MethodRecognizer::kFloat32x4ShuffleW)); |
| 1544 Float32x4ShuffleInstr* instr = new Float32x4ShuffleInstr( |
| 1545 getter, |
| 1546 new Value(call->ArgumentAt(0)), |
| 1547 mask, |
| 1548 call->deopt_id()); |
| 1549 ReplaceCall(call, instr); |
| 1550 return true; |
| 1551 } |
| 1552 UNREACHABLE(); |
| 1553 return false; |
| 1538 } | 1554 } |
| 1539 | 1555 |
| 1540 | 1556 |
| 1541 bool FlowGraphOptimizer::InlineUint32x4Getter(InstanceCallInstr* call, | 1557 bool FlowGraphOptimizer::InlineUint32x4Getter(InstanceCallInstr* call, |
| 1542 MethodRecognizer::Kind getter) { | 1558 MethodRecognizer::Kind getter) { |
| 1543 if (!ShouldInlineSimd()) { | 1559 if (!ShouldInlineSimd()) { |
| 1544 return false; | 1560 return false; |
| 1545 } | 1561 } |
| 1546 AddCheckClass(call->ArgumentAt(0), | 1562 AddCheckClass(call->ArgumentAt(0), |
| 1547 ICData::ZoneHandle( | 1563 ICData::ZoneHandle( |
| 1548 call->ic_data()->AsUnaryClassChecksForArgNr(0)), | 1564 call->ic_data()->AsUnaryClassChecksForArgNr(0)), |
| 1549 call->deopt_id(), | 1565 call->deopt_id(), |
| 1550 call->env(), | 1566 call->env(), |
| 1551 call); | 1567 call); |
| 1552 Uint32x4GetFlagInstr* instr = new Uint32x4GetFlagInstr( | 1568 if (getter == MethodRecognizer::kUint32x4GetSignMask) { |
| 1553 getter, | 1569 Simd32x4GetSignMaskInstr* instr = new Simd32x4GetSignMaskInstr( |
| 1554 new Value(call->ArgumentAt(0)), | 1570 getter, |
| 1555 call->deopt_id()); | 1571 new Value(call->ArgumentAt(0)), |
| 1556 ReplaceCall(call, instr); | 1572 call->deopt_id()); |
| 1557 return true; | 1573 ReplaceCall(call, instr); |
| 1574 return true; |
| 1575 } else { |
| 1576 Uint32x4GetFlagInstr* instr = new Uint32x4GetFlagInstr( |
| 1577 getter, |
| 1578 new Value(call->ArgumentAt(0)), |
| 1579 call->deopt_id()); |
| 1580 ReplaceCall(call, instr); |
| 1581 return true; |
| 1582 } |
| 1558 } | 1583 } |
| 1559 | 1584 |
| 1560 | 1585 |
| 1561 bool FlowGraphOptimizer::InlineFloat32x4BinaryOp(InstanceCallInstr* call, | 1586 bool FlowGraphOptimizer::InlineFloat32x4BinaryOp(InstanceCallInstr* call, |
| 1562 Token::Kind op_kind) { | 1587 Token::Kind op_kind) { |
| 1563 if (!ShouldInlineSimd()) { | 1588 if (!ShouldInlineSimd()) { |
| 1564 return false; | 1589 return false; |
| 1565 } | 1590 } |
| 1566 ASSERT(call->ArgumentCount() == 2); | 1591 ASSERT(call->ArgumentCount() == 2); |
| 1567 Definition* left = call->ArgumentAt(0); | 1592 Definition* left = call->ArgumentAt(0); |
| (...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1685 if (!ic_data.HasOneTarget()) { | 1710 if (!ic_data.HasOneTarget()) { |
| 1686 // Target is not only StringBase_get_isEmpty. | 1711 // Target is not only StringBase_get_isEmpty. |
| 1687 return false; | 1712 return false; |
| 1688 } | 1713 } |
| 1689 InlineStringIsEmptyGetter(call); | 1714 InlineStringIsEmptyGetter(call); |
| 1690 return true; | 1715 return true; |
| 1691 case MethodRecognizer::kFloat32x4ShuffleX: | 1716 case MethodRecognizer::kFloat32x4ShuffleX: |
| 1692 case MethodRecognizer::kFloat32x4ShuffleY: | 1717 case MethodRecognizer::kFloat32x4ShuffleY: |
| 1693 case MethodRecognizer::kFloat32x4ShuffleZ: | 1718 case MethodRecognizer::kFloat32x4ShuffleZ: |
| 1694 case MethodRecognizer::kFloat32x4ShuffleW: | 1719 case MethodRecognizer::kFloat32x4ShuffleW: |
| 1720 case MethodRecognizer::kFloat32x4GetSignMask: |
| 1695 if (!ic_data.HasReceiverClassId(kFloat32x4Cid) || | 1721 if (!ic_data.HasReceiverClassId(kFloat32x4Cid) || |
| 1696 !ic_data.HasOneTarget()) { | 1722 !ic_data.HasOneTarget()) { |
| 1697 return false; | 1723 return false; |
| 1698 } | 1724 } |
| 1699 return InlineFloat32x4Getter(call, recognized_kind); | 1725 return InlineFloat32x4Getter(call, recognized_kind); |
| 1700 case MethodRecognizer::kUint32x4GetFlagX: | 1726 case MethodRecognizer::kUint32x4GetFlagX: |
| 1701 case MethodRecognizer::kUint32x4GetFlagY: | 1727 case MethodRecognizer::kUint32x4GetFlagY: |
| 1702 case MethodRecognizer::kUint32x4GetFlagZ: | 1728 case MethodRecognizer::kUint32x4GetFlagZ: |
| 1703 case MethodRecognizer::kUint32x4GetFlagW: { | 1729 case MethodRecognizer::kUint32x4GetFlagW: |
| 1730 case MethodRecognizer::kUint32x4GetSignMask: { |
| 1704 if (!ic_data.HasReceiverClassId(kUint32x4Cid) || | 1731 if (!ic_data.HasReceiverClassId(kUint32x4Cid) || |
| 1705 !ic_data.HasOneTarget()) { | 1732 !ic_data.HasOneTarget()) { |
| 1706 return false; | 1733 return false; |
| 1707 } | 1734 } |
| 1708 return InlineUint32x4Getter(call, recognized_kind); | 1735 return InlineUint32x4Getter(call, recognized_kind); |
| 1709 } | 1736 } |
| 1710 default: | 1737 default: |
| 1711 ASSERT(recognized_kind == MethodRecognizer::kUnknown); | 1738 ASSERT(recognized_kind == MethodRecognizer::kUnknown); |
| 1712 } | 1739 } |
| 1713 return false; | 1740 return false; |
| (...skipping 4792 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6506 Float32x4ConstructorInstr* instr) { | 6533 Float32x4ConstructorInstr* instr) { |
| 6507 SetValue(instr, non_constant_); | 6534 SetValue(instr, non_constant_); |
| 6508 } | 6535 } |
| 6509 | 6536 |
| 6510 | 6537 |
| 6511 void ConstantPropagator::VisitFloat32x4Shuffle(Float32x4ShuffleInstr* instr) { | 6538 void ConstantPropagator::VisitFloat32x4Shuffle(Float32x4ShuffleInstr* instr) { |
| 6512 SetValue(instr, non_constant_); | 6539 SetValue(instr, non_constant_); |
| 6513 } | 6540 } |
| 6514 | 6541 |
| 6515 | 6542 |
| 6543 void ConstantPropagator::VisitSimd32x4GetSignMask( |
| 6544 Simd32x4GetSignMaskInstr* instr) { |
| 6545 SetValue(instr, non_constant_); |
| 6546 } |
| 6547 |
| 6548 |
| 6516 void ConstantPropagator::VisitFloat32x4Zero(Float32x4ZeroInstr* instr) { | 6549 void ConstantPropagator::VisitFloat32x4Zero(Float32x4ZeroInstr* instr) { |
| 6517 SetValue(instr, non_constant_); | 6550 SetValue(instr, non_constant_); |
| 6518 } | 6551 } |
| 6519 | 6552 |
| 6520 | 6553 |
| 6521 void ConstantPropagator::VisitFloat32x4Splat(Float32x4SplatInstr* instr) { | 6554 void ConstantPropagator::VisitFloat32x4Splat(Float32x4SplatInstr* instr) { |
| 6522 SetValue(instr, non_constant_); | 6555 SetValue(instr, non_constant_); |
| 6523 } | 6556 } |
| 6524 | 6557 |
| 6525 | 6558 |
| (...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 6557 void ConstantPropagator::VisitFloat32x4With(Float32x4WithInstr* instr) { | 6590 void ConstantPropagator::VisitFloat32x4With(Float32x4WithInstr* instr) { |
| 6558 SetValue(instr, non_constant_); | 6591 SetValue(instr, non_constant_); |
| 6559 } | 6592 } |
| 6560 | 6593 |
| 6561 | 6594 |
| 6562 void ConstantPropagator::VisitFloat32x4ToUint32x4( | 6595 void ConstantPropagator::VisitFloat32x4ToUint32x4( |
| 6563 Float32x4ToUint32x4Instr* instr) { | 6596 Float32x4ToUint32x4Instr* instr) { |
| 6564 SetValue(instr, non_constant_); | 6597 SetValue(instr, non_constant_); |
| 6565 } | 6598 } |
| 6566 | 6599 |
| 6600 |
| 6567 void ConstantPropagator::VisitFloat32x4TwoArgShuffle( | 6601 void ConstantPropagator::VisitFloat32x4TwoArgShuffle( |
| 6568 Float32x4TwoArgShuffleInstr* instr) { | 6602 Float32x4TwoArgShuffleInstr* instr) { |
| 6569 SetValue(instr, non_constant_); | 6603 SetValue(instr, non_constant_); |
| 6570 } | 6604 } |
| 6571 | 6605 |
| 6572 | 6606 |
| 6573 void ConstantPropagator::VisitUint32x4BoolConstructor( | 6607 void ConstantPropagator::VisitUint32x4BoolConstructor( |
| 6574 Uint32x4BoolConstructorInstr* instr) { | 6608 Uint32x4BoolConstructorInstr* instr) { |
| 6575 SetValue(instr, non_constant_); | 6609 SetValue(instr, non_constant_); |
| 6576 } | 6610 } |
| (...skipping 961 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7538 } | 7572 } |
| 7539 | 7573 |
| 7540 // Insert materializations at environment uses. | 7574 // Insert materializations at environment uses. |
| 7541 for (intptr_t i = 0; i < exits.length(); i++) { | 7575 for (intptr_t i = 0; i < exits.length(); i++) { |
| 7542 CreateMaterializationAt(exits[i], alloc, alloc->cls(), *fields); | 7576 CreateMaterializationAt(exits[i], alloc, alloc->cls(), *fields); |
| 7543 } | 7577 } |
| 7544 } | 7578 } |
| 7545 | 7579 |
| 7546 | 7580 |
| 7547 } // namespace dart | 7581 } // namespace dart |
| OLD | NEW |