OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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_ARM | 5 #if V8_TARGET_ARCH_ARM |
6 | 6 |
7 #include "src/codegen.h" | 7 #include "src/codegen.h" |
8 #include "src/debug/debug.h" | 8 #include "src/debug/debug.h" |
9 #include "src/deoptimizer.h" | 9 #include "src/deoptimizer.h" |
10 #include "src/full-codegen/full-codegen.h" | 10 #include "src/full-codegen/full-codegen.h" |
(...skipping 941 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
952 | 952 |
953 void Builtins::Generate_JSEntryTrampoline(MacroAssembler* masm) { | 953 void Builtins::Generate_JSEntryTrampoline(MacroAssembler* masm) { |
954 Generate_JSEntryTrampolineHelper(masm, false); | 954 Generate_JSEntryTrampolineHelper(masm, false); |
955 } | 955 } |
956 | 956 |
957 | 957 |
958 void Builtins::Generate_JSConstructEntryTrampoline(MacroAssembler* masm) { | 958 void Builtins::Generate_JSConstructEntryTrampoline(MacroAssembler* masm) { |
959 Generate_JSEntryTrampolineHelper(masm, true); | 959 Generate_JSEntryTrampolineHelper(masm, true); |
960 } | 960 } |
961 | 961 |
| 962 static void LeaveInterpreterFrame(MacroAssembler* masm, Register scratch) { |
| 963 Register args_count = scratch; |
| 964 |
| 965 // Get the arguments + receiver count. |
| 966 __ ldr(args_count, |
| 967 MemOperand(fp, InterpreterFrameConstants::kBytecodeArrayFromFp)); |
| 968 __ ldr(args_count, |
| 969 FieldMemOperand(args_count, BytecodeArray::kParameterSizeOffset)); |
| 970 |
| 971 // Leave the frame (also dropping the register file). |
| 972 __ LeaveFrame(StackFrame::JAVA_SCRIPT); |
| 973 |
| 974 // Drop receiver + arguments. |
| 975 __ add(sp, sp, args_count, LeaveCC); |
| 976 } |
| 977 |
962 // Generate code for entering a JS function with the interpreter. | 978 // Generate code for entering a JS function with the interpreter. |
963 // On entry to the function the receiver and arguments have been pushed on the | 979 // On entry to the function the receiver and arguments have been pushed on the |
964 // stack left to right. The actual argument count matches the formal parameter | 980 // stack left to right. The actual argument count matches the formal parameter |
965 // count expected by the function. | 981 // count expected by the function. |
966 // | 982 // |
967 // The live registers are: | 983 // The live registers are: |
968 // o r1: the JS function object being called. | 984 // o r1: the JS function object being called. |
969 // o r3: the new target | 985 // o r3: the new target |
970 // o cp: our context | 986 // o cp: our context |
971 // o pp: the caller's constant pool pointer (if enabled) | 987 // o pp: the caller's constant pool pointer (if enabled) |
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1055 | 1071 |
1056 // Dispatch to the first bytecode handler for the function. | 1072 // Dispatch to the first bytecode handler for the function. |
1057 __ ldrb(r1, MemOperand(kInterpreterBytecodeArrayRegister, | 1073 __ ldrb(r1, MemOperand(kInterpreterBytecodeArrayRegister, |
1058 kInterpreterBytecodeOffsetRegister)); | 1074 kInterpreterBytecodeOffsetRegister)); |
1059 __ ldr(ip, MemOperand(kInterpreterDispatchTableRegister, r1, LSL, | 1075 __ ldr(ip, MemOperand(kInterpreterDispatchTableRegister, r1, LSL, |
1060 kPointerSizeLog2)); | 1076 kPointerSizeLog2)); |
1061 __ Call(ip); | 1077 __ Call(ip); |
1062 masm->isolate()->heap()->SetInterpreterEntryReturnPCOffset(masm->pc_offset()); | 1078 masm->isolate()->heap()->SetInterpreterEntryReturnPCOffset(masm->pc_offset()); |
1063 | 1079 |
1064 // The return value is in r0. | 1080 // The return value is in r0. |
1065 | 1081 LeaveInterpreterFrame(masm, r2); |
1066 // Get the arguments + reciever count. | |
1067 __ ldr(r2, MemOperand(fp, InterpreterFrameConstants::kBytecodeArrayFromFp)); | |
1068 __ ldr(r2, FieldMemOperand(r2, BytecodeArray::kParameterSizeOffset)); | |
1069 | |
1070 // Leave the frame (also dropping the register file). | |
1071 __ LeaveFrame(StackFrame::JAVA_SCRIPT); | |
1072 | |
1073 __ add(sp, sp, r2, LeaveCC); | |
1074 __ Jump(lr); | 1082 __ Jump(lr); |
1075 | 1083 |
1076 // If the bytecode array is no longer present, then the underlying function | 1084 // If the bytecode array is no longer present, then the underlying function |
1077 // has been switched to a different kind of code and we heal the closure by | 1085 // has been switched to a different kind of code and we heal the closure by |
1078 // switching the code entry field over to the new code object as well. | 1086 // switching the code entry field over to the new code object as well. |
1079 __ bind(&bytecode_array_not_present); | 1087 __ bind(&bytecode_array_not_present); |
1080 __ LeaveFrame(StackFrame::JAVA_SCRIPT); | 1088 __ LeaveFrame(StackFrame::JAVA_SCRIPT); |
1081 __ ldr(r4, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); | 1089 __ ldr(r4, FieldMemOperand(r1, JSFunction::kSharedFunctionInfoOffset)); |
1082 __ ldr(r4, FieldMemOperand(r4, SharedFunctionInfo::kCodeOffset)); | 1090 __ ldr(r4, FieldMemOperand(r4, SharedFunctionInfo::kCodeOffset)); |
1083 __ add(r4, r4, Operand(Code::kHeaderSize - kHeapObjectTag)); | 1091 __ add(r4, r4, Operand(Code::kHeaderSize - kHeapObjectTag)); |
1084 __ str(r4, FieldMemOperand(r1, JSFunction::kCodeEntryOffset)); | 1092 __ str(r4, FieldMemOperand(r1, JSFunction::kCodeEntryOffset)); |
1085 __ RecordWriteCodeEntryField(r1, r4, r5); | 1093 __ RecordWriteCodeEntryField(r1, r4, r5); |
1086 __ Jump(r4); | 1094 __ Jump(r4); |
1087 } | 1095 } |
1088 | 1096 |
| 1097 void Builtins::Generate_InterpreterMarkBaselineOnReturn(MacroAssembler* masm) { |
| 1098 // Save the function and context for call to CompileBaseline. |
| 1099 __ ldr(r1, MemOperand(fp, StandardFrameConstants::kFunctionOffset)); |
| 1100 __ ldr(kContextRegister, |
| 1101 MemOperand(fp, StandardFrameConstants::kContextOffset)); |
| 1102 |
| 1103 // Leave the frame before recompiling for baseline so that we don't count as |
| 1104 // an activation on the stack. |
| 1105 LeaveInterpreterFrame(masm, r2); |
| 1106 |
| 1107 { |
| 1108 FrameScope frame_scope(masm, StackFrame::INTERNAL); |
| 1109 // Push return value. |
| 1110 __ push(r0); |
| 1111 |
| 1112 // Push function as argument and compile for baseline. |
| 1113 __ push(r1); |
| 1114 __ CallRuntime(Runtime::kCompileBaseline); |
| 1115 |
| 1116 // Restore return value. |
| 1117 __ pop(r0); |
| 1118 } |
| 1119 __ Jump(lr); |
| 1120 } |
| 1121 |
1089 static void Generate_InterpreterPushArgs(MacroAssembler* masm, Register index, | 1122 static void Generate_InterpreterPushArgs(MacroAssembler* masm, Register index, |
1090 Register limit, Register scratch) { | 1123 Register limit, Register scratch) { |
1091 Label loop_header, loop_check; | 1124 Label loop_header, loop_check; |
1092 __ b(al, &loop_check); | 1125 __ b(al, &loop_check); |
1093 __ bind(&loop_header); | 1126 __ bind(&loop_header); |
1094 __ ldr(scratch, MemOperand(index, -kPointerSize, PostIndex)); | 1127 __ ldr(scratch, MemOperand(index, -kPointerSize, PostIndex)); |
1095 __ push(scratch); | 1128 __ push(scratch); |
1096 __ bind(&loop_check); | 1129 __ bind(&loop_check); |
1097 __ cmp(index, limit); | 1130 __ cmp(index, limit); |
1098 __ b(gt, &loop_header); | 1131 __ b(gt, &loop_header); |
(...skipping 1643 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2742 } | 2775 } |
2743 } | 2776 } |
2744 | 2777 |
2745 | 2778 |
2746 #undef __ | 2779 #undef __ |
2747 | 2780 |
2748 } // namespace internal | 2781 } // namespace internal |
2749 } // namespace v8 | 2782 } // namespace v8 |
2750 | 2783 |
2751 #endif // V8_TARGET_ARCH_ARM | 2784 #endif // V8_TARGET_ARCH_ARM |
OLD | NEW |