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 248 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
259 __ ldr(prototype, MemOperand(prototype, Context::SlotOffset(index))); | 259 __ ldr(prototype, MemOperand(prototype, Context::SlotOffset(index))); |
260 // Load the initial map. The global functions all have initial maps. | 260 // Load the initial map. The global functions all have initial maps. |
261 __ ldr(prototype, | 261 __ ldr(prototype, |
262 FieldMemOperand(prototype, JSFunction::kPrototypeOrInitialMapOffset)); | 262 FieldMemOperand(prototype, JSFunction::kPrototypeOrInitialMapOffset)); |
263 // Load the prototype from the initial map. | 263 // Load the prototype from the initial map. |
264 __ ldr(prototype, FieldMemOperand(prototype, Map::kPrototypeOffset)); | 264 __ ldr(prototype, FieldMemOperand(prototype, Map::kPrototypeOffset)); |
265 } | 265 } |
266 | 266 |
267 | 267 |
268 void StubCompiler::GenerateDirectLoadGlobalFunctionPrototype( | 268 void StubCompiler::GenerateDirectLoadGlobalFunctionPrototype( |
269 MacroAssembler* masm, int index, Register prototype) { | 269 MacroAssembler* masm, int index, Register prototype, Label* miss) { |
| 270 // Check we're still in the same context. |
| 271 __ ldr(prototype, MemOperand(cp, Context::SlotOffset(Context::GLOBAL_INDEX))); |
| 272 __ Move(ip, Top::global()); |
| 273 __ cmp(prototype, ip); |
| 274 __ b(ne, miss); |
270 // Get the global function with the given index. | 275 // Get the global function with the given index. |
271 JSFunction* function = JSFunction::cast(Top::global_context()->get(index)); | 276 JSFunction* function = JSFunction::cast(Top::global_context()->get(index)); |
272 // Load its initial map. The global functions all have initial maps. | 277 // Load its initial map. The global functions all have initial maps. |
273 __ Move(prototype, Handle<Map>(function->initial_map())); | 278 __ Move(prototype, Handle<Map>(function->initial_map())); |
274 // Load the prototype from the initial map. | 279 // Load the prototype from the initial map. |
275 __ ldr(prototype, FieldMemOperand(prototype, Map::kPrototypeOffset)); | 280 __ ldr(prototype, FieldMemOperand(prototype, Map::kPrototypeOffset)); |
276 } | 281 } |
277 | 282 |
278 | 283 |
279 // Load a fast property out of a holder object (src). In-object properties | 284 // Load a fast property out of a holder object (src). In-object properties |
(...skipping 1147 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1427 | 1432 |
1428 const int argc = arguments().immediate(); | 1433 const int argc = arguments().immediate(); |
1429 | 1434 |
1430 Label miss; | 1435 Label miss; |
1431 Label index_out_of_range; | 1436 Label index_out_of_range; |
1432 GenerateNameCheck(name, &miss); | 1437 GenerateNameCheck(name, &miss); |
1433 | 1438 |
1434 // Check that the maps starting from the prototype haven't changed. | 1439 // Check that the maps starting from the prototype haven't changed. |
1435 GenerateDirectLoadGlobalFunctionPrototype(masm(), | 1440 GenerateDirectLoadGlobalFunctionPrototype(masm(), |
1436 Context::STRING_FUNCTION_INDEX, | 1441 Context::STRING_FUNCTION_INDEX, |
1437 r0); | 1442 r0, |
| 1443 &miss); |
1438 ASSERT(object != holder); | 1444 ASSERT(object != holder); |
1439 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, | 1445 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, |
1440 r1, r3, r4, name, &miss); | 1446 r1, r3, r4, name, &miss); |
1441 | 1447 |
1442 Register receiver = r1; | 1448 Register receiver = r1; |
1443 Register index = r4; | 1449 Register index = r4; |
1444 Register scratch = r3; | 1450 Register scratch = r3; |
1445 Register result = r0; | 1451 Register result = r0; |
1446 __ ldr(receiver, MemOperand(sp, argc * kPointerSize)); | 1452 __ ldr(receiver, MemOperand(sp, argc * kPointerSize)); |
1447 if (argc > 0) { | 1453 if (argc > 0) { |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1498 const int argc = arguments().immediate(); | 1504 const int argc = arguments().immediate(); |
1499 | 1505 |
1500 Label miss; | 1506 Label miss; |
1501 Label index_out_of_range; | 1507 Label index_out_of_range; |
1502 | 1508 |
1503 GenerateNameCheck(name, &miss); | 1509 GenerateNameCheck(name, &miss); |
1504 | 1510 |
1505 // Check that the maps starting from the prototype haven't changed. | 1511 // Check that the maps starting from the prototype haven't changed. |
1506 GenerateDirectLoadGlobalFunctionPrototype(masm(), | 1512 GenerateDirectLoadGlobalFunctionPrototype(masm(), |
1507 Context::STRING_FUNCTION_INDEX, | 1513 Context::STRING_FUNCTION_INDEX, |
1508 r0); | 1514 r0, |
| 1515 &miss); |
1509 ASSERT(object != holder); | 1516 ASSERT(object != holder); |
1510 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, | 1517 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, |
1511 r1, r3, r4, name, &miss); | 1518 r1, r3, r4, name, &miss); |
1512 | 1519 |
1513 Register receiver = r0; | 1520 Register receiver = r0; |
1514 Register index = r4; | 1521 Register index = r4; |
1515 Register scratch1 = r1; | 1522 Register scratch1 = r1; |
1516 Register scratch2 = r3; | 1523 Register scratch2 = r3; |
1517 Register result = r0; | 1524 Register result = r0; |
1518 __ ldr(receiver, MemOperand(sp, argc * kPointerSize)); | 1525 __ ldr(receiver, MemOperand(sp, argc * kPointerSize)); |
(...skipping 179 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1698 case STRING_CHECK: | 1705 case STRING_CHECK: |
1699 if (!function->IsBuiltin()) { | 1706 if (!function->IsBuiltin()) { |
1700 // Calling non-builtins with a value as receiver requires boxing. | 1707 // Calling non-builtins with a value as receiver requires boxing. |
1701 __ jmp(&miss); | 1708 __ jmp(&miss); |
1702 } else { | 1709 } else { |
1703 // Check that the object is a two-byte string or a symbol. | 1710 // Check that the object is a two-byte string or a symbol. |
1704 __ CompareObjectType(r1, r3, r3, FIRST_NONSTRING_TYPE); | 1711 __ CompareObjectType(r1, r3, r3, FIRST_NONSTRING_TYPE); |
1705 __ b(hs, &miss); | 1712 __ b(hs, &miss); |
1706 // Check that the maps starting from the prototype haven't changed. | 1713 // Check that the maps starting from the prototype haven't changed. |
1707 GenerateDirectLoadGlobalFunctionPrototype( | 1714 GenerateDirectLoadGlobalFunctionPrototype( |
1708 masm(), Context::STRING_FUNCTION_INDEX, r0); | 1715 masm(), Context::STRING_FUNCTION_INDEX, r0, &miss); |
1709 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, r3, | 1716 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, r3, |
1710 r1, r4, name, &miss); | 1717 r1, r4, name, &miss); |
1711 } | 1718 } |
1712 break; | 1719 break; |
1713 | 1720 |
1714 case NUMBER_CHECK: { | 1721 case NUMBER_CHECK: { |
1715 if (!function->IsBuiltin()) { | 1722 if (!function->IsBuiltin()) { |
1716 // Calling non-builtins with a value as receiver requires boxing. | 1723 // Calling non-builtins with a value as receiver requires boxing. |
1717 __ jmp(&miss); | 1724 __ jmp(&miss); |
1718 } else { | 1725 } else { |
1719 Label fast; | 1726 Label fast; |
1720 // Check that the object is a smi or a heap number. | 1727 // Check that the object is a smi or a heap number. |
1721 __ tst(r1, Operand(kSmiTagMask)); | 1728 __ tst(r1, Operand(kSmiTagMask)); |
1722 __ b(eq, &fast); | 1729 __ b(eq, &fast); |
1723 __ CompareObjectType(r1, r0, r0, HEAP_NUMBER_TYPE); | 1730 __ CompareObjectType(r1, r0, r0, HEAP_NUMBER_TYPE); |
1724 __ b(ne, &miss); | 1731 __ b(ne, &miss); |
1725 __ bind(&fast); | 1732 __ bind(&fast); |
1726 // Check that the maps starting from the prototype haven't changed. | 1733 // Check that the maps starting from the prototype haven't changed. |
1727 GenerateDirectLoadGlobalFunctionPrototype( | 1734 GenerateDirectLoadGlobalFunctionPrototype( |
1728 masm(), Context::NUMBER_FUNCTION_INDEX, r0); | 1735 masm(), Context::NUMBER_FUNCTION_INDEX, r0, &miss); |
1729 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, r3, | 1736 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, r3, |
1730 r1, r4, name, &miss); | 1737 r1, r4, name, &miss); |
1731 } | 1738 } |
1732 break; | 1739 break; |
1733 } | 1740 } |
1734 | 1741 |
1735 case BOOLEAN_CHECK: { | 1742 case BOOLEAN_CHECK: { |
1736 if (!function->IsBuiltin()) { | 1743 if (!function->IsBuiltin()) { |
1737 // Calling non-builtins with a value as receiver requires boxing. | 1744 // Calling non-builtins with a value as receiver requires boxing. |
1738 __ jmp(&miss); | 1745 __ jmp(&miss); |
1739 } else { | 1746 } else { |
1740 Label fast; | 1747 Label fast; |
1741 // Check that the object is a boolean. | 1748 // Check that the object is a boolean. |
1742 __ LoadRoot(ip, Heap::kTrueValueRootIndex); | 1749 __ LoadRoot(ip, Heap::kTrueValueRootIndex); |
1743 __ cmp(r1, ip); | 1750 __ cmp(r1, ip); |
1744 __ b(eq, &fast); | 1751 __ b(eq, &fast); |
1745 __ LoadRoot(ip, Heap::kFalseValueRootIndex); | 1752 __ LoadRoot(ip, Heap::kFalseValueRootIndex); |
1746 __ cmp(r1, ip); | 1753 __ cmp(r1, ip); |
1747 __ b(ne, &miss); | 1754 __ b(ne, &miss); |
1748 __ bind(&fast); | 1755 __ bind(&fast); |
1749 // Check that the maps starting from the prototype haven't changed. | 1756 // Check that the maps starting from the prototype haven't changed. |
1750 GenerateDirectLoadGlobalFunctionPrototype( | 1757 GenerateDirectLoadGlobalFunctionPrototype( |
1751 masm(), Context::BOOLEAN_FUNCTION_INDEX, r0); | 1758 masm(), Context::BOOLEAN_FUNCTION_INDEX, r0, &miss); |
1752 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, r3, | 1759 CheckPrototypes(JSObject::cast(object->GetPrototype()), r0, holder, r3, |
1753 r1, r4, name, &miss); | 1760 r1, r4, name, &miss); |
1754 } | 1761 } |
1755 break; | 1762 break; |
1756 } | 1763 } |
1757 | 1764 |
1758 default: | 1765 default: |
1759 UNREACHABLE(); | 1766 UNREACHABLE(); |
1760 } | 1767 } |
1761 | 1768 |
(...skipping 804 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2566 // Return the generated code. | 2573 // Return the generated code. |
2567 return GetCode(); | 2574 return GetCode(); |
2568 } | 2575 } |
2569 | 2576 |
2570 | 2577 |
2571 #undef __ | 2578 #undef __ |
2572 | 2579 |
2573 } } // namespace v8::internal | 2580 } } // namespace v8::internal |
2574 | 2581 |
2575 #endif // V8_TARGET_ARCH_ARM | 2582 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |