Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(132)

Side by Side Diff: src/ia32/code-stubs-ia32.cc

Issue 23537038: Remove override mode from BinaryOpStub (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 7 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/full-codegen.cc ('k') | src/ia32/full-codegen-ia32.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 1190 matching lines...) Expand 10 before | Expand all | Expand 10 after
1201 (StringAddFlags)(STRING_ADD_CHECK_NONE | STRING_ADD_ERECT_FRAME)); 1201 (StringAddFlags)(STRING_ADD_CHECK_NONE | STRING_ADD_ERECT_FRAME));
1202 GenerateRegisterArgsPush(masm); 1202 GenerateRegisterArgsPush(masm);
1203 __ TailCallStub(&string_add_stub); 1203 __ TailCallStub(&string_add_stub);
1204 1204
1205 __ bind(&call_runtime); 1205 __ bind(&call_runtime);
1206 GenerateTypeTransition(masm); 1206 GenerateTypeTransition(masm);
1207 } 1207 }
1208 1208
1209 1209
1210 static void BinaryOpStub_GenerateHeapResultAllocation(MacroAssembler* masm, 1210 static void BinaryOpStub_GenerateHeapResultAllocation(MacroAssembler* masm,
1211 Label* alloc_failure, 1211 Label* alloc_failure);
1212 OverwriteMode mode);
1213 1212
1214 1213
1215 // Input: 1214 // Input:
1216 // edx: left operand (tagged) 1215 // edx: left operand (tagged)
1217 // eax: right operand (tagged) 1216 // eax: right operand (tagged)
1218 // Output: 1217 // Output:
1219 // eax: result (tagged) 1218 // eax: result (tagged)
1220 void BinaryOpStub::GenerateInt32Stub(MacroAssembler* masm) { 1219 void BinaryOpStub::GenerateInt32Stub(MacroAssembler* masm) {
1221 Label call_runtime; 1220 Label call_runtime;
1222 ASSERT(Max(left_type_, right_type_) == BinaryOpIC::INT32); 1221 ASSERT(Max(left_type_, right_type_) == BinaryOpIC::INT32);
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
1261 case Token::SUB: __ subsd(xmm0, xmm1); break; 1260 case Token::SUB: __ subsd(xmm0, xmm1); break;
1262 case Token::MUL: __ mulsd(xmm0, xmm1); break; 1261 case Token::MUL: __ mulsd(xmm0, xmm1); break;
1263 case Token::DIV: __ divsd(xmm0, xmm1); break; 1262 case Token::DIV: __ divsd(xmm0, xmm1); break;
1264 default: UNREACHABLE(); 1263 default: UNREACHABLE();
1265 } 1264 }
1266 // Check result type if it is currently Int32. 1265 // Check result type if it is currently Int32.
1267 if (result_type_ <= BinaryOpIC::INT32) { 1266 if (result_type_ <= BinaryOpIC::INT32) {
1268 FloatingPointHelper::CheckSSE2OperandIsInt32( 1267 FloatingPointHelper::CheckSSE2OperandIsInt32(
1269 masm, &not_int32, xmm0, ecx, ecx, xmm2); 1268 masm, &not_int32, xmm0, ecx, ecx, xmm2);
1270 } 1269 }
1271 BinaryOpStub_GenerateHeapResultAllocation(masm, &call_runtime, mode_); 1270 BinaryOpStub_GenerateHeapResultAllocation(masm, &call_runtime);
1272 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0); 1271 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0);
1273 __ ret(0); 1272 __ ret(0);
1274 } 1273 }
1275 } else { // SSE2 not available, use FPU. 1274 } else { // SSE2 not available, use FPU.
1276 FloatingPointHelper::CheckFloatOperands(masm, &not_floats, ebx); 1275 FloatingPointHelper::CheckFloatOperands(masm, &not_floats, ebx);
1277 FloatingPointHelper::LoadFloatOperands( 1276 FloatingPointHelper::LoadFloatOperands(
1278 masm, 1277 masm,
1279 ecx, 1278 ecx,
1280 FloatingPointHelper::ARGS_IN_REGISTERS); 1279 FloatingPointHelper::ARGS_IN_REGISTERS);
1281 if (op_ == Token::MOD) { 1280 if (op_ == Token::MOD) {
1282 // The operands are now on the FPU stack, but we don't need them. 1281 // The operands are now on the FPU stack, but we don't need them.
1283 __ fstp(0); 1282 __ fstp(0);
1284 __ fstp(0); 1283 __ fstp(0);
1285 GenerateRegisterArgsPush(masm); 1284 GenerateRegisterArgsPush(masm);
1286 __ InvokeBuiltin(Builtins::MOD, JUMP_FUNCTION); 1285 __ InvokeBuiltin(Builtins::MOD, JUMP_FUNCTION);
1287 } else { 1286 } else {
1288 switch (op_) { 1287 switch (op_) {
1289 case Token::ADD: __ faddp(1); break; 1288 case Token::ADD: __ faddp(1); break;
1290 case Token::SUB: __ fsubp(1); break; 1289 case Token::SUB: __ fsubp(1); break;
1291 case Token::MUL: __ fmulp(1); break; 1290 case Token::MUL: __ fmulp(1); break;
1292 case Token::DIV: __ fdivp(1); break; 1291 case Token::DIV: __ fdivp(1); break;
1293 default: UNREACHABLE(); 1292 default: UNREACHABLE();
1294 } 1293 }
1295 Label after_alloc_failure; 1294 Label after_alloc_failure;
1296 BinaryOpStub_GenerateHeapResultAllocation( 1295 BinaryOpStub_GenerateHeapResultAllocation(
1297 masm, &after_alloc_failure, mode_); 1296 masm, &after_alloc_failure);
1298 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset)); 1297 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset));
1299 __ ret(0); 1298 __ ret(0);
1300 __ bind(&after_alloc_failure); 1299 __ bind(&after_alloc_failure);
1301 __ fstp(0); // Pop FPU stack before calling runtime. 1300 __ fstp(0); // Pop FPU stack before calling runtime.
1302 __ jmp(&call_runtime); 1301 __ jmp(&call_runtime);
1303 } 1302 }
1304 } 1303 }
1305 1304
1306 __ bind(&not_floats); 1305 __ bind(&not_floats);
1307 __ bind(&not_int32); 1306 __ bind(&not_int32);
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
1345 __ SmiTag(eax); 1344 __ SmiTag(eax);
1346 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack. 1345 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack.
1347 1346
1348 // All ops except SHR return a signed int32 that we load in 1347 // All ops except SHR return a signed int32 that we load in
1349 // a HeapNumber. 1348 // a HeapNumber.
1350 if (op_ != Token::SHR) { 1349 if (op_ != Token::SHR) {
1351 __ bind(&non_smi_result); 1350 __ bind(&non_smi_result);
1352 // Allocate a heap number if needed. 1351 // Allocate a heap number if needed.
1353 __ mov(ebx, eax); // ebx: result 1352 __ mov(ebx, eax); // ebx: result
1354 Label skip_allocation; 1353 Label skip_allocation;
1355 switch (mode_) { 1354 __ AllocateHeapNumber(eax, ecx, edx, &call_runtime);
1356 case OVERWRITE_LEFT: 1355 __ bind(&skip_allocation);
1357 case OVERWRITE_RIGHT:
1358 // If the operand was an object, we skip the
1359 // allocation of a heap number.
1360 __ mov(eax, Operand(esp, mode_ == OVERWRITE_RIGHT ?
1361 1 * kPointerSize : 2 * kPointerSize));
1362 __ JumpIfNotSmi(eax, &skip_allocation, Label::kNear);
1363 // Fall through!
1364 case NO_OVERWRITE:
1365 __ AllocateHeapNumber(eax, ecx, edx, &call_runtime);
1366 __ bind(&skip_allocation);
1367 break;
1368 default: UNREACHABLE();
1369 }
1370 // Store the result in the HeapNumber and return. 1356 // Store the result in the HeapNumber and return.
1371 if (CpuFeatures::IsSupported(SSE2)) { 1357 if (CpuFeatures::IsSupported(SSE2)) {
1372 CpuFeatureScope use_sse2(masm, SSE2); 1358 CpuFeatureScope use_sse2(masm, SSE2);
1373 __ Cvtsi2sd(xmm0, ebx); 1359 __ Cvtsi2sd(xmm0, ebx);
1374 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0); 1360 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0);
1375 } else { 1361 } else {
1376 __ mov(Operand(esp, 1 * kPointerSize), ebx); 1362 __ mov(Operand(esp, 1 * kPointerSize), ebx);
1377 __ fild_s(Operand(esp, 1 * kPointerSize)); 1363 __ fild_s(Operand(esp, 1 * kPointerSize));
1378 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset)); 1364 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset));
1379 } 1365 }
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after
1490 masm, &not_floats, xmm1, ecx, ecx, xmm2); 1476 masm, &not_floats, xmm1, ecx, ecx, xmm2);
1491 } 1477 }
1492 1478
1493 switch (op_) { 1479 switch (op_) {
1494 case Token::ADD: __ addsd(xmm0, xmm1); break; 1480 case Token::ADD: __ addsd(xmm0, xmm1); break;
1495 case Token::SUB: __ subsd(xmm0, xmm1); break; 1481 case Token::SUB: __ subsd(xmm0, xmm1); break;
1496 case Token::MUL: __ mulsd(xmm0, xmm1); break; 1482 case Token::MUL: __ mulsd(xmm0, xmm1); break;
1497 case Token::DIV: __ divsd(xmm0, xmm1); break; 1483 case Token::DIV: __ divsd(xmm0, xmm1); break;
1498 default: UNREACHABLE(); 1484 default: UNREACHABLE();
1499 } 1485 }
1500 BinaryOpStub_GenerateHeapResultAllocation(masm, &call_runtime, mode_); 1486 BinaryOpStub_GenerateHeapResultAllocation(masm, &call_runtime);
1501 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0); 1487 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0);
1502 __ ret(0); 1488 __ ret(0);
1503 } else { // SSE2 not available, use FPU. 1489 } else { // SSE2 not available, use FPU.
1504 FloatingPointHelper::CheckFloatOperands(masm, &not_floats, ebx); 1490 FloatingPointHelper::CheckFloatOperands(masm, &not_floats, ebx);
1505 FloatingPointHelper::LoadFloatOperands( 1491 FloatingPointHelper::LoadFloatOperands(
1506 masm, 1492 masm,
1507 ecx, 1493 ecx,
1508 FloatingPointHelper::ARGS_IN_REGISTERS); 1494 FloatingPointHelper::ARGS_IN_REGISTERS);
1509 switch (op_) { 1495 switch (op_) {
1510 case Token::ADD: __ faddp(1); break; 1496 case Token::ADD: __ faddp(1); break;
1511 case Token::SUB: __ fsubp(1); break; 1497 case Token::SUB: __ fsubp(1); break;
1512 case Token::MUL: __ fmulp(1); break; 1498 case Token::MUL: __ fmulp(1); break;
1513 case Token::DIV: __ fdivp(1); break; 1499 case Token::DIV: __ fdivp(1); break;
1514 default: UNREACHABLE(); 1500 default: UNREACHABLE();
1515 } 1501 }
1516 Label after_alloc_failure; 1502 Label after_alloc_failure;
1517 BinaryOpStub_GenerateHeapResultAllocation( 1503 BinaryOpStub_GenerateHeapResultAllocation(
1518 masm, &after_alloc_failure, mode_); 1504 masm, &after_alloc_failure);
1519 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset)); 1505 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset));
1520 __ ret(0); 1506 __ ret(0);
1521 __ bind(&after_alloc_failure); 1507 __ bind(&after_alloc_failure);
1522 __ fstp(0); // Pop FPU stack before calling runtime. 1508 __ fstp(0); // Pop FPU stack before calling runtime.
1523 __ jmp(&call_runtime); 1509 __ jmp(&call_runtime);
1524 } 1510 }
1525 1511
1526 __ bind(&not_floats); 1512 __ bind(&not_floats);
1527 GenerateTypeTransition(masm); 1513 GenerateTypeTransition(masm);
1528 break; 1514 break;
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
1569 __ SmiTag(eax); 1555 __ SmiTag(eax);
1570 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack. 1556 __ ret(2 * kPointerSize); // Drop two pushed arguments from the stack.
1571 1557
1572 // All ops except SHR return a signed int32 that we load in 1558 // All ops except SHR return a signed int32 that we load in
1573 // a HeapNumber. 1559 // a HeapNumber.
1574 if (op_ != Token::SHR) { 1560 if (op_ != Token::SHR) {
1575 __ bind(&non_smi_result); 1561 __ bind(&non_smi_result);
1576 // Allocate a heap number if needed. 1562 // Allocate a heap number if needed.
1577 __ mov(ebx, eax); // ebx: result 1563 __ mov(ebx, eax); // ebx: result
1578 Label skip_allocation; 1564 Label skip_allocation;
1579 switch (mode_) { 1565 __ AllocateHeapNumber(eax, ecx, edx, &call_runtime);
1580 case OVERWRITE_LEFT: 1566 __ bind(&skip_allocation);
1581 case OVERWRITE_RIGHT:
1582 // If the operand was an object, we skip the
1583 // allocation of a heap number.
1584 __ mov(eax, Operand(esp, mode_ == OVERWRITE_RIGHT ?
1585 1 * kPointerSize : 2 * kPointerSize));
1586 __ JumpIfNotSmi(eax, &skip_allocation, Label::kNear);
1587 // Fall through!
1588 case NO_OVERWRITE:
1589 __ AllocateHeapNumber(eax, ecx, edx, &call_runtime);
1590 __ bind(&skip_allocation);
1591 break;
1592 default: UNREACHABLE();
1593 }
1594 // Store the result in the HeapNumber and return. 1567 // Store the result in the HeapNumber and return.
1595 if (CpuFeatures::IsSupported(SSE2)) { 1568 if (CpuFeatures::IsSupported(SSE2)) {
1596 CpuFeatureScope use_sse2(masm, SSE2); 1569 CpuFeatureScope use_sse2(masm, SSE2);
1597 __ Cvtsi2sd(xmm0, ebx); 1570 __ Cvtsi2sd(xmm0, ebx);
1598 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0); 1571 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0);
1599 } else { 1572 } else {
1600 __ mov(Operand(esp, 1 * kPointerSize), ebx); 1573 __ mov(Operand(esp, 1 * kPointerSize), ebx);
1601 __ fild_s(Operand(esp, 1 * kPointerSize)); 1574 __ fild_s(Operand(esp, 1 * kPointerSize));
1602 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset)); 1575 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset));
1603 } 1576 }
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
1683 CpuFeatureScope use_sse2(masm, SSE2); 1656 CpuFeatureScope use_sse2(masm, SSE2);
1684 FloatingPointHelper::LoadSSE2Operands(masm, &not_floats); 1657 FloatingPointHelper::LoadSSE2Operands(masm, &not_floats);
1685 1658
1686 switch (op_) { 1659 switch (op_) {
1687 case Token::ADD: __ addsd(xmm0, xmm1); break; 1660 case Token::ADD: __ addsd(xmm0, xmm1); break;
1688 case Token::SUB: __ subsd(xmm0, xmm1); break; 1661 case Token::SUB: __ subsd(xmm0, xmm1); break;
1689 case Token::MUL: __ mulsd(xmm0, xmm1); break; 1662 case Token::MUL: __ mulsd(xmm0, xmm1); break;
1690 case Token::DIV: __ divsd(xmm0, xmm1); break; 1663 case Token::DIV: __ divsd(xmm0, xmm1); break;
1691 default: UNREACHABLE(); 1664 default: UNREACHABLE();
1692 } 1665 }
1693 BinaryOpStub_GenerateHeapResultAllocation(masm, &call_runtime, mode_); 1666 BinaryOpStub_GenerateHeapResultAllocation(masm, &call_runtime);
1694 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0); 1667 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0);
1695 __ ret(0); 1668 __ ret(0);
1696 } else { // SSE2 not available, use FPU. 1669 } else { // SSE2 not available, use FPU.
1697 FloatingPointHelper::CheckFloatOperands(masm, &not_floats, ebx); 1670 FloatingPointHelper::CheckFloatOperands(masm, &not_floats, ebx);
1698 FloatingPointHelper::LoadFloatOperands( 1671 FloatingPointHelper::LoadFloatOperands(
1699 masm, 1672 masm,
1700 ecx, 1673 ecx,
1701 FloatingPointHelper::ARGS_IN_REGISTERS); 1674 FloatingPointHelper::ARGS_IN_REGISTERS);
1702 switch (op_) { 1675 switch (op_) {
1703 case Token::ADD: __ faddp(1); break; 1676 case Token::ADD: __ faddp(1); break;
1704 case Token::SUB: __ fsubp(1); break; 1677 case Token::SUB: __ fsubp(1); break;
1705 case Token::MUL: __ fmulp(1); break; 1678 case Token::MUL: __ fmulp(1); break;
1706 case Token::DIV: __ fdivp(1); break; 1679 case Token::DIV: __ fdivp(1); break;
1707 default: UNREACHABLE(); 1680 default: UNREACHABLE();
1708 } 1681 }
1709 Label after_alloc_failure; 1682 Label after_alloc_failure;
1710 BinaryOpStub_GenerateHeapResultAllocation( 1683 BinaryOpStub_GenerateHeapResultAllocation(
1711 masm, &after_alloc_failure, mode_); 1684 masm, &after_alloc_failure);
1712 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset)); 1685 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset));
1713 __ ret(0); 1686 __ ret(0);
1714 __ bind(&after_alloc_failure); 1687 __ bind(&after_alloc_failure);
1715 __ fstp(0); // Pop FPU stack before calling runtime. 1688 __ fstp(0); // Pop FPU stack before calling runtime.
1716 __ jmp(&call_runtime); 1689 __ jmp(&call_runtime);
1717 } 1690 }
1718 __ bind(&not_floats); 1691 __ bind(&not_floats);
1719 break; 1692 break;
1720 } 1693 }
1721 case Token::MOD: { 1694 case Token::MOD: {
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
1757 __ SmiTag(eax); 1730 __ SmiTag(eax);
1758 __ ret(2 * kPointerSize); // Drop the arguments from the stack. 1731 __ ret(2 * kPointerSize); // Drop the arguments from the stack.
1759 1732
1760 // All ops except SHR return a signed int32 that we load in 1733 // All ops except SHR return a signed int32 that we load in
1761 // a HeapNumber. 1734 // a HeapNumber.
1762 if (op_ != Token::SHR) { 1735 if (op_ != Token::SHR) {
1763 __ bind(&non_smi_result); 1736 __ bind(&non_smi_result);
1764 // Allocate a heap number if needed. 1737 // Allocate a heap number if needed.
1765 __ mov(ebx, eax); // ebx: result 1738 __ mov(ebx, eax); // ebx: result
1766 Label skip_allocation; 1739 Label skip_allocation;
1767 switch (mode_) { 1740 __ AllocateHeapNumber(eax, ecx, edx, &call_runtime);
1768 case OVERWRITE_LEFT: 1741 __ bind(&skip_allocation);
1769 case OVERWRITE_RIGHT:
1770 // If the operand was an object, we skip the
1771 // allocation of a heap number.
1772 __ mov(eax, Operand(esp, mode_ == OVERWRITE_RIGHT ?
1773 1 * kPointerSize : 2 * kPointerSize));
1774 __ JumpIfNotSmi(eax, &skip_allocation, Label::kNear);
1775 // Fall through!
1776 case NO_OVERWRITE:
1777 __ AllocateHeapNumber(eax, ecx, edx, &call_runtime);
1778 __ bind(&skip_allocation);
1779 break;
1780 default: UNREACHABLE();
1781 }
1782 // Store the result in the HeapNumber and return. 1742 // Store the result in the HeapNumber and return.
1783 if (CpuFeatures::IsSupported(SSE2)) { 1743 if (CpuFeatures::IsSupported(SSE2)) {
1784 CpuFeatureScope use_sse2(masm, SSE2); 1744 CpuFeatureScope use_sse2(masm, SSE2);
1785 __ Cvtsi2sd(xmm0, ebx); 1745 __ Cvtsi2sd(xmm0, ebx);
1786 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0); 1746 __ movdbl(FieldOperand(eax, HeapNumber::kValueOffset), xmm0);
1787 } else { 1747 } else {
1788 __ mov(Operand(esp, 1 * kPointerSize), ebx); 1748 __ mov(Operand(esp, 1 * kPointerSize), ebx);
1789 __ fild_s(Operand(esp, 1 * kPointerSize)); 1749 __ fild_s(Operand(esp, 1 * kPointerSize));
1790 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset)); 1750 __ fstp_d(FieldOperand(eax, HeapNumber::kValueOffset));
1791 } 1751 }
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after
1858 (StringAddFlags)(STRING_ADD_CHECK_LEFT | STRING_ADD_ERECT_FRAME)); 1818 (StringAddFlags)(STRING_ADD_CHECK_LEFT | STRING_ADD_ERECT_FRAME));
1859 GenerateRegisterArgsPush(masm); 1819 GenerateRegisterArgsPush(masm);
1860 __ TailCallStub(&string_add_right_stub); 1820 __ TailCallStub(&string_add_right_stub);
1861 1821
1862 // Neither argument is a string. 1822 // Neither argument is a string.
1863 __ bind(&call_runtime); 1823 __ bind(&call_runtime);
1864 } 1824 }
1865 1825
1866 1826
1867 static void BinaryOpStub_GenerateHeapResultAllocation(MacroAssembler* masm, 1827 static void BinaryOpStub_GenerateHeapResultAllocation(MacroAssembler* masm,
1868 Label* alloc_failure, 1828 Label* alloc_failure) {
1869 OverwriteMode mode) {
1870 Label skip_allocation; 1829 Label skip_allocation;
1871 switch (mode) { 1830 // Allocate a heap number for the result. Keep eax and edx intact
1872 case OVERWRITE_LEFT: { 1831 // for the possible runtime call.
1873 // If the argument in edx is already an object, we skip the 1832 __ AllocateHeapNumber(ebx, ecx, no_reg, alloc_failure);
1874 // allocation of a heap number. 1833 // Now eax can be overwritten losing one of the arguments as we are
1875 __ JumpIfNotSmi(edx, &skip_allocation, Label::kNear); 1834 // now done and will not need it any more.
1876 // Allocate a heap number for the result. Keep eax and edx intact 1835 __ mov(eax, ebx);
1877 // for the possible runtime call. 1836 __ bind(&skip_allocation);
1878 __ AllocateHeapNumber(ebx, ecx, no_reg, alloc_failure);
1879 // Now edx can be overwritten losing one of the arguments as we are
1880 // now done and will not need it any more.
1881 __ mov(edx, ebx);
1882 __ bind(&skip_allocation);
1883 // Use object in edx as a result holder
1884 __ mov(eax, edx);
1885 break;
1886 }
1887 case OVERWRITE_RIGHT:
1888 // If the argument in eax is already an object, we skip the
1889 // allocation of a heap number.
1890 __ JumpIfNotSmi(eax, &skip_allocation, Label::kNear);
1891 // Fall through!
1892 case NO_OVERWRITE:
1893 // Allocate a heap number for the result. Keep eax and edx intact
1894 // for the possible runtime call.
1895 __ AllocateHeapNumber(ebx, ecx, no_reg, alloc_failure);
1896 // Now eax can be overwritten losing one of the arguments as we are
1897 // now done and will not need it any more.
1898 __ mov(eax, ebx);
1899 __ bind(&skip_allocation);
1900 break;
1901 default: UNREACHABLE();
1902 }
1903 } 1837 }
1904 1838
1905 1839
1906 void BinaryOpStub::GenerateRegisterArgsPush(MacroAssembler* masm) { 1840 void BinaryOpStub::GenerateRegisterArgsPush(MacroAssembler* masm) {
1907 __ pop(ecx); 1841 __ pop(ecx);
1908 __ push(edx); 1842 __ push(edx);
1909 __ push(eax); 1843 __ push(eax);
1910 __ push(ecx); 1844 __ push(ecx);
1911 } 1845 }
1912 1846
(...skipping 5634 matching lines...) Expand 10 before | Expand all | Expand 10 after
7547 __ bind(&fast_elements_case); 7481 __ bind(&fast_elements_case);
7548 GenerateCase(masm, FAST_ELEMENTS); 7482 GenerateCase(masm, FAST_ELEMENTS);
7549 } 7483 }
7550 7484
7551 7485
7552 #undef __ 7486 #undef __
7553 7487
7554 } } // namespace v8::internal 7488 } } // namespace v8::internal
7555 7489
7556 #endif // V8_TARGET_ARCH_IA32 7490 #endif // V8_TARGET_ARCH_IA32
OLDNEW
« no previous file with comments | « src/full-codegen.cc ('k') | src/ia32/full-codegen-ia32.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698