| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 562 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 573 } | 573 } |
| 574 | 574 |
| 575 | 575 |
| 576 LOperand* LChunkBuilder::UseOrConstantAtStart(HValue* value) { | 576 LOperand* LChunkBuilder::UseOrConstantAtStart(HValue* value) { |
| 577 return CanBeImmediateConstant(value) | 577 return CanBeImmediateConstant(value) |
| 578 ? chunk_->DefineConstantOperand(HConstant::cast(value)) | 578 ? chunk_->DefineConstantOperand(HConstant::cast(value)) |
| 579 : UseAtStart(value); | 579 : UseAtStart(value); |
| 580 } | 580 } |
| 581 | 581 |
| 582 | 582 |
| 583 LOperand* LChunkBuilder::UseFixedOrConstant(HValue* value, |
| 584 Register fixed_register) { |
| 585 return CanBeImmediateConstant(value) |
| 586 ? chunk_->DefineConstantOperand(HConstant::cast(value)) |
| 587 : UseFixed(value, fixed_register); |
| 588 } |
| 589 |
| 590 |
| 583 LOperand* LChunkBuilder::UseRegisterOrConstant(HValue* value) { | 591 LOperand* LChunkBuilder::UseRegisterOrConstant(HValue* value) { |
| 584 return CanBeImmediateConstant(value) | 592 return CanBeImmediateConstant(value) |
| 585 ? chunk_->DefineConstantOperand(HConstant::cast(value)) | 593 ? chunk_->DefineConstantOperand(HConstant::cast(value)) |
| 586 : UseRegister(value); | 594 : UseRegister(value); |
| 587 } | 595 } |
| 588 | 596 |
| 589 | 597 |
| 590 LOperand* LChunkBuilder::UseRegisterOrConstantAtStart(HValue* value) { | 598 LOperand* LChunkBuilder::UseRegisterOrConstantAtStart(HValue* value) { |
| 591 return CanBeImmediateConstant(value) | 599 return CanBeImmediateConstant(value) |
| 592 ? chunk_->DefineConstantOperand(HConstant::cast(value)) | 600 ? chunk_->DefineConstantOperand(HConstant::cast(value)) |
| (...skipping 316 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 909 current_block_ = NULL; | 917 current_block_ = NULL; |
| 910 } | 918 } |
| 911 | 919 |
| 912 | 920 |
| 913 void LChunkBuilder::VisitInstruction(HInstruction* current) { | 921 void LChunkBuilder::VisitInstruction(HInstruction* current) { |
| 914 HInstruction* old_current = current_instruction_; | 922 HInstruction* old_current = current_instruction_; |
| 915 current_instruction_ = current; | 923 current_instruction_ = current; |
| 916 | 924 |
| 917 LInstruction* instr = NULL; | 925 LInstruction* instr = NULL; |
| 918 if (current->CanReplaceWithDummyUses()) { | 926 if (current->CanReplaceWithDummyUses()) { |
| 919 HValue* first_operand = current->OperandCount() == 0 | 927 if (current->OperandCount() == 0) { |
| 920 ? graph()->GetConstant1() | 928 instr = DefineAsRegister(new(zone()) LDummy()); |
| 921 : current->OperandAt(0); | 929 } else { |
| 922 instr = DefineAsRegister(new(zone()) LDummyUse(UseAny(first_operand))); | 930 instr = DefineAsRegister(new(zone()) |
| 931 LDummyUse(UseAny(current->OperandAt(0)))); |
| 932 } |
| 923 for (int i = 1; i < current->OperandCount(); ++i) { | 933 for (int i = 1; i < current->OperandCount(); ++i) { |
| 924 LInstruction* dummy = | 934 LInstruction* dummy = |
| 925 new(zone()) LDummyUse(UseAny(current->OperandAt(i))); | 935 new(zone()) LDummyUse(UseAny(current->OperandAt(i))); |
| 926 dummy->set_hydrogen_value(current); | 936 dummy->set_hydrogen_value(current); |
| 927 chunk_->AddInstruction(dummy, current_block_); | 937 chunk_->AddInstruction(dummy, current_block_); |
| 928 } | 938 } |
| 929 } else { | 939 } else { |
| 930 instr = current->CompileToLithium(this); | 940 instr = current->CompileToLithium(this); |
| 931 } | 941 } |
| 932 | 942 |
| (...skipping 342 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1275 | 1285 |
| 1276 | 1286 |
| 1277 LInstruction* LChunkBuilder::DoMathFloor(HUnaryMathOperation* instr) { | 1287 LInstruction* LChunkBuilder::DoMathFloor(HUnaryMathOperation* instr) { |
| 1278 LOperand* input = UseRegisterAtStart(instr->value()); | 1288 LOperand* input = UseRegisterAtStart(instr->value()); |
| 1279 LMathFloor* result = new(zone()) LMathFloor(input); | 1289 LMathFloor* result = new(zone()) LMathFloor(input); |
| 1280 return AssignEnvironment(DefineAsRegister(result)); | 1290 return AssignEnvironment(DefineAsRegister(result)); |
| 1281 } | 1291 } |
| 1282 | 1292 |
| 1283 | 1293 |
| 1284 LInstruction* LChunkBuilder::DoMathRound(HUnaryMathOperation* instr) { | 1294 LInstruction* LChunkBuilder::DoMathRound(HUnaryMathOperation* instr) { |
| 1285 LOperand* context = UseAny(instr->context()); | |
| 1286 LOperand* input = UseRegister(instr->value()); | 1295 LOperand* input = UseRegister(instr->value()); |
| 1287 LOperand* temp = FixedTemp(xmm4); | 1296 LOperand* temp = FixedTemp(xmm4); |
| 1288 LMathRound* result = new(zone()) LMathRound(context, input, temp); | 1297 LMathRound* result = new(zone()) LMathRound(input, temp); |
| 1289 return AssignEnvironment(DefineAsRegister(result)); | 1298 return AssignEnvironment(DefineAsRegister(result)); |
| 1290 } | 1299 } |
| 1291 | 1300 |
| 1292 | 1301 |
| 1293 LInstruction* LChunkBuilder::DoMathAbs(HUnaryMathOperation* instr) { | 1302 LInstruction* LChunkBuilder::DoMathAbs(HUnaryMathOperation* instr) { |
| 1294 LOperand* context = UseAny(instr->context()); // Deferred use. | 1303 LOperand* context = UseAny(instr->context()); // Deferred use. |
| 1295 LOperand* input = UseRegisterAtStart(instr->value()); | 1304 LOperand* input = UseRegisterAtStart(instr->value()); |
| 1296 LMathAbs* result = new(zone()) LMathAbs(context, input); | 1305 LMathAbs* result = new(zone()) LMathAbs(context, input); |
| 1297 return AssignEnvironment(AssignPointerMap(DefineSameAsFirst(result))); | 1306 return AssignEnvironment(AssignPointerMap(DefineSameAsFirst(result))); |
| 1298 } | 1307 } |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1340 | 1349 |
| 1341 | 1350 |
| 1342 LInstruction* LChunkBuilder::DoMathSqrt(HUnaryMathOperation* instr) { | 1351 LInstruction* LChunkBuilder::DoMathSqrt(HUnaryMathOperation* instr) { |
| 1343 LOperand* input = UseRegisterAtStart(instr->value()); | 1352 LOperand* input = UseRegisterAtStart(instr->value()); |
| 1344 LMathSqrt* result = new(zone()) LMathSqrt(input); | 1353 LMathSqrt* result = new(zone()) LMathSqrt(input); |
| 1345 return DefineSameAsFirst(result); | 1354 return DefineSameAsFirst(result); |
| 1346 } | 1355 } |
| 1347 | 1356 |
| 1348 | 1357 |
| 1349 LInstruction* LChunkBuilder::DoMathPowHalf(HUnaryMathOperation* instr) { | 1358 LInstruction* LChunkBuilder::DoMathPowHalf(HUnaryMathOperation* instr) { |
| 1350 LOperand* context = UseAny(instr->context()); | |
| 1351 LOperand* input = UseRegisterAtStart(instr->value()); | 1359 LOperand* input = UseRegisterAtStart(instr->value()); |
| 1352 LOperand* temp = TempRegister(); | 1360 LOperand* temp = TempRegister(); |
| 1353 LMathPowHalf* result = new(zone()) LMathPowHalf(context, input, temp); | 1361 LMathPowHalf* result = new(zone()) LMathPowHalf(input, temp); |
| 1354 return DefineSameAsFirst(result); | 1362 return DefineSameAsFirst(result); |
| 1355 } | 1363 } |
| 1356 | 1364 |
| 1357 | 1365 |
| 1358 LInstruction* LChunkBuilder::DoCallKeyed(HCallKeyed* instr) { | 1366 LInstruction* LChunkBuilder::DoCallKeyed(HCallKeyed* instr) { |
| 1359 ASSERT(instr->key()->representation().IsTagged()); | 1367 ASSERT(instr->key()->representation().IsTagged()); |
| 1360 LOperand* context = UseFixed(instr->context(), esi); | 1368 LOperand* context = UseFixed(instr->context(), esi); |
| 1361 LOperand* key = UseFixed(instr->key(), ecx); | 1369 LOperand* key = UseFixed(instr->key(), ecx); |
| 1362 LCallKeyed* result = new(zone()) LCallKeyed(context, key); | 1370 LCallKeyed* result = new(zone()) LCallKeyed(context, key); |
| 1363 return MarkAsCall(DefineFixed(result, eax), instr); | 1371 return MarkAsCall(DefineFixed(result, eax), instr); |
| (...skipping 357 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1721 ASSERT(instr->right()->representation().Equals(r)); | 1729 ASSERT(instr->right()->representation().Equals(r)); |
| 1722 LOperand* left = UseRegisterOrConstantAtStart(instr->left()); | 1730 LOperand* left = UseRegisterOrConstantAtStart(instr->left()); |
| 1723 LOperand* right = UseOrConstantAtStart(instr->right()); | 1731 LOperand* right = UseOrConstantAtStart(instr->right()); |
| 1724 return new(zone()) LCompareNumericAndBranch(left, right); | 1732 return new(zone()) LCompareNumericAndBranch(left, right); |
| 1725 } else { | 1733 } else { |
| 1726 ASSERT(r.IsDouble()); | 1734 ASSERT(r.IsDouble()); |
| 1727 ASSERT(instr->left()->representation().IsDouble()); | 1735 ASSERT(instr->left()->representation().IsDouble()); |
| 1728 ASSERT(instr->right()->representation().IsDouble()); | 1736 ASSERT(instr->right()->representation().IsDouble()); |
| 1729 LOperand* left; | 1737 LOperand* left; |
| 1730 LOperand* right; | 1738 LOperand* right; |
| 1731 if (instr->left()->IsConstant() && instr->right()->IsConstant()) { | 1739 if (CanBeImmediateConstant(instr->left()) && |
| 1732 left = UseRegisterOrConstantAtStart(instr->left()); | 1740 CanBeImmediateConstant(instr->right())) { |
| 1733 right = UseRegisterOrConstantAtStart(instr->right()); | 1741 // The code generator requires either both inputs to be constant |
| 1742 // operands, or neither. |
| 1743 left = UseConstant(instr->left()); |
| 1744 right = UseConstant(instr->right()); |
| 1734 } else { | 1745 } else { |
| 1735 left = UseRegisterAtStart(instr->left()); | 1746 left = UseRegisterAtStart(instr->left()); |
| 1736 right = UseRegisterAtStart(instr->right()); | 1747 right = UseRegisterAtStart(instr->right()); |
| 1737 } | 1748 } |
| 1738 return new(zone()) LCompareNumericAndBranch(left, right); | 1749 return new(zone()) LCompareNumericAndBranch(left, right); |
| 1739 } | 1750 } |
| 1740 } | 1751 } |
| 1741 | 1752 |
| 1742 | 1753 |
| 1743 LInstruction* LChunkBuilder::DoCompareObjectEqAndBranch( | 1754 LInstruction* LChunkBuilder::DoCompareObjectEqAndBranch( |
| 1744 HCompareObjectEqAndBranch* instr) { | 1755 HCompareObjectEqAndBranch* instr) { |
| 1745 LInstruction* goto_instr = CheckElideControlInstruction(instr); | 1756 LInstruction* goto_instr = CheckElideControlInstruction(instr); |
| 1746 if (goto_instr != NULL) return goto_instr; | 1757 if (goto_instr != NULL) return goto_instr; |
| 1747 LOperand* left = UseRegisterAtStart(instr->left()); | 1758 LOperand* left = UseRegisterAtStart(instr->left()); |
| 1748 LOperand* right = UseOrConstantAtStart(instr->right()); | 1759 LOperand* right = UseOrConstantAtStart(instr->right()); |
| 1749 return new(zone()) LCmpObjectEqAndBranch(left, right); | 1760 return new(zone()) LCmpObjectEqAndBranch(left, right); |
| 1750 } | 1761 } |
| 1751 | 1762 |
| 1752 | 1763 |
| 1753 LInstruction* LChunkBuilder::DoCompareHoleAndBranch( | 1764 LInstruction* LChunkBuilder::DoCompareHoleAndBranch( |
| 1754 HCompareHoleAndBranch* instr) { | 1765 HCompareHoleAndBranch* instr) { |
| 1755 LOperand* value = UseRegisterAtStart(instr->value()); | 1766 LOperand* value = UseRegisterAtStart(instr->value()); |
| 1756 return new(zone()) LCmpHoleAndBranch(value); | 1767 return new(zone()) LCmpHoleAndBranch(value); |
| 1757 } | 1768 } |
| 1758 | 1769 |
| 1759 | 1770 |
| 1771 LInstruction* LChunkBuilder::DoCompareMinusZeroAndBranch( |
| 1772 HCompareMinusZeroAndBranch* instr) { |
| 1773 LInstruction* goto_instr = CheckElideControlInstruction(instr); |
| 1774 if (goto_instr != NULL) return goto_instr; |
| 1775 LOperand* value = UseRegister(instr->value()); |
| 1776 LOperand* scratch = TempRegister(); |
| 1777 return new(zone()) LCompareMinusZeroAndBranch(value, scratch); |
| 1778 } |
| 1779 |
| 1780 |
| 1760 LInstruction* LChunkBuilder::DoIsObjectAndBranch(HIsObjectAndBranch* instr) { | 1781 LInstruction* LChunkBuilder::DoIsObjectAndBranch(HIsObjectAndBranch* instr) { |
| 1761 ASSERT(instr->value()->representation().IsSmiOrTagged()); | 1782 ASSERT(instr->value()->representation().IsSmiOrTagged()); |
| 1762 LOperand* temp = TempRegister(); | 1783 LOperand* temp = TempRegister(); |
| 1763 return new(zone()) LIsObjectAndBranch(UseRegister(instr->value()), temp); | 1784 return new(zone()) LIsObjectAndBranch(UseRegister(instr->value()), temp); |
| 1764 } | 1785 } |
| 1765 | 1786 |
| 1766 | 1787 |
| 1767 LInstruction* LChunkBuilder::DoIsStringAndBranch(HIsStringAndBranch* instr) { | 1788 LInstruction* LChunkBuilder::DoIsStringAndBranch(HIsStringAndBranch* instr) { |
| 1768 ASSERT(instr->value()->representation().IsTagged()); | 1789 ASSERT(instr->value()->representation().IsTagged()); |
| 1769 LOperand* temp = TempRegister(); | 1790 LOperand* temp = TempRegister(); |
| (...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1855 | 1876 |
| 1856 | 1877 |
| 1857 LInstruction* LChunkBuilder::DoDateField(HDateField* instr) { | 1878 LInstruction* LChunkBuilder::DoDateField(HDateField* instr) { |
| 1858 LOperand* date = UseFixed(instr->value(), eax); | 1879 LOperand* date = UseFixed(instr->value(), eax); |
| 1859 LDateField* result = | 1880 LDateField* result = |
| 1860 new(zone()) LDateField(date, FixedTemp(ecx), instr->index()); | 1881 new(zone()) LDateField(date, FixedTemp(ecx), instr->index()); |
| 1861 return MarkAsCall(DefineFixed(result, eax), instr, CAN_DEOPTIMIZE_EAGERLY); | 1882 return MarkAsCall(DefineFixed(result, eax), instr, CAN_DEOPTIMIZE_EAGERLY); |
| 1862 } | 1883 } |
| 1863 | 1884 |
| 1864 | 1885 |
| 1886 LInstruction* LChunkBuilder::DoSeqStringGetChar(HSeqStringGetChar* instr) { |
| 1887 LOperand* string = UseRegisterAtStart(instr->string()); |
| 1888 LOperand* index = UseRegisterOrConstantAtStart(instr->index()); |
| 1889 return DefineAsRegister(new(zone()) LSeqStringGetChar(string, index)); |
| 1890 } |
| 1891 |
| 1892 |
| 1865 LInstruction* LChunkBuilder::DoSeqStringSetChar(HSeqStringSetChar* instr) { | 1893 LInstruction* LChunkBuilder::DoSeqStringSetChar(HSeqStringSetChar* instr) { |
| 1866 LOperand* string = UseRegister(instr->string()); | 1894 LOperand* string = UseRegisterAtStart(instr->string()); |
| 1867 LOperand* index = UseRegister(instr->index()); | 1895 LOperand* index = UseRegisterOrConstantAtStart(instr->index()); |
| 1868 ASSERT(ecx.is_byte_register()); | 1896 LOperand* value = (instr->encoding() == String::ONE_BYTE_ENCODING) |
| 1869 LOperand* value = UseFixed(instr->value(), ecx); | 1897 ? UseFixedOrConstant(instr->value(), eax) |
| 1870 LSeqStringSetChar* result = | 1898 : UseRegisterOrConstantAtStart(instr->value()); |
| 1871 new(zone()) LSeqStringSetChar(instr->encoding(), string, index, value); | 1899 return new(zone()) LSeqStringSetChar(string, index, value); |
| 1872 return DefineSameAsFirst(result); | |
| 1873 } | 1900 } |
| 1874 | 1901 |
| 1875 | 1902 |
| 1876 LInstruction* LChunkBuilder::DoBoundsCheck(HBoundsCheck* instr) { | 1903 LInstruction* LChunkBuilder::DoBoundsCheck(HBoundsCheck* instr) { |
| 1877 return AssignEnvironment(new(zone()) LBoundsCheck( | 1904 return AssignEnvironment(new(zone()) LBoundsCheck( |
| 1878 UseRegisterOrConstantAtStart(instr->index()), | 1905 UseRegisterOrConstantAtStart(instr->index()), |
| 1879 UseAtStart(instr->length()))); | 1906 UseAtStart(instr->length()))); |
| 1880 } | 1907 } |
| 1881 | 1908 |
| 1882 | 1909 |
| (...skipping 109 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1992 : NULL; | 2019 : NULL; |
| 1993 LNumberTagU* result = new(zone()) LNumberTagU(value, temp); | 2020 LNumberTagU* result = new(zone()) LNumberTagU(value, temp); |
| 1994 return AssignEnvironment(AssignPointerMap(DefineSameAsFirst(result))); | 2021 return AssignEnvironment(AssignPointerMap(DefineSameAsFirst(result))); |
| 1995 } else { | 2022 } else { |
| 1996 LNumberTagI* result = new(zone()) LNumberTagI(value); | 2023 LNumberTagI* result = new(zone()) LNumberTagI(value); |
| 1997 return AssignEnvironment(AssignPointerMap(DefineSameAsFirst(result))); | 2024 return AssignEnvironment(AssignPointerMap(DefineSameAsFirst(result))); |
| 1998 } | 2025 } |
| 1999 } else if (to.IsSmi()) { | 2026 } else if (to.IsSmi()) { |
| 2000 HValue* val = instr->value(); | 2027 HValue* val = instr->value(); |
| 2001 LOperand* value = UseRegister(val); | 2028 LOperand* value = UseRegister(val); |
| 2002 LInstruction* result = | 2029 LInstruction* result = val->CheckFlag(HInstruction::kUint32) |
| 2003 DefineSameAsFirst(new(zone()) LInteger32ToSmi(value)); | 2030 ? DefineSameAsFirst(new(zone()) LUint32ToSmi(value)) |
| 2031 : DefineSameAsFirst(new(zone()) LInteger32ToSmi(value)); |
| 2004 if (val->HasRange() && val->range()->IsInSmiRange()) { | 2032 if (val->HasRange() && val->range()->IsInSmiRange()) { |
| 2005 return result; | 2033 return result; |
| 2006 } | 2034 } |
| 2007 return AssignEnvironment(result); | 2035 return AssignEnvironment(result); |
| 2008 } else { | 2036 } else { |
| 2009 ASSERT(to.IsDouble()); | 2037 ASSERT(to.IsDouble()); |
| 2010 if (instr->value()->CheckFlag(HInstruction::kUint32)) { | 2038 if (instr->value()->CheckFlag(HInstruction::kUint32)) { |
| 2011 LOperand* temp = FixedTemp(xmm1); | 2039 LOperand* temp = FixedTemp(xmm1); |
| 2012 return DefineAsRegister( | 2040 return DefineAsRegister( |
| 2013 new(zone()) LUint32ToDouble(UseRegister(instr->value()), temp)); | 2041 new(zone()) LUint32ToDouble(UseRegister(instr->value()), temp)); |
| (...skipping 77 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2091 LClampTToUint8NoSSE2* res = | 2119 LClampTToUint8NoSSE2* res = |
| 2092 new(zone()) LClampTToUint8NoSSE2(value, TempRegister(), | 2120 new(zone()) LClampTToUint8NoSSE2(value, TempRegister(), |
| 2093 TempRegister(), TempRegister()); | 2121 TempRegister(), TempRegister()); |
| 2094 return AssignEnvironment(DefineFixed(res, ecx)); | 2122 return AssignEnvironment(DefineFixed(res, ecx)); |
| 2095 } | 2123 } |
| 2096 } | 2124 } |
| 2097 } | 2125 } |
| 2098 | 2126 |
| 2099 | 2127 |
| 2100 LInstruction* LChunkBuilder::DoReturn(HReturn* instr) { | 2128 LInstruction* LChunkBuilder::DoReturn(HReturn* instr) { |
| 2101 LOperand* context = info()->IsStub() | 2129 LOperand* context = info()->IsStub() ? UseFixed(instr->context(), esi) : NULL; |
| 2102 ? UseFixed(instr->context(), esi) | |
| 2103 : NULL; | |
| 2104 LOperand* parameter_count = UseRegisterOrConstant(instr->parameter_count()); | 2130 LOperand* parameter_count = UseRegisterOrConstant(instr->parameter_count()); |
| 2105 return new(zone()) LReturn(UseFixed(instr->value(), eax), context, | 2131 return new(zone()) LReturn( |
| 2106 parameter_count); | 2132 UseFixed(instr->value(), eax), context, parameter_count); |
| 2107 } | 2133 } |
| 2108 | 2134 |
| 2109 | 2135 |
| 2110 LInstruction* LChunkBuilder::DoConstant(HConstant* instr) { | 2136 LInstruction* LChunkBuilder::DoConstant(HConstant* instr) { |
| 2111 Representation r = instr->representation(); | 2137 Representation r = instr->representation(); |
| 2112 if (r.IsSmi()) { | 2138 if (r.IsSmi()) { |
| 2113 return DefineAsRegister(new(zone()) LConstantS); | 2139 return DefineAsRegister(new(zone()) LConstantS); |
| 2114 } else if (r.IsInteger32()) { | 2140 } else if (r.IsInteger32()) { |
| 2115 return DefineAsRegister(new(zone()) LConstantI); | 2141 return DefineAsRegister(new(zone()) LConstantI); |
| 2116 } else if (r.IsDouble()) { | 2142 } else if (r.IsDouble()) { |
| (...skipping 294 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2411 obj = needs_write_barrier_for_map | 2437 obj = needs_write_barrier_for_map |
| 2412 ? UseRegister(instr->object()) | 2438 ? UseRegister(instr->object()) |
| 2413 : UseRegisterAtStart(instr->object()); | 2439 : UseRegisterAtStart(instr->object()); |
| 2414 } | 2440 } |
| 2415 | 2441 |
| 2416 bool can_be_constant = instr->value()->IsConstant() && | 2442 bool can_be_constant = instr->value()->IsConstant() && |
| 2417 HConstant::cast(instr->value())->NotInNewSpace() && | 2443 HConstant::cast(instr->value())->NotInNewSpace() && |
| 2418 !(FLAG_track_double_fields && instr->field_representation().IsDouble()); | 2444 !(FLAG_track_double_fields && instr->field_representation().IsDouble()); |
| 2419 | 2445 |
| 2420 LOperand* val; | 2446 LOperand* val; |
| 2421 if (instr->field_representation().IsByte()) { | 2447 if (instr->field_representation().IsInteger8() || |
| 2448 instr->field_representation().IsUInteger8()) { |
| 2422 // mov_b requires a byte register (i.e. any of eax, ebx, ecx, edx). | 2449 // mov_b requires a byte register (i.e. any of eax, ebx, ecx, edx). |
| 2423 // Just force the value to be in eax and we're safe here. | 2450 // Just force the value to be in eax and we're safe here. |
| 2424 val = UseFixed(instr->value(), eax); | 2451 val = UseFixed(instr->value(), eax); |
| 2425 } else if (needs_write_barrier) { | 2452 } else if (needs_write_barrier) { |
| 2426 val = UseTempRegister(instr->value()); | 2453 val = UseTempRegister(instr->value()); |
| 2427 } else if (can_be_constant) { | 2454 } else if (can_be_constant) { |
| 2428 val = UseRegisterOrConstant(instr->value()); | 2455 val = UseRegisterOrConstant(instr->value()); |
| 2429 } else if (FLAG_track_fields && instr->field_representation().IsSmi()) { | 2456 } else if (FLAG_track_fields && instr->field_representation().IsSmi()) { |
| 2430 val = UseTempRegister(instr->value()); | 2457 val = UseTempRegister(instr->value()); |
| 2431 } else if (FLAG_track_double_fields && | 2458 } else if (FLAG_track_double_fields && |
| (...skipping 29 matching lines...) Expand all Loading... |
| 2461 LOperand* value = UseFixed(instr->value(), eax); | 2488 LOperand* value = UseFixed(instr->value(), eax); |
| 2462 | 2489 |
| 2463 LStoreNamedGeneric* result = | 2490 LStoreNamedGeneric* result = |
| 2464 new(zone()) LStoreNamedGeneric(context, object, value); | 2491 new(zone()) LStoreNamedGeneric(context, object, value); |
| 2465 return MarkAsCall(result, instr); | 2492 return MarkAsCall(result, instr); |
| 2466 } | 2493 } |
| 2467 | 2494 |
| 2468 | 2495 |
| 2469 LInstruction* LChunkBuilder::DoStringAdd(HStringAdd* instr) { | 2496 LInstruction* LChunkBuilder::DoStringAdd(HStringAdd* instr) { |
| 2470 LOperand* context = UseFixed(instr->context(), esi); | 2497 LOperand* context = UseFixed(instr->context(), esi); |
| 2471 LOperand* left = UseOrConstantAtStart(instr->left()); | 2498 LOperand* left = FLAG_new_string_add |
| 2472 LOperand* right = UseOrConstantAtStart(instr->right()); | 2499 ? UseFixed(instr->left(), edx) |
| 2500 : UseOrConstantAtStart(instr->left()); |
| 2501 LOperand* right = FLAG_new_string_add |
| 2502 ? UseFixed(instr->right(), eax) |
| 2503 : UseOrConstantAtStart(instr->right()); |
| 2473 LStringAdd* string_add = new(zone()) LStringAdd(context, left, right); | 2504 LStringAdd* string_add = new(zone()) LStringAdd(context, left, right); |
| 2474 return MarkAsCall(DefineFixed(string_add, eax), instr); | 2505 return MarkAsCall(DefineFixed(string_add, eax), instr); |
| 2475 } | 2506 } |
| 2476 | 2507 |
| 2477 | 2508 |
| 2478 LInstruction* LChunkBuilder::DoStringCharCodeAt(HStringCharCodeAt* instr) { | 2509 LInstruction* LChunkBuilder::DoStringCharCodeAt(HStringCharCodeAt* instr) { |
| 2479 LOperand* string = UseTempRegister(instr->string()); | 2510 LOperand* string = UseTempRegister(instr->string()); |
| 2480 LOperand* index = UseTempRegister(instr->index()); | 2511 LOperand* index = UseTempRegister(instr->index()); |
| 2481 LOperand* context = UseAny(instr->context()); | 2512 LOperand* context = UseAny(instr->context()); |
| 2482 LStringCharCodeAt* result = | 2513 LStringCharCodeAt* result = |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2531 LInstruction* LChunkBuilder::DoParameter(HParameter* instr) { | 2562 LInstruction* LChunkBuilder::DoParameter(HParameter* instr) { |
| 2532 LParameter* result = new(zone()) LParameter; | 2563 LParameter* result = new(zone()) LParameter; |
| 2533 if (instr->kind() == HParameter::STACK_PARAMETER) { | 2564 if (instr->kind() == HParameter::STACK_PARAMETER) { |
| 2534 int spill_index = chunk()->GetParameterStackSlot(instr->index()); | 2565 int spill_index = chunk()->GetParameterStackSlot(instr->index()); |
| 2535 return DefineAsSpilled(result, spill_index); | 2566 return DefineAsSpilled(result, spill_index); |
| 2536 } else { | 2567 } else { |
| 2537 ASSERT(info()->IsStub()); | 2568 ASSERT(info()->IsStub()); |
| 2538 CodeStubInterfaceDescriptor* descriptor = | 2569 CodeStubInterfaceDescriptor* descriptor = |
| 2539 info()->code_stub()->GetInterfaceDescriptor(info()->isolate()); | 2570 info()->code_stub()->GetInterfaceDescriptor(info()->isolate()); |
| 2540 int index = static_cast<int>(instr->index()); | 2571 int index = static_cast<int>(instr->index()); |
| 2541 Register reg = DESCRIPTOR_GET_PARAMETER_REGISTER(descriptor, index); | 2572 Register reg = descriptor->GetParameterRegister(index); |
| 2542 return DefineFixed(result, reg); | 2573 return DefineFixed(result, reg); |
| 2543 } | 2574 } |
| 2544 } | 2575 } |
| 2545 | 2576 |
| 2546 | 2577 |
| 2547 LInstruction* LChunkBuilder::DoUnknownOSRValue(HUnknownOSRValue* instr) { | 2578 LInstruction* LChunkBuilder::DoUnknownOSRValue(HUnknownOSRValue* instr) { |
| 2548 // Use an index that corresponds to the location in the unoptimized frame, | 2579 // Use an index that corresponds to the location in the unoptimized frame, |
| 2549 // which the optimized frame will subsume. | 2580 // which the optimized frame will subsume. |
| 2550 int env_index = instr->index(); | 2581 int env_index = instr->index(); |
| 2551 int spill_index = 0; | 2582 int spill_index = 0; |
| (...skipping 180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2732 LInstruction* LChunkBuilder::DoLoadFieldByIndex(HLoadFieldByIndex* instr) { | 2763 LInstruction* LChunkBuilder::DoLoadFieldByIndex(HLoadFieldByIndex* instr) { |
| 2733 LOperand* object = UseRegister(instr->object()); | 2764 LOperand* object = UseRegister(instr->object()); |
| 2734 LOperand* index = UseTempRegister(instr->index()); | 2765 LOperand* index = UseTempRegister(instr->index()); |
| 2735 return DefineSameAsFirst(new(zone()) LLoadFieldByIndex(object, index)); | 2766 return DefineSameAsFirst(new(zone()) LLoadFieldByIndex(object, index)); |
| 2736 } | 2767 } |
| 2737 | 2768 |
| 2738 | 2769 |
| 2739 } } // namespace v8::internal | 2770 } } // namespace v8::internal |
| 2740 | 2771 |
| 2741 #endif // V8_TARGET_ARCH_IA32 | 2772 #endif // V8_TARGET_ARCH_IA32 |
| OLD | NEW |