OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #if V8_TARGET_ARCH_ARM64 | 5 #if V8_TARGET_ARCH_ARM64 |
6 | 6 |
7 #include "src/arm64/frames-arm64.h" | 7 #include "src/arm64/frames-arm64.h" |
8 #include "src/codegen.h" | 8 #include "src/codegen.h" |
9 #include "src/debug/debug.h" | 9 #include "src/debug/debug.h" |
10 #include "src/deoptimizer.h" | 10 #include "src/deoptimizer.h" |
(...skipping 945 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
956 | 956 |
957 void Builtins::Generate_JSEntryTrampoline(MacroAssembler* masm) { | 957 void Builtins::Generate_JSEntryTrampoline(MacroAssembler* masm) { |
958 Generate_JSEntryTrampolineHelper(masm, false); | 958 Generate_JSEntryTrampolineHelper(masm, false); |
959 } | 959 } |
960 | 960 |
961 | 961 |
962 void Builtins::Generate_JSConstructEntryTrampoline(MacroAssembler* masm) { | 962 void Builtins::Generate_JSConstructEntryTrampoline(MacroAssembler* masm) { |
963 Generate_JSEntryTrampolineHelper(masm, true); | 963 Generate_JSEntryTrampolineHelper(masm, true); |
964 } | 964 } |
965 | 965 |
| 966 |
966 // Generate code for entering a JS function with the interpreter. | 967 // Generate code for entering a JS function with the interpreter. |
967 // On entry to the function the receiver and arguments have been pushed on the | 968 // On entry to the function the receiver and arguments have been pushed on the |
968 // stack left to right. The actual argument count matches the formal parameter | 969 // stack left to right. The actual argument count matches the formal parameter |
969 // count expected by the function. | 970 // count expected by the function. |
970 // | 971 // |
971 // The live registers are: | 972 // The live registers are: |
972 // - x1: the JS function object being called. | 973 // - x1: the JS function object being called. |
973 // - x3: the new target | 974 // - x3: the new target |
974 // - cp: our context. | 975 // - cp: our context. |
975 // - fp: our caller's frame pointer. | 976 // - fp: our caller's frame pointer. |
(...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1054 __ Mov(kInterpreterDispatchTableRegister, | 1055 __ Mov(kInterpreterDispatchTableRegister, |
1055 Operand(ExternalReference::interpreter_dispatch_table_address( | 1056 Operand(ExternalReference::interpreter_dispatch_table_address( |
1056 masm->isolate()))); | 1057 masm->isolate()))); |
1057 | 1058 |
1058 // Dispatch to the first bytecode handler for the function. | 1059 // Dispatch to the first bytecode handler for the function. |
1059 __ Ldrb(x1, MemOperand(kInterpreterBytecodeArrayRegister, | 1060 __ Ldrb(x1, MemOperand(kInterpreterBytecodeArrayRegister, |
1060 kInterpreterBytecodeOffsetRegister)); | 1061 kInterpreterBytecodeOffsetRegister)); |
1061 __ Mov(x1, Operand(x1, LSL, kPointerSizeLog2)); | 1062 __ Mov(x1, Operand(x1, LSL, kPointerSizeLog2)); |
1062 __ Ldr(ip0, MemOperand(kInterpreterDispatchTableRegister, x1)); | 1063 __ Ldr(ip0, MemOperand(kInterpreterDispatchTableRegister, x1)); |
1063 __ Call(ip0); | 1064 __ Call(ip0); |
1064 masm->isolate()->heap()->SetInterpreterEntryReturnPCOffset(masm->pc_offset()); | |
1065 | 1065 |
1066 // The return value is in x0. | 1066 // Even though the first bytecode handler was called, we will never return. |
1067 | 1067 __ Abort(kUnexpectedReturnFromBytecodeHandler); |
1068 // Get the arguments + reciever count. | |
1069 __ ldr(x1, MemOperand(fp, InterpreterFrameConstants::kBytecodeArrayFromFp)); | |
1070 __ Ldr(w1, FieldMemOperand(x1, BytecodeArray::kParameterSizeOffset)); | |
1071 | |
1072 // Leave the frame (also dropping the register file). | |
1073 __ LeaveFrame(StackFrame::JAVA_SCRIPT); | |
1074 | |
1075 // Drop receiver + arguments and return. | |
1076 __ Drop(x1, 1); | |
1077 __ Ret(); | |
1078 | 1068 |
1079 // Load debug copy of the bytecode array. | 1069 // Load debug copy of the bytecode array. |
1080 __ Bind(&load_debug_bytecode_array); | 1070 __ Bind(&load_debug_bytecode_array); |
1081 __ Ldr(kInterpreterBytecodeArrayRegister, | 1071 __ Ldr(kInterpreterBytecodeArrayRegister, |
1082 FieldMemOperand(debug_info, DebugInfo::kAbstractCodeIndex)); | 1072 FieldMemOperand(debug_info, DebugInfo::kAbstractCodeIndex)); |
1083 __ B(&bytecode_array_loaded); | 1073 __ B(&bytecode_array_loaded); |
1084 | 1074 |
1085 // If the bytecode array is no longer present, then the underlying function | 1075 // If the bytecode array is no longer present, then the underlying function |
1086 // has been switched to a different kind of code and we heal the closure by | 1076 // has been switched to a different kind of code and we heal the closure by |
1087 // switching the code entry field over to the new code object as well. | 1077 // switching the code entry field over to the new code object as well. |
1088 __ Bind(&bytecode_array_not_present); | 1078 __ Bind(&bytecode_array_not_present); |
1089 __ LeaveFrame(StackFrame::JAVA_SCRIPT); | 1079 __ LeaveFrame(StackFrame::JAVA_SCRIPT); |
1090 __ Ldr(x7, FieldMemOperand(x1, JSFunction::kSharedFunctionInfoOffset)); | 1080 __ Ldr(x7, FieldMemOperand(x1, JSFunction::kSharedFunctionInfoOffset)); |
1091 __ Ldr(x7, FieldMemOperand(x7, SharedFunctionInfo::kCodeOffset)); | 1081 __ Ldr(x7, FieldMemOperand(x7, SharedFunctionInfo::kCodeOffset)); |
1092 __ Add(x7, x7, Operand(Code::kHeaderSize - kHeapObjectTag)); | 1082 __ Add(x7, x7, Operand(Code::kHeaderSize - kHeapObjectTag)); |
1093 __ Str(x7, FieldMemOperand(x1, JSFunction::kCodeEntryOffset)); | 1083 __ Str(x7, FieldMemOperand(x1, JSFunction::kCodeEntryOffset)); |
1094 __ RecordWriteCodeEntryField(x1, x7, x5); | 1084 __ RecordWriteCodeEntryField(x1, x7, x5); |
1095 __ Jump(x7); | 1085 __ Jump(x7); |
1096 } | 1086 } |
1097 | 1087 |
1098 // static | |
1099 void Builtins::Generate_InterpreterPushArgsAndCallImpl( | |
1100 MacroAssembler* masm, TailCallMode tail_call_mode) { | |
1101 // ----------- S t a t e ------------- | |
1102 // -- x0 : the number of arguments (not including the receiver) | |
1103 // -- x2 : the address of the first argument to be pushed. Subsequent | |
1104 // arguments should be consecutive above this, in the same order as | |
1105 // they are to be pushed onto the stack. | |
1106 // -- x1 : the target to call (can be any Object). | |
1107 // ----------------------------------- | |
1108 | 1088 |
1109 // Find the address of the last argument. | 1089 void Builtins::Generate_InterpreterExitTrampoline(MacroAssembler* masm) { |
1110 __ add(x3, x0, Operand(1)); // Add one for receiver. | 1090 // The return value is in accumulator, which is already in x0. |
1111 __ lsl(x3, x3, kPointerSizeLog2); | |
1112 __ sub(x4, x2, x3); | |
1113 | 1091 |
1114 // Push the arguments. | 1092 // Leave the frame (also dropping the register file). |
1115 Label loop_header, loop_check; | 1093 __ LeaveFrame(StackFrame::JAVA_SCRIPT); |
1116 __ Mov(x5, jssp); | |
1117 __ Claim(x3, 1); | |
1118 __ B(&loop_check); | |
1119 __ Bind(&loop_header); | |
1120 // TODO(rmcilroy): Push two at a time once we ensure we keep stack aligned. | |
1121 __ Ldr(x3, MemOperand(x2, -kPointerSize, PostIndex)); | |
1122 __ Str(x3, MemOperand(x5, -kPointerSize, PreIndex)); | |
1123 __ Bind(&loop_check); | |
1124 __ Cmp(x2, x4); | |
1125 __ B(gt, &loop_header); | |
1126 | 1094 |
1127 // Call the target. | 1095 // Drop receiver + arguments and return. |
1128 __ Jump(masm->isolate()->builtins()->Call(ConvertReceiverMode::kAny, | 1096 __ Ldr(w1, FieldMemOperand(kInterpreterBytecodeArrayRegister, |
1129 tail_call_mode), | 1097 BytecodeArray::kParameterSizeOffset)); |
1130 RelocInfo::CODE_TARGET); | 1098 __ Drop(x1, 1); |
| 1099 __ Ret(); |
1131 } | 1100 } |
1132 | 1101 |
1133 // static | |
1134 void Builtins::Generate_InterpreterPushArgsAndConstruct(MacroAssembler* masm) { | |
1135 // ----------- S t a t e ------------- | |
1136 // -- x0 : argument count (not including receiver) | |
1137 // -- x3 : new target | |
1138 // -- x1 : constructor to call | |
1139 // -- x2 : address of the first argument | |
1140 // ----------------------------------- | |
1141 | 1102 |
1142 // Find the address of the last argument. | 1103 static void Generate_EnterBytecodeDispatch(MacroAssembler* masm) { |
1143 __ add(x5, x0, Operand(1)); // Add one for receiver (to be constructed). | |
1144 __ lsl(x5, x5, kPointerSizeLog2); | |
1145 | |
1146 // Set stack pointer and where to stop. | |
1147 __ Mov(x6, jssp); | |
1148 __ Claim(x5, 1); | |
1149 __ sub(x4, x6, x5); | |
1150 | |
1151 // Push a slot for the receiver. | |
1152 __ Str(xzr, MemOperand(x6, -kPointerSize, PreIndex)); | |
1153 | |
1154 Label loop_header, loop_check; | |
1155 // Push the arguments. | |
1156 __ B(&loop_check); | |
1157 __ Bind(&loop_header); | |
1158 // TODO(rmcilroy): Push two at a time once we ensure we keep stack aligned. | |
1159 __ Ldr(x5, MemOperand(x2, -kPointerSize, PostIndex)); | |
1160 __ Str(x5, MemOperand(x6, -kPointerSize, PreIndex)); | |
1161 __ Bind(&loop_check); | |
1162 __ Cmp(x6, x4); | |
1163 __ B(gt, &loop_header); | |
1164 | |
1165 // Call the constructor with x0, x1, and x3 unmodified. | |
1166 __ Jump(masm->isolate()->builtins()->Construct(), RelocInfo::CODE_TARGET); | |
1167 } | |
1168 | |
1169 void Builtins::Generate_InterpreterEnterBytecodeDispatch(MacroAssembler* masm) { | |
1170 // Set the return address to the correct point in the interpreter entry | |
1171 // trampoline. | |
1172 Smi* interpreter_entry_return_pc_offset( | |
1173 masm->isolate()->heap()->interpreter_entry_return_pc_offset()); | |
1174 DCHECK_NE(interpreter_entry_return_pc_offset, Smi::FromInt(0)); | |
1175 __ LoadObject(x1, masm->isolate()->builtins()->InterpreterEntryTrampoline()); | |
1176 __ Add(lr, x1, Operand(interpreter_entry_return_pc_offset->value() + | |
1177 Code::kHeaderSize - kHeapObjectTag)); | |
1178 | |
1179 // Initialize the dispatch table register. | 1104 // Initialize the dispatch table register. |
1180 __ Mov(kInterpreterDispatchTableRegister, | 1105 __ Mov(kInterpreterDispatchTableRegister, |
1181 Operand(ExternalReference::interpreter_dispatch_table_address( | 1106 Operand(ExternalReference::interpreter_dispatch_table_address( |
1182 masm->isolate()))); | 1107 masm->isolate()))); |
1183 | 1108 |
1184 // Get the bytecode array pointer from the frame. | 1109 // Get the bytecode array pointer from the frame. |
1185 __ Ldr(kInterpreterBytecodeArrayRegister, | 1110 __ Ldr(kInterpreterBytecodeArrayRegister, |
1186 MemOperand(fp, InterpreterFrameConstants::kBytecodeArrayFromFp)); | 1111 MemOperand(fp, InterpreterFrameConstants::kBytecodeArrayFromFp)); |
1187 | 1112 |
1188 if (FLAG_debug_code) { | 1113 if (FLAG_debug_code) { |
(...skipping 11 matching lines...) Expand all Loading... |
1200 __ SmiUntag(kInterpreterBytecodeOffsetRegister); | 1125 __ SmiUntag(kInterpreterBytecodeOffsetRegister); |
1201 | 1126 |
1202 // Dispatch to the target bytecode. | 1127 // Dispatch to the target bytecode. |
1203 __ Ldrb(x1, MemOperand(kInterpreterBytecodeArrayRegister, | 1128 __ Ldrb(x1, MemOperand(kInterpreterBytecodeArrayRegister, |
1204 kInterpreterBytecodeOffsetRegister)); | 1129 kInterpreterBytecodeOffsetRegister)); |
1205 __ Mov(x1, Operand(x1, LSL, kPointerSizeLog2)); | 1130 __ Mov(x1, Operand(x1, LSL, kPointerSizeLog2)); |
1206 __ Ldr(ip0, MemOperand(kInterpreterDispatchTableRegister, x1)); | 1131 __ Ldr(ip0, MemOperand(kInterpreterDispatchTableRegister, x1)); |
1207 __ Jump(ip0); | 1132 __ Jump(ip0); |
1208 } | 1133 } |
1209 | 1134 |
| 1135 |
| 1136 static void Generate_InterpreterNotifyDeoptimizedHelper( |
| 1137 MacroAssembler* masm, Deoptimizer::BailoutType type) { |
| 1138 // Enter an internal frame. |
| 1139 { |
| 1140 FrameScope scope(masm, StackFrame::INTERNAL); |
| 1141 |
| 1142 // Pass the deoptimization type to the runtime system. |
| 1143 __ Mov(x1, Operand(Smi::FromInt(static_cast<int>(type)))); |
| 1144 __ Push(x1); |
| 1145 __ CallRuntime(Runtime::kNotifyDeoptimized); |
| 1146 // Tear down internal frame. |
| 1147 } |
| 1148 |
| 1149 // Drop state (we don't use these for interpreter deopts) and and pop the |
| 1150 // accumulator value into the accumulator register. |
| 1151 __ Drop(1); |
| 1152 __ Pop(kInterpreterAccumulatorRegister); |
| 1153 |
| 1154 // Enter the bytecode dispatch. |
| 1155 Generate_EnterBytecodeDispatch(masm); |
| 1156 } |
| 1157 |
| 1158 |
| 1159 void Builtins::Generate_InterpreterNotifyDeoptimized(MacroAssembler* masm) { |
| 1160 Generate_InterpreterNotifyDeoptimizedHelper(masm, Deoptimizer::EAGER); |
| 1161 } |
| 1162 |
| 1163 |
| 1164 void Builtins::Generate_InterpreterNotifySoftDeoptimized(MacroAssembler* masm) { |
| 1165 Generate_InterpreterNotifyDeoptimizedHelper(masm, Deoptimizer::SOFT); |
| 1166 } |
| 1167 |
| 1168 |
| 1169 void Builtins::Generate_InterpreterNotifyLazyDeoptimized(MacroAssembler* masm) { |
| 1170 Generate_InterpreterNotifyDeoptimizedHelper(masm, Deoptimizer::LAZY); |
| 1171 } |
| 1172 |
| 1173 void Builtins::Generate_InterpreterEnterBytecodeDispatch(MacroAssembler* masm) { |
| 1174 // Set the address of the interpreter entry trampoline as a return address. |
| 1175 // This simulates the initial call to bytecode handlers in interpreter entry |
| 1176 // trampoline. The return will never actually be taken, but our stack walker |
| 1177 // uses this address to determine whether a frame is interpreted. |
| 1178 __ LoadObject(lr, masm->isolate()->builtins()->InterpreterEntryTrampoline()); |
| 1179 |
| 1180 Generate_EnterBytecodeDispatch(masm); |
| 1181 } |
| 1182 |
| 1183 |
1210 void Builtins::Generate_CompileLazy(MacroAssembler* masm) { | 1184 void Builtins::Generate_CompileLazy(MacroAssembler* masm) { |
1211 // ----------- S t a t e ------------- | 1185 // ----------- S t a t e ------------- |
1212 // -- x0 : argument count (preserved for callee) | 1186 // -- x0 : argument count (preserved for callee) |
1213 // -- x3 : new target (preserved for callee) | 1187 // -- x3 : new target (preserved for callee) |
1214 // -- x1 : target function (preserved for callee) | 1188 // -- x1 : target function (preserved for callee) |
1215 // ----------------------------------- | 1189 // ----------------------------------- |
1216 // First lookup code, maybe we don't need to compile! | 1190 // First lookup code, maybe we don't need to compile! |
1217 Label gotta_call_runtime; | 1191 Label gotta_call_runtime; |
1218 Label maybe_call_runtime; | 1192 Label maybe_call_runtime; |
1219 Label try_shared; | 1193 Label try_shared; |
(...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1488 __ CallRuntime(Runtime::kNotifyDeoptimized); | 1462 __ CallRuntime(Runtime::kNotifyDeoptimized); |
1489 } | 1463 } |
1490 | 1464 |
1491 // Get the full codegen state from the stack and untag it. | 1465 // Get the full codegen state from the stack and untag it. |
1492 Register state = x6; | 1466 Register state = x6; |
1493 __ Peek(state, 0); | 1467 __ Peek(state, 0); |
1494 __ SmiUntag(state); | 1468 __ SmiUntag(state); |
1495 | 1469 |
1496 // Switch on the state. | 1470 // Switch on the state. |
1497 Label with_tos_register, unknown_state; | 1471 Label with_tos_register, unknown_state; |
1498 __ CompareAndBranch(state, | 1472 __ CompareAndBranch( |
1499 static_cast<int>(Deoptimizer::BailoutState::NO_REGISTERS), | 1473 state, FullCodeGenerator::NO_REGISTERS, ne, &with_tos_register); |
1500 ne, &with_tos_register); | |
1501 __ Drop(1); // Remove state. | 1474 __ Drop(1); // Remove state. |
1502 __ Ret(); | 1475 __ Ret(); |
1503 | 1476 |
1504 __ Bind(&with_tos_register); | 1477 __ Bind(&with_tos_register); |
1505 // Reload TOS register. | 1478 // Reload TOS register. |
1506 DCHECK_EQ(kInterpreterAccumulatorRegister.code(), x0.code()); | |
1507 __ Peek(x0, kPointerSize); | 1479 __ Peek(x0, kPointerSize); |
1508 __ CompareAndBranch(state, | 1480 __ CompareAndBranch(state, FullCodeGenerator::TOS_REG, ne, &unknown_state); |
1509 static_cast<int>(Deoptimizer::BailoutState::TOS_REGISTER), | |
1510 ne, &unknown_state); | |
1511 __ Drop(2); // Remove state and TOS. | 1481 __ Drop(2); // Remove state and TOS. |
1512 __ Ret(); | 1482 __ Ret(); |
1513 | 1483 |
1514 __ Bind(&unknown_state); | 1484 __ Bind(&unknown_state); |
1515 __ Abort(kInvalidFullCodegenState); | 1485 __ Abort(kInvalidFullCodegenState); |
1516 } | 1486 } |
1517 | 1487 |
1518 | 1488 |
1519 void Builtins::Generate_NotifyDeoptimized(MacroAssembler* masm) { | 1489 void Builtins::Generate_NotifyDeoptimized(MacroAssembler* masm) { |
1520 Generate_NotifyDeoptimizedHelper(masm, Deoptimizer::EAGER); | 1490 Generate_NotifyDeoptimizedHelper(masm, Deoptimizer::EAGER); |
(...skipping 1180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2701 RelocInfo::CODE_TARGET); | 2671 RelocInfo::CODE_TARGET); |
2702 } | 2672 } |
2703 | 2673 |
2704 // Called Construct on an Object that doesn't have a [[Construct]] internal | 2674 // Called Construct on an Object that doesn't have a [[Construct]] internal |
2705 // method. | 2675 // method. |
2706 __ bind(&non_constructor); | 2676 __ bind(&non_constructor); |
2707 __ Jump(masm->isolate()->builtins()->ConstructedNonConstructable(), | 2677 __ Jump(masm->isolate()->builtins()->ConstructedNonConstructable(), |
2708 RelocInfo::CODE_TARGET); | 2678 RelocInfo::CODE_TARGET); |
2709 } | 2679 } |
2710 | 2680 |
| 2681 |
| 2682 // static |
| 2683 void Builtins::Generate_InterpreterPushArgsAndCallImpl( |
| 2684 MacroAssembler* masm, TailCallMode tail_call_mode) { |
| 2685 // ----------- S t a t e ------------- |
| 2686 // -- x0 : the number of arguments (not including the receiver) |
| 2687 // -- x2 : the address of the first argument to be pushed. Subsequent |
| 2688 // arguments should be consecutive above this, in the same order as |
| 2689 // they are to be pushed onto the stack. |
| 2690 // -- x1 : the target to call (can be any Object). |
| 2691 // ----------------------------------- |
| 2692 |
| 2693 // Find the address of the last argument. |
| 2694 __ add(x3, x0, Operand(1)); // Add one for receiver. |
| 2695 __ lsl(x3, x3, kPointerSizeLog2); |
| 2696 __ sub(x4, x2, x3); |
| 2697 |
| 2698 // Push the arguments. |
| 2699 Label loop_header, loop_check; |
| 2700 __ Mov(x5, jssp); |
| 2701 __ Claim(x3, 1); |
| 2702 __ B(&loop_check); |
| 2703 __ Bind(&loop_header); |
| 2704 // TODO(rmcilroy): Push two at a time once we ensure we keep stack aligned. |
| 2705 __ Ldr(x3, MemOperand(x2, -kPointerSize, PostIndex)); |
| 2706 __ Str(x3, MemOperand(x5, -kPointerSize, PreIndex)); |
| 2707 __ Bind(&loop_check); |
| 2708 __ Cmp(x2, x4); |
| 2709 __ B(gt, &loop_header); |
| 2710 |
| 2711 // Call the target. |
| 2712 __ Jump(masm->isolate()->builtins()->Call(ConvertReceiverMode::kAny, |
| 2713 tail_call_mode), |
| 2714 RelocInfo::CODE_TARGET); |
| 2715 } |
| 2716 |
| 2717 |
| 2718 // static |
| 2719 void Builtins::Generate_InterpreterPushArgsAndConstruct(MacroAssembler* masm) { |
| 2720 // ----------- S t a t e ------------- |
| 2721 // -- x0 : argument count (not including receiver) |
| 2722 // -- x3 : new target |
| 2723 // -- x1 : constructor to call |
| 2724 // -- x2 : address of the first argument |
| 2725 // ----------------------------------- |
| 2726 |
| 2727 // Find the address of the last argument. |
| 2728 __ add(x5, x0, Operand(1)); // Add one for receiver (to be constructed). |
| 2729 __ lsl(x5, x5, kPointerSizeLog2); |
| 2730 |
| 2731 // Set stack pointer and where to stop. |
| 2732 __ Mov(x6, jssp); |
| 2733 __ Claim(x5, 1); |
| 2734 __ sub(x4, x6, x5); |
| 2735 |
| 2736 // Push a slot for the receiver. |
| 2737 __ Str(xzr, MemOperand(x6, -kPointerSize, PreIndex)); |
| 2738 |
| 2739 Label loop_header, loop_check; |
| 2740 // Push the arguments. |
| 2741 __ B(&loop_check); |
| 2742 __ Bind(&loop_header); |
| 2743 // TODO(rmcilroy): Push two at a time once we ensure we keep stack aligned. |
| 2744 __ Ldr(x5, MemOperand(x2, -kPointerSize, PostIndex)); |
| 2745 __ Str(x5, MemOperand(x6, -kPointerSize, PreIndex)); |
| 2746 __ Bind(&loop_check); |
| 2747 __ Cmp(x6, x4); |
| 2748 __ B(gt, &loop_header); |
| 2749 |
| 2750 // Call the constructor with x0, x1, and x3 unmodified. |
| 2751 __ Jump(masm->isolate()->builtins()->Construct(), RelocInfo::CODE_TARGET); |
| 2752 } |
| 2753 |
2711 // static | 2754 // static |
2712 void Builtins::Generate_AllocateInNewSpace(MacroAssembler* masm) { | 2755 void Builtins::Generate_AllocateInNewSpace(MacroAssembler* masm) { |
2713 ASM_LOCATION("Builtins::Generate_AllocateInNewSpace"); | 2756 ASM_LOCATION("Builtins::Generate_AllocateInNewSpace"); |
2714 // ----------- S t a t e ------------- | 2757 // ----------- S t a t e ------------- |
2715 // -- x1 : requested object size (untagged) | 2758 // -- x1 : requested object size (untagged) |
2716 // -- lr : return address | 2759 // -- lr : return address |
2717 // ----------------------------------- | 2760 // ----------------------------------- |
2718 __ SmiTag(x1); | 2761 __ SmiTag(x1); |
2719 __ Push(x1); | 2762 __ Push(x1); |
2720 __ Move(cp, Smi::FromInt(0)); | 2763 __ Move(cp, Smi::FromInt(0)); |
(...skipping 159 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2880 } | 2923 } |
2881 } | 2924 } |
2882 | 2925 |
2883 | 2926 |
2884 #undef __ | 2927 #undef __ |
2885 | 2928 |
2886 } // namespace internal | 2929 } // namespace internal |
2887 } // namespace v8 | 2930 } // namespace v8 |
2888 | 2931 |
2889 #endif // V8_TARGET_ARCH_ARM | 2932 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |