OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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 #include <assert.h> // For assert | 5 #include <assert.h> // For assert |
6 #include <limits.h> // For LONG_MIN, LONG_MAX. | 6 #include <limits.h> // For LONG_MIN, LONG_MAX. |
7 | 7 |
8 #if V8_TARGET_ARCH_PPC | 8 #if V8_TARGET_ARCH_PPC |
9 | 9 |
10 #include "src/base/bits.h" | 10 #include "src/base/bits.h" |
(...skipping 983 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
994 Move(dst, d1); | 994 Move(dst, d1); |
995 } | 995 } |
996 | 996 |
997 | 997 |
998 void MacroAssembler::MovFromFloatParameter(const DoubleRegister dst) { | 998 void MacroAssembler::MovFromFloatParameter(const DoubleRegister dst) { |
999 Move(dst, d1); | 999 Move(dst, d1); |
1000 } | 1000 } |
1001 | 1001 |
1002 | 1002 |
1003 void MacroAssembler::InvokePrologue(const ParameterCount& expected, | 1003 void MacroAssembler::InvokePrologue(const ParameterCount& expected, |
1004 const ParameterCount& actual, | 1004 const ParameterCount& actual, Label* done, |
1005 Handle<Code> code_constant, | |
1006 Register code_reg, Label* done, | |
1007 bool* definitely_mismatches, | 1005 bool* definitely_mismatches, |
1008 InvokeFlag flag, | 1006 InvokeFlag flag, |
1009 const CallWrapper& call_wrapper) { | 1007 const CallWrapper& call_wrapper) { |
1010 bool definitely_matches = false; | 1008 bool definitely_matches = false; |
1011 *definitely_mismatches = false; | 1009 *definitely_mismatches = false; |
1012 Label regular_invoke; | 1010 Label regular_invoke; |
1013 | 1011 |
1014 // Check whether the expected and actual arguments count match. If not, | 1012 // Check whether the expected and actual arguments count match. If not, |
1015 // setup registers according to contract with ArgumentsAdaptorTrampoline: | 1013 // setup registers according to contract with ArgumentsAdaptorTrampoline: |
1016 // r3: actual arguments count | 1014 // r3: actual arguments count |
1017 // r4: function (passed through to callee) | 1015 // r4: function (passed through to callee) |
1018 // r5: expected arguments count | 1016 // r5: expected arguments count |
1019 | 1017 |
1020 // The code below is made a lot easier because the calling code already sets | 1018 // The code below is made a lot easier because the calling code already sets |
1021 // up actual and expected registers according to the contract if values are | 1019 // up actual and expected registers according to the contract if values are |
1022 // passed in registers. | 1020 // passed in registers. |
1023 | 1021 |
1024 // ARM has some sanity checks as per below, considering add them for PPC | 1022 // ARM has some sanity checks as per below, considering add them for PPC |
1025 // DCHECK(actual.is_immediate() || actual.reg().is(r3)); | 1023 // DCHECK(actual.is_immediate() || actual.reg().is(r3)); |
1026 // DCHECK(expected.is_immediate() || expected.reg().is(r5)); | 1024 // DCHECK(expected.is_immediate() || expected.reg().is(r5)); |
1027 // DCHECK((!code_constant.is_null() && code_reg.is(no_reg)) | |
1028 // || code_reg.is(r6)); | |
1029 | 1025 |
1030 if (expected.is_immediate()) { | 1026 if (expected.is_immediate()) { |
1031 DCHECK(actual.is_immediate()); | 1027 DCHECK(actual.is_immediate()); |
1032 mov(r3, Operand(actual.immediate())); | 1028 mov(r3, Operand(actual.immediate())); |
1033 if (expected.immediate() == actual.immediate()) { | 1029 if (expected.immediate() == actual.immediate()) { |
1034 definitely_matches = true; | 1030 definitely_matches = true; |
1035 } else { | 1031 } else { |
1036 const int sentinel = SharedFunctionInfo::kDontAdaptArgumentsSentinel; | 1032 const int sentinel = SharedFunctionInfo::kDontAdaptArgumentsSentinel; |
1037 if (expected.immediate() == sentinel) { | 1033 if (expected.immediate() == sentinel) { |
1038 // Don't worry about adapting arguments for builtins that | 1034 // Don't worry about adapting arguments for builtins that |
(...skipping 11 matching lines...) Expand all Loading... |
1050 mov(r3, Operand(actual.immediate())); | 1046 mov(r3, Operand(actual.immediate())); |
1051 cmpi(expected.reg(), Operand(actual.immediate())); | 1047 cmpi(expected.reg(), Operand(actual.immediate())); |
1052 beq(®ular_invoke); | 1048 beq(®ular_invoke); |
1053 } else { | 1049 } else { |
1054 cmp(expected.reg(), actual.reg()); | 1050 cmp(expected.reg(), actual.reg()); |
1055 beq(®ular_invoke); | 1051 beq(®ular_invoke); |
1056 } | 1052 } |
1057 } | 1053 } |
1058 | 1054 |
1059 if (!definitely_matches) { | 1055 if (!definitely_matches) { |
1060 if (!code_constant.is_null()) { | |
1061 mov(r6, Operand(code_constant)); | |
1062 addi(r6, r6, Operand(Code::kHeaderSize - kHeapObjectTag)); | |
1063 } | |
1064 | |
1065 Handle<Code> adaptor = isolate()->builtins()->ArgumentsAdaptorTrampoline(); | 1056 Handle<Code> adaptor = isolate()->builtins()->ArgumentsAdaptorTrampoline(); |
1066 if (flag == CALL_FUNCTION) { | 1057 if (flag == CALL_FUNCTION) { |
1067 call_wrapper.BeforeCall(CallSize(adaptor)); | 1058 call_wrapper.BeforeCall(CallSize(adaptor)); |
1068 Call(adaptor); | 1059 Call(adaptor); |
1069 call_wrapper.AfterCall(); | 1060 call_wrapper.AfterCall(); |
1070 if (!*definitely_mismatches) { | 1061 if (!*definitely_mismatches) { |
1071 b(done); | 1062 b(done); |
1072 } | 1063 } |
1073 } else { | 1064 } else { |
1074 Jump(adaptor, RelocInfo::CODE_TARGET); | 1065 Jump(adaptor, RelocInfo::CODE_TARGET); |
1075 } | 1066 } |
1076 bind(®ular_invoke); | 1067 bind(®ular_invoke); |
1077 } | 1068 } |
1078 } | 1069 } |
1079 | 1070 |
1080 | 1071 |
1081 void MacroAssembler::InvokeCode(Register code, const ParameterCount& expected, | 1072 void MacroAssembler::InvokeCode(Register code, const ParameterCount& expected, |
1082 const ParameterCount& actual, InvokeFlag flag, | 1073 const ParameterCount& actual, InvokeFlag flag, |
1083 const CallWrapper& call_wrapper) { | 1074 const CallWrapper& call_wrapper) { |
1084 // You can't call a function without a valid frame. | 1075 // You can't call a function without a valid frame. |
1085 DCHECK(flag == JUMP_FUNCTION || has_frame()); | 1076 DCHECK(flag == JUMP_FUNCTION || has_frame()); |
1086 | 1077 |
1087 Label done; | 1078 Label done; |
1088 bool definitely_mismatches = false; | 1079 bool definitely_mismatches = false; |
1089 InvokePrologue(expected, actual, Handle<Code>::null(), code, &done, | 1080 InvokePrologue(expected, actual, &done, &definitely_mismatches, flag, |
1090 &definitely_mismatches, flag, call_wrapper); | 1081 call_wrapper); |
1091 if (!definitely_mismatches) { | 1082 if (!definitely_mismatches) { |
1092 if (flag == CALL_FUNCTION) { | 1083 if (flag == CALL_FUNCTION) { |
1093 call_wrapper.BeforeCall(CallSize(code)); | 1084 call_wrapper.BeforeCall(CallSize(code)); |
1094 CallJSEntry(code); | 1085 CallJSEntry(code); |
1095 call_wrapper.AfterCall(); | 1086 call_wrapper.AfterCall(); |
1096 } else { | 1087 } else { |
1097 DCHECK(flag == JUMP_FUNCTION); | 1088 DCHECK(flag == JUMP_FUNCTION); |
1098 JumpToJSEntry(code); | 1089 JumpToJSEntry(code); |
1099 } | 1090 } |
1100 | 1091 |
(...skipping 3320 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4421 } | 4412 } |
4422 if (mag.shift > 0) srawi(result, result, mag.shift); | 4413 if (mag.shift > 0) srawi(result, result, mag.shift); |
4423 ExtractBit(r0, dividend, 31); | 4414 ExtractBit(r0, dividend, 31); |
4424 add(result, result, r0); | 4415 add(result, result, r0); |
4425 } | 4416 } |
4426 | 4417 |
4427 } // namespace internal | 4418 } // namespace internal |
4428 } // namespace v8 | 4419 } // namespace v8 |
4429 | 4420 |
4430 #endif // V8_TARGET_ARCH_PPC | 4421 #endif // V8_TARGET_ARCH_PPC |
OLD | NEW |