Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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/code-stubs.h" | 5 #include "src/code-stubs.h" |
| 6 | 6 |
| 7 #include <sstream> | 7 #include <sstream> |
| 8 | 8 |
| 9 #include "src/bootstrapper.h" | 9 #include "src/bootstrapper.h" |
| 10 #include "src/code-factory.h" | 10 #include "src/code-factory.h" |
| (...skipping 1590 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1601 Node* lhs = assembler->Parameter(0); | 1601 Node* lhs = assembler->Parameter(0); |
| 1602 Node* rhs = assembler->Parameter(1); | 1602 Node* rhs = assembler->Parameter(1); |
| 1603 Node* context = assembler->Parameter(2); | 1603 Node* context = assembler->Parameter(2); |
| 1604 Node* lhs_value = assembler->TruncateTaggedToWord32(context, lhs); | 1604 Node* lhs_value = assembler->TruncateTaggedToWord32(context, lhs); |
| 1605 Node* rhs_value = assembler->TruncateTaggedToWord32(context, rhs); | 1605 Node* rhs_value = assembler->TruncateTaggedToWord32(context, rhs); |
| 1606 Node* value = assembler->Word32Xor(lhs_value, rhs_value); | 1606 Node* value = assembler->Word32Xor(lhs_value, rhs_value); |
| 1607 Node* result = assembler->ChangeInt32ToTagged(value); | 1607 Node* result = assembler->ChangeInt32ToTagged(value); |
| 1608 assembler->Return(result); | 1608 assembler->Return(result); |
| 1609 } | 1609 } |
| 1610 | 1610 |
| 1611 void IncStub::GenerateAssembly(CodeStubAssembler* assembler) const { | |
| 1612 typedef CodeStubAssembler::Label Label; | |
| 1613 typedef compiler::Node Node; | |
| 1614 typedef CodeStubAssembler::Variable Variable; | |
| 1615 | |
| 1616 Node* value = assembler->Parameter(0); | |
| 1617 Node* context = assembler->Parameter(1); | |
| 1618 | |
| 1619 // Shared entry for floating point increment. | |
| 1620 Label do_finc(assembler); | |
| 1621 Variable var_finc_value(assembler, MachineRepresentation::kFloat64); | |
| 1622 | |
| 1623 // Input has been converted to a number using ToNumber, so it must be a | |
|
epertoso
2016/04/19 15:48:23
Where does this conversion happen?
rmcilroy
2016/04/19 15:50:03
In BytecodeGenerator::VisitCountOperation. The val
| |
| 1624 // Smi or a HeapNumber. | |
| 1625 Label if_issmi(assembler), if_isnotsmi(assembler); | |
| 1626 assembler->Branch(assembler->WordIsSmi(value), &if_issmi, &if_isnotsmi); | |
| 1627 | |
| 1628 assembler->Bind(&if_issmi); | |
| 1629 { | |
| 1630 // Try fast Smi addition first. | |
| 1631 Node* one = assembler->SmiConstant(Smi::FromInt(1)); | |
| 1632 Node* pair = assembler->SmiAddWithOverflow(value, one); | |
| 1633 Node* overflow = assembler->Projection(1, pair); | |
| 1634 | |
| 1635 // Check if the Smi additon overflowed. | |
| 1636 Label if_overflow(assembler), if_notoverflow(assembler); | |
| 1637 assembler->Branch(overflow, &if_overflow, &if_notoverflow); | |
| 1638 | |
| 1639 assembler->Bind(&if_notoverflow); | |
| 1640 assembler->Return(assembler->Projection(0, pair)); | |
| 1641 | |
| 1642 assembler->Bind(&if_overflow); | |
| 1643 { | |
| 1644 var_finc_value.Bind(assembler->SmiToFloat64(value)); | |
| 1645 assembler->Goto(&do_finc); | |
| 1646 } | |
| 1647 } | |
| 1648 | |
| 1649 assembler->Bind(&if_isnotsmi); | |
| 1650 { | |
| 1651 // Value must be a heap number if we reach this point. | |
| 1652 if (FLAG_debug_code) { | |
| 1653 // Assert that the value is a HeapNumber. | |
| 1654 Node* value_map = assembler->LoadMap(value); | |
| 1655 | |
| 1656 Label if_valueisnumber(assembler), | |
| 1657 if_valuenotnumber(assembler, Label::kDeferred); | |
| 1658 Node* number_map = assembler->HeapNumberMapConstant(); | |
| 1659 assembler->Branch(assembler->WordEqual(value_map, number_map), | |
| 1660 &if_valueisnumber, &if_valuenotnumber); | |
| 1661 | |
| 1662 assembler->Bind(&if_valuenotnumber); | |
| 1663 { | |
| 1664 Node* abort_id = assembler->SmiConstant( | |
| 1665 Smi::FromInt(BailoutReason::kExpectedHeapNumber)); | |
| 1666 assembler->CallRuntime(Runtime::kAbort, context, abort_id); | |
| 1667 assembler->Goto(&if_valueisnumber); // Won't actually be reached. | |
| 1668 } | |
| 1669 | |
| 1670 assembler->Bind(&if_valueisnumber); | |
| 1671 } | |
| 1672 | |
| 1673 // Load the heap number value | |
| 1674 var_finc_value.Bind(assembler->LoadHeapNumberValue(value)); | |
| 1675 assembler->Goto(&do_finc); | |
| 1676 } | |
| 1677 | |
| 1678 assembler->Bind(&do_finc); | |
| 1679 { | |
| 1680 Node* finc_value = var_finc_value.value(); | |
| 1681 Node* one = assembler->Float64Constant(1.0); | |
| 1682 Node* finc_result = assembler->Float64Add(finc_value, one); | |
| 1683 Node* result = assembler->ChangeFloat64ToTagged(finc_result); | |
| 1684 assembler->Return(result); | |
| 1685 } | |
| 1686 } | |
| 1687 | |
| 1688 void DecStub::GenerateAssembly(CodeStubAssembler* assembler) const { | |
| 1689 typedef CodeStubAssembler::Label Label; | |
| 1690 typedef compiler::Node Node; | |
| 1691 typedef CodeStubAssembler::Variable Variable; | |
| 1692 | |
| 1693 Node* value = assembler->Parameter(0); | |
| 1694 Node* context = assembler->Parameter(1); | |
| 1695 | |
| 1696 // Shared entry for floating point increment. | |
| 1697 Label do_fdec(assembler); | |
| 1698 Variable var_fdec_value(assembler, MachineRepresentation::kFloat64); | |
| 1699 | |
| 1700 // Input has been converted to a number using ToNumber, so it must be a | |
| 1701 // Smi or a HeapNumber. | |
| 1702 Label if_issmi(assembler), if_isnotsmi(assembler); | |
| 1703 assembler->Branch(assembler->WordIsSmi(value), &if_issmi, &if_isnotsmi); | |
| 1704 | |
| 1705 assembler->Bind(&if_issmi); | |
| 1706 { | |
| 1707 // Try fast Smi addition first. | |
| 1708 Node* one = assembler->SmiConstant(Smi::FromInt(1)); | |
| 1709 Node* pair = assembler->SmiSubWithOverflow(value, one); | |
| 1710 Node* overflow = assembler->Projection(1, pair); | |
| 1711 | |
| 1712 // Check if the Smi subtraction overflowed. | |
| 1713 Label if_overflow(assembler), if_notoverflow(assembler); | |
| 1714 assembler->Branch(overflow, &if_overflow, &if_notoverflow); | |
| 1715 | |
| 1716 assembler->Bind(&if_notoverflow); | |
| 1717 assembler->Return(assembler->Projection(0, pair)); | |
| 1718 | |
| 1719 assembler->Bind(&if_overflow); | |
| 1720 { | |
| 1721 var_fdec_value.Bind(assembler->SmiToFloat64(value)); | |
| 1722 assembler->Goto(&do_fdec); | |
| 1723 } | |
| 1724 } | |
| 1725 | |
| 1726 assembler->Bind(&if_isnotsmi); | |
| 1727 { | |
| 1728 // Value must be a heap number if we reach this point. | |
| 1729 if (FLAG_debug_code) { | |
| 1730 // Assert that the value is a HeapNumber. | |
| 1731 Node* value_map = assembler->LoadMap(value); | |
| 1732 | |
| 1733 Label if_valueisnumber(assembler), | |
| 1734 if_valuenotnumber(assembler, Label::kDeferred); | |
| 1735 Node* number_map = assembler->HeapNumberMapConstant(); | |
| 1736 assembler->Branch(assembler->WordEqual(value_map, number_map), | |
| 1737 &if_valueisnumber, &if_valuenotnumber); | |
| 1738 | |
| 1739 assembler->Bind(&if_valuenotnumber); | |
| 1740 { | |
| 1741 Node* abort_id = assembler->SmiConstant( | |
| 1742 Smi::FromInt(BailoutReason::kExpectedHeapNumber)); | |
| 1743 assembler->CallRuntime(Runtime::kAbort, context, abort_id); | |
| 1744 assembler->Goto(&if_valueisnumber); // Won't actually be reached. | |
| 1745 } | |
| 1746 | |
| 1747 assembler->Bind(&if_valueisnumber); | |
| 1748 } | |
| 1749 | |
| 1750 // Load the heap number value | |
| 1751 var_fdec_value.Bind(assembler->LoadHeapNumberValue(value)); | |
| 1752 assembler->Goto(&do_fdec); | |
| 1753 } | |
| 1754 | |
| 1755 assembler->Bind(&do_fdec); | |
| 1756 { | |
| 1757 Node* fdec_value = var_fdec_value.value(); | |
| 1758 Node* one = assembler->Float64Constant(1.0); | |
| 1759 Node* fdec_result = assembler->Float64Sub(fdec_value, one); | |
| 1760 Node* result = assembler->ChangeFloat64ToTagged(fdec_result); | |
| 1761 assembler->Return(result); | |
| 1762 } | |
| 1763 } | |
| 1764 | |
| 1611 namespace { | 1765 namespace { |
| 1612 | 1766 |
| 1613 enum RelationalComparisonMode { | 1767 enum RelationalComparisonMode { |
| 1614 kLessThan, | 1768 kLessThan, |
| 1615 kLessThanOrEqual, | 1769 kLessThanOrEqual, |
| 1616 kGreaterThan, | 1770 kGreaterThan, |
| 1617 kGreaterThanOrEqual | 1771 kGreaterThanOrEqual |
| 1618 }; | 1772 }; |
| 1619 | 1773 |
| 1620 void GenerateAbstractRelationalComparison(CodeStubAssembler* assembler, | 1774 void GenerateAbstractRelationalComparison(CodeStubAssembler* assembler, |
| (...skipping 2475 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 4096 if (type->Is(Type::UntaggedPointer())) { | 4250 if (type->Is(Type::UntaggedPointer())) { |
| 4097 return Representation::External(); | 4251 return Representation::External(); |
| 4098 } | 4252 } |
| 4099 | 4253 |
| 4100 DCHECK(!type->Is(Type::Untagged())); | 4254 DCHECK(!type->Is(Type::Untagged())); |
| 4101 return Representation::Tagged(); | 4255 return Representation::Tagged(); |
| 4102 } | 4256 } |
| 4103 | 4257 |
| 4104 } // namespace internal | 4258 } // namespace internal |
| 4105 } // namespace v8 | 4259 } // namespace v8 |
| OLD | NEW |