| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/globals.h" | 5 #include "vm/globals.h" |
| 6 #if defined(TARGET_ARCH_ARM) | 6 #if defined(TARGET_ARCH_ARM) |
| 7 | 7 |
| 8 #include "vm/assembler.h" | 8 #include "vm/assembler.h" |
| 9 #include "vm/code_generator.h" | 9 #include "vm/code_generator.h" |
| 10 #include "vm/compiler.h" | 10 #include "vm/compiler.h" |
| (...skipping 1575 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1586 void StubCode::GenerateClosureCallInlineCacheStub(Assembler* assembler) { | 1586 void StubCode::GenerateClosureCallInlineCacheStub(Assembler* assembler) { |
| 1587 GenerateNArgsCheckInlineCacheStub(assembler, 1); | 1587 GenerateNArgsCheckInlineCacheStub(assembler, 1); |
| 1588 } | 1588 } |
| 1589 | 1589 |
| 1590 | 1590 |
| 1591 void StubCode::GenerateMegamorphicCallStub(Assembler* assembler) { | 1591 void StubCode::GenerateMegamorphicCallStub(Assembler* assembler) { |
| 1592 GenerateNArgsCheckInlineCacheStub(assembler, 1); | 1592 GenerateNArgsCheckInlineCacheStub(assembler, 1); |
| 1593 } | 1593 } |
| 1594 | 1594 |
| 1595 | 1595 |
| 1596 // Intermediary stub between a static call and its target. ICData contains |
| 1597 // the target function and the call count. |
| 1598 // R5: ICData |
| 1599 void StubCode::GenerateUnoptimizedStaticCallStub(Assembler* assembler) { |
| 1600 GenerateUsageCounterIncrement(assembler, R6); |
| 1601 #if defined(DEBUG) |
| 1602 { Label ok; |
| 1603 // Check that the IC data array has NumberOfArgumentsChecked() == 0. |
| 1604 // 'num_args_tested' is stored as an untagged int. |
| 1605 __ ldr(R6, FieldAddress(R5, ICData::num_args_tested_offset())); |
| 1606 __ CompareImmediate(R6, 0); |
| 1607 __ b(&ok, EQ); |
| 1608 __ Stop("Incorrect IC data for unoptimized static call"); |
| 1609 __ Bind(&ok); |
| 1610 } |
| 1611 #endif // DEBUG |
| 1612 |
| 1613 // R5: IC data object (preserved). |
| 1614 __ ldr(R6, FieldAddress(R5, ICData::ic_data_offset())); |
| 1615 // R6: ic_data_array with entries: target functions and count. |
| 1616 __ AddImmediate(R6, R6, Array::data_offset() - kHeapObjectTag); |
| 1617 // R6: points directly to the first ic data array element. |
| 1618 const intptr_t target_offset = ICData::TargetIndexFor(0) * kWordSize; |
| 1619 const intptr_t count_offset = ICData::CountIndexFor(0) * kWordSize; |
| 1620 |
| 1621 // Increment count for this call. |
| 1622 Label increment_done; |
| 1623 __ LoadFromOffset(kLoadWord, R1, R6, count_offset); |
| 1624 __ adds(R1, R1, ShifterOperand(Smi::RawValue(1))); |
| 1625 __ StoreToOffset(kStoreWord, R1, R6, count_offset); |
| 1626 __ b(&increment_done, VC); // No overflow. |
| 1627 __ LoadImmediate(R1, Smi::RawValue(Smi::kMaxValue)); |
| 1628 __ StoreToOffset(kStoreWord, R1, R6, count_offset); |
| 1629 __ Bind(&increment_done); |
| 1630 |
| 1631 Label target_is_compiled; |
| 1632 // Get function and call it, if possible. |
| 1633 __ LoadFromOffset(kLoadWord, R1, R6, target_offset); |
| 1634 __ ldr(R0, FieldAddress(R1, Function::code_offset())); |
| 1635 __ CompareImmediate(R0, reinterpret_cast<intptr_t>(Object::null())); |
| 1636 __ b(&target_is_compiled, NE); |
| 1637 // R1: function. |
| 1638 |
| 1639 __ EnterStubFrame(); |
| 1640 // Preserve target function and IC data object. |
| 1641 __ PushList((1 << R1) | (1 << R5)); |
| 1642 __ Push(R1); // Pass function. |
| 1643 __ CallRuntime(kCompileFunctionRuntimeEntry); |
| 1644 __ Drop(1); // Discard argument. |
| 1645 __ PopList((1 << R1) | (1 << R5)); // Restore function and IC data. |
| 1646 __ LeaveStubFrame(); |
| 1647 // R0: target function. |
| 1648 __ ldr(R0, FieldAddress(R1, Function::code_offset())); |
| 1649 |
| 1650 __ Bind(&target_is_compiled); |
| 1651 // R0: target code. |
| 1652 __ ldr(R0, FieldAddress(R0, Code::instructions_offset())); |
| 1653 __ AddImmediate(R0, Instructions::HeaderSize() - kHeapObjectTag); |
| 1654 // Load arguments descriptor into R4. |
| 1655 __ ldr(R4, FieldAddress(R5, ICData::arguments_descriptor_offset())); |
| 1656 __ bx(R0); |
| 1657 } |
| 1658 |
| 1659 |
| 1596 void StubCode::GenerateBreakpointRuntimeStub(Assembler* assembler) { | 1660 void StubCode::GenerateBreakpointRuntimeStub(Assembler* assembler) { |
| 1597 __ Unimplemented("BreakpointRuntime stub"); | 1661 __ Unimplemented("BreakpointRuntime stub"); |
| 1598 } | 1662 } |
| 1599 | 1663 |
| 1600 | 1664 |
| 1601 // LR: return address (Dart code). | 1665 // LR: return address (Dart code). |
| 1602 // R4: arguments descriptor array. | 1666 // R5: IC data (unoptimized static call). |
| 1603 void StubCode::GenerateBreakpointStaticStub(Assembler* assembler) { | 1667 void StubCode::GenerateBreakpointStaticStub(Assembler* assembler) { |
| 1604 // Create a stub frame as we are pushing some objects on the stack before | 1668 // Create a stub frame as we are pushing some objects on the stack before |
| 1605 // calling into the runtime. | 1669 // calling into the runtime. |
| 1606 __ EnterStubFrame(); | 1670 __ EnterStubFrame(); |
| 1607 __ LoadImmediate(R0, reinterpret_cast<intptr_t>(Object::null())); | 1671 __ LoadImmediate(R0, reinterpret_cast<intptr_t>(Object::null())); |
| 1608 // Preserve arguments descriptor and make room for result. | 1672 // Preserve arguments descriptor and make room for result. |
| 1609 __ PushList((1 << R0) | (1 << R4)); | 1673 __ PushList((1 << R0) | (1 << R5)); |
| 1610 __ CallRuntime(kBreakpointStaticHandlerRuntimeEntry); | 1674 __ CallRuntime(kBreakpointStaticHandlerRuntimeEntry); |
| 1611 // Pop code object result and restore arguments descriptor. | 1675 // Pop code object result and restore arguments descriptor. |
| 1612 __ PopList((1 << R0) | (1 << R4)); | 1676 __ PopList((1 << R0) | (1 << R5)); |
| 1613 __ LeaveStubFrame(); | 1677 __ LeaveStubFrame(); |
| 1614 | 1678 |
| 1615 // Now call the static function. The breakpoint handler function | 1679 // Now call the static function. The breakpoint handler function |
| 1616 // ensures that the call target is compiled. | 1680 // ensures that the call target is compiled. |
| 1617 __ ldr(R0, FieldAddress(R0, Code::instructions_offset())); | 1681 __ ldr(R0, FieldAddress(R0, Code::instructions_offset())); |
| 1618 __ AddImmediate(R0, Instructions::HeaderSize() - kHeapObjectTag); | 1682 __ AddImmediate(R0, Instructions::HeaderSize() - kHeapObjectTag); |
| 1683 // Load arguments descriptor into R4. |
| 1684 __ ldr(R4, FieldAddress(R5, ICData::arguments_descriptor_offset())); |
| 1619 __ bx(R0); | 1685 __ bx(R0); |
| 1620 } | 1686 } |
| 1621 | 1687 |
| 1622 | 1688 |
| 1623 // R0: return value. | 1689 // R0: return value. |
| 1624 void StubCode::GenerateBreakpointReturnStub(Assembler* assembler) { | 1690 void StubCode::GenerateBreakpointReturnStub(Assembler* assembler) { |
| 1625 // Create a stub frame as we are pushing some objects on the stack before | 1691 // Create a stub frame as we are pushing some objects on the stack before |
| 1626 // calling into the runtime. | 1692 // calling into the runtime. |
| 1627 __ EnterStubFrame(); | 1693 __ EnterStubFrame(); |
| 1628 __ Push(R0); | 1694 __ Push(R0); |
| (...skipping 351 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1980 __ Bind(&reference_compare); | 2046 __ Bind(&reference_compare); |
| 1981 __ cmp(left, ShifterOperand(right)); | 2047 __ cmp(left, ShifterOperand(right)); |
| 1982 __ Bind(&done); | 2048 __ Bind(&done); |
| 1983 __ PopList((1 << R0) | (1 << R1) | (1 << R2)); | 2049 __ PopList((1 << R0) | (1 << R1) | (1 << R2)); |
| 1984 __ Ret(); | 2050 __ Ret(); |
| 1985 } | 2051 } |
| 1986 | 2052 |
| 1987 } // namespace dart | 2053 } // namespace dart |
| 1988 | 2054 |
| 1989 #endif // defined TARGET_ARCH_ARM | 2055 #endif // defined TARGET_ARCH_ARM |
| OLD | NEW |