OLD | NEW |
1 // Copyright 2006-2009 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2009 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 1348 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1359 | 1359 |
1360 CheckPrototypes(JSObject::cast(object), edx, | 1360 CheckPrototypes(JSObject::cast(object), edx, |
1361 holder, ebx, | 1361 holder, ebx, |
1362 eax, edi, name, &miss); | 1362 eax, edi, name, &miss); |
1363 | 1363 |
1364 if (argc == 0) { | 1364 if (argc == 0) { |
1365 // Noop, return the length. | 1365 // Noop, return the length. |
1366 __ mov(eax, FieldOperand(edx, JSArray::kLengthOffset)); | 1366 __ mov(eax, FieldOperand(edx, JSArray::kLengthOffset)); |
1367 __ ret((argc + 1) * kPointerSize); | 1367 __ ret((argc + 1) * kPointerSize); |
1368 } else { | 1368 } else { |
| 1369 Label call_builtin; |
| 1370 |
1369 // Get the elements array of the object. | 1371 // Get the elements array of the object. |
1370 __ mov(ebx, FieldOperand(edx, JSArray::kElementsOffset)); | 1372 __ mov(ebx, FieldOperand(edx, JSArray::kElementsOffset)); |
1371 | 1373 |
1372 // Check that the elements are in fast mode (not dictionary). | 1374 // Check that the elements are in fast mode and writable. |
1373 __ cmp(FieldOperand(ebx, HeapObject::kMapOffset), | 1375 __ cmp(FieldOperand(ebx, HeapObject::kMapOffset), |
1374 Immediate(Factory::fixed_array_map())); | 1376 Immediate(Factory::fixed_array_map())); |
1375 __ j(not_equal, &miss); | 1377 __ j(not_equal, &call_builtin); |
1376 | 1378 |
1377 if (argc == 1) { // Otherwise fall through to call builtin. | 1379 if (argc == 1) { // Otherwise fall through to call builtin. |
1378 Label call_builtin, exit, with_write_barrier, attempt_to_grow_elements; | 1380 Label exit, with_write_barrier, attempt_to_grow_elements; |
1379 | 1381 |
1380 // Get the array's length into eax and calculate new length. | 1382 // Get the array's length into eax and calculate new length. |
1381 __ mov(eax, FieldOperand(edx, JSArray::kLengthOffset)); | 1383 __ mov(eax, FieldOperand(edx, JSArray::kLengthOffset)); |
1382 STATIC_ASSERT(kSmiTagSize == 1); | 1384 STATIC_ASSERT(kSmiTagSize == 1); |
1383 STATIC_ASSERT(kSmiTag == 0); | 1385 STATIC_ASSERT(kSmiTag == 0); |
1384 __ add(Operand(eax), Immediate(Smi::FromInt(argc))); | 1386 __ add(Operand(eax), Immediate(Smi::FromInt(argc))); |
1385 | 1387 |
1386 // Get the element's length into ecx. | 1388 // Get the element's length into ecx. |
1387 __ mov(ecx, FieldOperand(ebx, FixedArray::kLengthOffset)); | 1389 __ mov(ecx, FieldOperand(ebx, FixedArray::kLengthOffset)); |
1388 | 1390 |
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1449 // Restore receiver to edx as finish sequence assumes it's here. | 1451 // Restore receiver to edx as finish sequence assumes it's here. |
1450 __ mov(edx, Operand(esp, (argc + 1) * kPointerSize)); | 1452 __ mov(edx, Operand(esp, (argc + 1) * kPointerSize)); |
1451 | 1453 |
1452 // Increment element's and array's sizes. | 1454 // Increment element's and array's sizes. |
1453 __ add(FieldOperand(ebx, FixedArray::kLengthOffset), | 1455 __ add(FieldOperand(ebx, FixedArray::kLengthOffset), |
1454 Immediate(Smi::FromInt(kAllocationDelta))); | 1456 Immediate(Smi::FromInt(kAllocationDelta))); |
1455 __ mov(FieldOperand(edx, JSArray::kLengthOffset), eax); | 1457 __ mov(FieldOperand(edx, JSArray::kLengthOffset), eax); |
1456 | 1458 |
1457 // Elements are in new space, so write barrier is not required. | 1459 // Elements are in new space, so write barrier is not required. |
1458 __ ret((argc + 1) * kPointerSize); | 1460 __ ret((argc + 1) * kPointerSize); |
1459 | |
1460 __ bind(&call_builtin); | |
1461 } | 1461 } |
1462 | 1462 |
| 1463 __ bind(&call_builtin); |
1463 __ TailCallExternalReference(ExternalReference(Builtins::c_ArrayPush), | 1464 __ TailCallExternalReference(ExternalReference(Builtins::c_ArrayPush), |
1464 argc + 1, | 1465 argc + 1, |
1465 1); | 1466 1); |
1466 } | 1467 } |
1467 | 1468 |
1468 __ bind(&miss); | 1469 __ bind(&miss); |
1469 Object* obj = GenerateMissBranch(); | 1470 Object* obj = GenerateMissBranch(); |
1470 if (obj->IsFailure()) return obj; | 1471 if (obj->IsFailure()) return obj; |
1471 | 1472 |
1472 // Return the generated code. | 1473 // Return the generated code. |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1504 // Check that the receiver isn't a smi. | 1505 // Check that the receiver isn't a smi. |
1505 __ test(edx, Immediate(kSmiTagMask)); | 1506 __ test(edx, Immediate(kSmiTagMask)); |
1506 __ j(zero, &miss); | 1507 __ j(zero, &miss); |
1507 CheckPrototypes(JSObject::cast(object), edx, | 1508 CheckPrototypes(JSObject::cast(object), edx, |
1508 holder, ebx, | 1509 holder, ebx, |
1509 eax, edi, name, &miss); | 1510 eax, edi, name, &miss); |
1510 | 1511 |
1511 // Get the elements array of the object. | 1512 // Get the elements array of the object. |
1512 __ mov(ebx, FieldOperand(edx, JSArray::kElementsOffset)); | 1513 __ mov(ebx, FieldOperand(edx, JSArray::kElementsOffset)); |
1513 | 1514 |
1514 // Check that the elements are in fast mode (not dictionary). | 1515 // Check that the elements are in fast mode and writable. |
1515 __ cmp(FieldOperand(ebx, HeapObject::kMapOffset), | 1516 __ cmp(FieldOperand(ebx, HeapObject::kMapOffset), |
1516 Immediate(Factory::fixed_array_map())); | 1517 Immediate(Factory::fixed_array_map())); |
1517 __ j(not_equal, &miss); | 1518 __ j(not_equal, &call_builtin); |
1518 | 1519 |
1519 // Get the array's length into ecx and calculate new length. | 1520 // Get the array's length into ecx and calculate new length. |
1520 __ mov(ecx, FieldOperand(edx, JSArray::kLengthOffset)); | 1521 __ mov(ecx, FieldOperand(edx, JSArray::kLengthOffset)); |
1521 __ sub(Operand(ecx), Immediate(Smi::FromInt(1))); | 1522 __ sub(Operand(ecx), Immediate(Smi::FromInt(1))); |
1522 __ j(negative, &return_undefined); | 1523 __ j(negative, &return_undefined); |
1523 | 1524 |
1524 // Get the last element. | 1525 // Get the last element. |
1525 STATIC_ASSERT(kSmiTagSize == 1); | 1526 STATIC_ASSERT(kSmiTagSize == 1); |
1526 STATIC_ASSERT(kSmiTag == 0); | 1527 STATIC_ASSERT(kSmiTag == 0); |
1527 __ mov(eax, FieldOperand(ebx, | 1528 __ mov(eax, FieldOperand(ebx, |
(...skipping 1203 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2731 // Return the generated code. | 2732 // Return the generated code. |
2732 return GetCode(); | 2733 return GetCode(); |
2733 } | 2734 } |
2734 | 2735 |
2735 | 2736 |
2736 #undef __ | 2737 #undef __ |
2737 | 2738 |
2738 } } // namespace v8::internal | 2739 } } // namespace v8::internal |
2739 | 2740 |
2740 #endif // V8_TARGET_ARCH_IA32 | 2741 #endif // V8_TARGET_ARCH_IA32 |
OLD | NEW |