[asm] Add StackArgumentsAccessor to ia32
This add StackArgumentsAccessor class to ia32, which slighty increases abstraction when accessing arguments in the stack. Bug: v8:10201 Change-Id: I4ee0323022d9334cb0b2af63a9c1f437eed9a079 Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/2073762 Reviewed-by: Toon Verwaest <verwaest@chromium.org> Reviewed-by: Leszek Swirski <leszeks@chromium.org> Commit-Queue: Victor Gomes <victorgomes@chromium.org> Auto-Submit: Victor Gomes <victorgomes@chromium.org> Cr-Commit-Position: refs/heads/master@{#66518}
This commit is contained in:
parent
5f5bcace28
commit
7750311321
@ -1599,9 +1599,10 @@ void Builtins::Generate_FunctionPrototypeApply(MacroAssembler* masm) {
|
||||
// ----------- S t a t e -------------
|
||||
// -- eax : argc
|
||||
// -- esp[0] : return address
|
||||
// -- esp[4] : argArray
|
||||
// -- esp[8] : thisArg
|
||||
// -- esp[12] : receiver
|
||||
// The order of args depends on V8_REVERSE_JSARGS
|
||||
// -- args[0] : receiver
|
||||
// -- args[1] : thisArg
|
||||
// -- args[2] : argArray
|
||||
// -----------------------------------
|
||||
|
||||
// 1. Load receiver into xmm0, argArray into edx (if present), remove all
|
||||
@ -1609,20 +1610,19 @@ void Builtins::Generate_FunctionPrototypeApply(MacroAssembler* masm) {
|
||||
// present) instead.
|
||||
{
|
||||
Label no_arg_array, no_this_arg;
|
||||
StackArgumentsAccessor args(eax);
|
||||
// Spill receiver to allow the usage of edi as a scratch register.
|
||||
__ movd(xmm0,
|
||||
Operand(esp, eax, times_system_pointer_size, kSystemPointerSize));
|
||||
__ movd(xmm0, args[0]);
|
||||
|
||||
__ LoadRoot(edx, RootIndex::kUndefinedValue);
|
||||
__ mov(edi, edx);
|
||||
__ test(eax, eax);
|
||||
__ j(zero, &no_this_arg, Label::kNear);
|
||||
{
|
||||
__ mov(edi, Operand(esp, eax, times_system_pointer_size, 0));
|
||||
__ mov(edi, args[1]);
|
||||
__ cmp(eax, Immediate(1));
|
||||
__ j(equal, &no_arg_array, Label::kNear);
|
||||
__ mov(edx,
|
||||
Operand(esp, eax, times_system_pointer_size, -kSystemPointerSize));
|
||||
__ mov(edx, args[2]);
|
||||
__ bind(&no_arg_array);
|
||||
}
|
||||
__ bind(&no_this_arg);
|
||||
@ -1690,7 +1690,10 @@ void Builtins::Generate_FunctionPrototypeCall(MacroAssembler* masm) {
|
||||
}
|
||||
|
||||
// 2. Get the callable to call (passed as receiver) from the stack.
|
||||
__ mov(edi, Operand(esp, eax, times_system_pointer_size, kSystemPointerSize));
|
||||
{
|
||||
StackArgumentsAccessor args(eax);
|
||||
__ mov(edi, args.GetReceiverOperand());
|
||||
}
|
||||
|
||||
// 3. Shift arguments and return address one slot down on the stack
|
||||
// (overwriting the original receiver). Adjust argument count to make
|
||||
@ -1716,10 +1719,11 @@ void Builtins::Generate_ReflectApply(MacroAssembler* masm) {
|
||||
// ----------- S t a t e -------------
|
||||
// -- eax : argc
|
||||
// -- esp[0] : return address
|
||||
// -- esp[4] : argumentsList
|
||||
// -- esp[8] : thisArgument
|
||||
// -- esp[12] : target
|
||||
// -- esp[16] : receiver
|
||||
// The order of args depends on V8_REVERSE_JSARGS
|
||||
// -- args[0] : receiver
|
||||
// -- args[1] : target
|
||||
// -- args[2] : thisArgument
|
||||
// -- args[3] : argumentsList
|
||||
// -----------------------------------
|
||||
|
||||
// 1. Load target into edi (if present), argumentsList into edx (if present),
|
||||
@ -1727,20 +1731,18 @@ void Builtins::Generate_ReflectApply(MacroAssembler* masm) {
|
||||
// thisArgument (if present) instead.
|
||||
{
|
||||
Label done;
|
||||
StackArgumentsAccessor args(eax);
|
||||
__ LoadRoot(edi, RootIndex::kUndefinedValue);
|
||||
__ mov(edx, edi);
|
||||
__ mov(ecx, edi);
|
||||
__ cmp(eax, Immediate(1));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ mov(edi, Operand(esp, eax, times_system_pointer_size,
|
||||
-0 * kSystemPointerSize));
|
||||
__ mov(edi, args[1]); // target
|
||||
__ j(equal, &done, Label::kNear);
|
||||
__ mov(ecx, Operand(esp, eax, times_system_pointer_size,
|
||||
-1 * kSystemPointerSize));
|
||||
__ mov(ecx, args[2]); // thisArgument
|
||||
__ cmp(eax, Immediate(3));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ mov(edx, Operand(esp, eax, times_system_pointer_size,
|
||||
-2 * kSystemPointerSize));
|
||||
__ mov(edx, args[3]); // argumentsList
|
||||
__ bind(&done);
|
||||
|
||||
// Spill argumentsList to use edx as a scratch register.
|
||||
@ -1776,10 +1778,11 @@ void Builtins::Generate_ReflectConstruct(MacroAssembler* masm) {
|
||||
// ----------- S t a t e -------------
|
||||
// -- eax : argc
|
||||
// -- esp[0] : return address
|
||||
// -- esp[4] : new.target (optional)
|
||||
// -- esp[8] : argumentsList
|
||||
// -- esp[12] : target
|
||||
// -- esp[16] : receiver
|
||||
// The order of args depends on V8_REVERSE_JSARGS
|
||||
// -- args[0] : receiver
|
||||
// -- args[1] : target
|
||||
// -- args[2] : argumentsList
|
||||
// -- args[3] : new.target (optional)
|
||||
// -----------------------------------
|
||||
|
||||
// 1. Load target into edi (if present), argumentsList into ecx (if present),
|
||||
@ -1788,21 +1791,19 @@ void Builtins::Generate_ReflectConstruct(MacroAssembler* masm) {
|
||||
// (if present) instead.
|
||||
{
|
||||
Label done;
|
||||
StackArgumentsAccessor args(eax);
|
||||
__ LoadRoot(edi, RootIndex::kUndefinedValue);
|
||||
__ mov(edx, edi);
|
||||
__ mov(ecx, edi);
|
||||
__ cmp(eax, Immediate(1));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ mov(edi, Operand(esp, eax, times_system_pointer_size,
|
||||
-0 * kSystemPointerSize));
|
||||
__ mov(edi, args[1]); // target
|
||||
__ mov(edx, edi);
|
||||
__ j(equal, &done, Label::kNear);
|
||||
__ mov(ecx, Operand(esp, eax, times_system_pointer_size,
|
||||
-1 * kSystemPointerSize));
|
||||
__ mov(ecx, args[2]); // argumentsList
|
||||
__ cmp(eax, Immediate(3));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ mov(edx, Operand(esp, eax, times_system_pointer_size,
|
||||
-2 * kSystemPointerSize));
|
||||
__ mov(edx, args[3]); // new.target
|
||||
__ bind(&done);
|
||||
|
||||
// Spill argumentsList to use ecx as a scratch register.
|
||||
@ -2064,6 +2065,7 @@ void Builtins::Generate_CallFunction(MacroAssembler* masm,
|
||||
// -- eax : the number of arguments (not including the receiver)
|
||||
// -- edi : the function to call (checked to be a JSFunction)
|
||||
// -----------------------------------
|
||||
StackArgumentsAccessor args(eax);
|
||||
__ AssertFunction(edi);
|
||||
|
||||
// See ES6 section 9.2.1 [[Call]] ( thisArgument, argumentsList)
|
||||
@ -2097,15 +2099,13 @@ void Builtins::Generate_CallFunction(MacroAssembler* masm,
|
||||
__ LoadGlobalProxy(ecx);
|
||||
} else {
|
||||
Label convert_to_object, convert_receiver;
|
||||
__ mov(ecx,
|
||||
Operand(esp, eax, times_system_pointer_size, kSystemPointerSize));
|
||||
__ mov(ecx, args.GetReceiverOperand());
|
||||
__ JumpIfSmi(ecx, &convert_to_object, Label::kNear);
|
||||
STATIC_ASSERT(LAST_JS_RECEIVER_TYPE == LAST_TYPE);
|
||||
__ CmpObjectType(ecx, FIRST_JS_RECEIVER_TYPE, ecx); // Clobbers ecx.
|
||||
__ j(above_equal, &done_convert);
|
||||
// Reload the receiver (it was clobbered by CmpObjectType).
|
||||
__ mov(ecx,
|
||||
Operand(esp, eax, times_system_pointer_size, kSystemPointerSize));
|
||||
__ mov(ecx, args.GetReceiverOperand());
|
||||
if (mode != ConvertReceiverMode::kNotNullOrUndefined) {
|
||||
Label convert_global_proxy;
|
||||
__ JumpIfRoot(ecx, RootIndex::kUndefinedValue, &convert_global_proxy,
|
||||
@ -2141,8 +2141,7 @@ void Builtins::Generate_CallFunction(MacroAssembler* masm,
|
||||
__ mov(edx, FieldOperand(edi, JSFunction::kSharedFunctionInfoOffset));
|
||||
__ bind(&convert_receiver);
|
||||
}
|
||||
__ mov(Operand(esp, eax, times_system_pointer_size, kSystemPointerSize),
|
||||
ecx);
|
||||
__ mov(args.GetReceiverOperand(), ecx);
|
||||
}
|
||||
__ bind(&done_convert);
|
||||
|
||||
@ -2277,8 +2276,9 @@ void Builtins::Generate_CallBoundFunctionImpl(MacroAssembler* masm) {
|
||||
__ AssertBoundFunction(edi);
|
||||
|
||||
// Patch the receiver to [[BoundThis]].
|
||||
StackArgumentsAccessor args(eax);
|
||||
__ mov(ecx, FieldOperand(edi, JSBoundFunction::kBoundThisOffset));
|
||||
__ mov(Operand(esp, eax, times_system_pointer_size, kSystemPointerSize), ecx);
|
||||
__ mov(args.GetReceiverOperand(), ecx);
|
||||
|
||||
// Push the [[BoundArguments]] onto the stack.
|
||||
Generate_PushBoundArguments(masm);
|
||||
@ -2295,6 +2295,7 @@ void Builtins::Generate_Call(MacroAssembler* masm, ConvertReceiverMode mode) {
|
||||
// -- eax : the number of arguments (not including the receiver)
|
||||
// -- edi : the target to call (can be any Object).
|
||||
// -----------------------------------
|
||||
StackArgumentsAccessor args(eax);
|
||||
|
||||
Label non_callable, non_function, non_smi, non_jsfunction,
|
||||
non_jsboundfunction;
|
||||
@ -2326,7 +2327,7 @@ void Builtins::Generate_Call(MacroAssembler* masm, ConvertReceiverMode mode) {
|
||||
// not we raise an exception).
|
||||
__ bind(&non_function);
|
||||
// Overwrite the original receiver with the (original) target.
|
||||
__ mov(Operand(esp, eax, times_system_pointer_size, kSystemPointerSize), edi);
|
||||
__ mov(args.GetReceiverOperand(), edi);
|
||||
// Let the "call_as_function_delegate" take care of the rest.
|
||||
__ LoadNativeContextSlot(edi, Context::CALL_AS_FUNCTION_DELEGATE_INDEX);
|
||||
__ Jump(masm->isolate()->builtins()->CallFunction(
|
||||
@ -2409,6 +2410,7 @@ void Builtins::Generate_Construct(MacroAssembler* masm) {
|
||||
// the JSFunction on which new was invoked initially)
|
||||
// -- edi : the constructor to call (can be any Object)
|
||||
// -----------------------------------
|
||||
StackArgumentsAccessor args(eax);
|
||||
|
||||
// Check if target is a Smi.
|
||||
Label non_constructor, non_proxy, non_jsfunction, non_jsboundfunction;
|
||||
@ -2445,8 +2447,7 @@ void Builtins::Generate_Construct(MacroAssembler* masm) {
|
||||
__ bind(&non_proxy);
|
||||
{
|
||||
// Overwrite the original receiver with the (original) target.
|
||||
__ mov(Operand(esp, eax, times_system_pointer_size, kSystemPointerSize),
|
||||
edi);
|
||||
__ mov(args.GetReceiverOperand(), edi);
|
||||
// Let the "call_as_constructor_delegate" take care of the rest.
|
||||
__ LoadNativeContextSlot(edi, Context::CALL_AS_CONSTRUCTOR_DELEGATE_INDEX);
|
||||
__ Jump(masm->isolate()->builtins()->CallFunction(),
|
||||
|
@ -1605,9 +1605,10 @@ void Builtins::Generate_FunctionPrototypeApply(MacroAssembler* masm) {
|
||||
// ----------- S t a t e -------------
|
||||
// -- rax : argc
|
||||
// -- rsp[0] : return address
|
||||
// -- rsp[8] : argArray
|
||||
// -- rsp[16] : thisArg
|
||||
// -- rsp[24] : receiver
|
||||
// The order of args depends on V8_REVERSE_JSARGS
|
||||
// -- args[0] : receiver
|
||||
// -- args[1] : thisArg
|
||||
// -- args[2] : argArray
|
||||
// -----------------------------------
|
||||
|
||||
// 1. Load receiver into rdi, argArray into rbx (if present), remove all
|
||||
@ -1615,17 +1616,17 @@ void Builtins::Generate_FunctionPrototypeApply(MacroAssembler* masm) {
|
||||
// present) instead.
|
||||
{
|
||||
Label no_arg_array, no_this_arg;
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
__ LoadRoot(rdx, RootIndex::kUndefinedValue);
|
||||
__ movq(rbx, rdx);
|
||||
__ movq(rdi, args.GetReceiverOperand());
|
||||
__ movq(rdi, args[0]);
|
||||
__ testq(rax, rax);
|
||||
__ j(zero, &no_this_arg, Label::kNear);
|
||||
{
|
||||
__ movq(rdx, args.GetArgumentOperand(1));
|
||||
__ movq(rdx, args[1]);
|
||||
__ cmpq(rax, Immediate(1));
|
||||
__ j(equal, &no_arg_array, Label::kNear);
|
||||
__ movq(rbx, args.GetArgumentOperand(2));
|
||||
__ movq(rbx, args[2]);
|
||||
__ bind(&no_arg_array);
|
||||
}
|
||||
__ bind(&no_this_arg);
|
||||
@ -1692,7 +1693,7 @@ void Builtins::Generate_FunctionPrototypeCall(MacroAssembler* masm) {
|
||||
|
||||
// 2. Get the callable to call (passed as receiver) from the stack.
|
||||
{
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
__ movq(rdi, args.GetReceiverOperand());
|
||||
}
|
||||
|
||||
@ -1702,10 +1703,10 @@ void Builtins::Generate_FunctionPrototypeCall(MacroAssembler* masm) {
|
||||
{
|
||||
Label loop;
|
||||
__ movq(rcx, rax);
|
||||
StackArgumentsAccessor args(rsp, rcx);
|
||||
StackArgumentsAccessor args(rcx);
|
||||
__ bind(&loop);
|
||||
__ movq(rbx, args.GetArgumentOperand(1));
|
||||
__ movq(args.GetArgumentOperand(0), rbx);
|
||||
__ movq(rbx, args[1]);
|
||||
__ movq(args[0], rbx);
|
||||
__ decq(rcx);
|
||||
__ j(not_zero, &loop); // While non-zero.
|
||||
__ DropUnderReturnAddress(1, rbx); // Drop one slot under return address.
|
||||
@ -1722,10 +1723,11 @@ void Builtins::Generate_ReflectApply(MacroAssembler* masm) {
|
||||
// ----------- S t a t e -------------
|
||||
// -- rax : argc
|
||||
// -- rsp[0] : return address
|
||||
// -- rsp[8] : argumentsList
|
||||
// -- rsp[16] : thisArgument
|
||||
// -- rsp[24] : target
|
||||
// -- rsp[32] : receiver
|
||||
// The order of args depends on V8_REVERSE_JSARGS
|
||||
// -- args[0] : receiver
|
||||
// -- args[1] : target
|
||||
// -- args[2] : thisArgument
|
||||
// -- args[3] : argumentsList
|
||||
// -----------------------------------
|
||||
|
||||
// 1. Load target into rdi (if present), argumentsList into rbx (if present),
|
||||
@ -1733,18 +1735,18 @@ void Builtins::Generate_ReflectApply(MacroAssembler* masm) {
|
||||
// thisArgument (if present) instead.
|
||||
{
|
||||
Label done;
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
__ LoadRoot(rdi, RootIndex::kUndefinedValue);
|
||||
__ movq(rdx, rdi);
|
||||
__ movq(rbx, rdi);
|
||||
__ cmpq(rax, Immediate(1));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ movq(rdi, args.GetArgumentOperand(1)); // target
|
||||
__ movq(rdi, args[1]); // target
|
||||
__ j(equal, &done, Label::kNear);
|
||||
__ movq(rdx, args.GetArgumentOperand(2)); // thisArgument
|
||||
__ movq(rdx, args[2]); // thisArgument
|
||||
__ cmpq(rax, Immediate(3));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ movq(rbx, args.GetArgumentOperand(3)); // argumentsList
|
||||
__ movq(rbx, args[3]); // argumentsList
|
||||
__ bind(&done);
|
||||
__ PopReturnAddressTo(rcx);
|
||||
__ leaq(rsp,
|
||||
@ -1773,10 +1775,11 @@ void Builtins::Generate_ReflectConstruct(MacroAssembler* masm) {
|
||||
// ----------- S t a t e -------------
|
||||
// -- rax : argc
|
||||
// -- rsp[0] : return address
|
||||
// -- rsp[8] : new.target (optional)
|
||||
// -- rsp[16] : argumentsList
|
||||
// -- rsp[24] : target
|
||||
// -- rsp[32] : receiver
|
||||
// The order of args depends on V8_REVERSE_JSARGS
|
||||
// -- args[0] : receiver
|
||||
// -- args[1] : target
|
||||
// -- args[2] : argumentsList
|
||||
// -- args[3] : new.target (optional)
|
||||
// -----------------------------------
|
||||
|
||||
// 1. Load target into rdi (if present), argumentsList into rbx (if present),
|
||||
@ -1785,19 +1788,19 @@ void Builtins::Generate_ReflectConstruct(MacroAssembler* masm) {
|
||||
// (if present) instead.
|
||||
{
|
||||
Label done;
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
__ LoadRoot(rdi, RootIndex::kUndefinedValue);
|
||||
__ movq(rdx, rdi);
|
||||
__ movq(rbx, rdi);
|
||||
__ cmpq(rax, Immediate(1));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ movq(rdi, args.GetArgumentOperand(1)); // target
|
||||
__ movq(rdi, args[1]); // target
|
||||
__ movq(rdx, rdi); // new.target defaults to target
|
||||
__ j(equal, &done, Label::kNear);
|
||||
__ movq(rbx, args.GetArgumentOperand(2)); // argumentsList
|
||||
__ movq(rbx, args[2]); // argumentsList
|
||||
__ cmpq(rax, Immediate(3));
|
||||
__ j(below, &done, Label::kNear);
|
||||
__ movq(rdx, args.GetArgumentOperand(3)); // new.target
|
||||
__ movq(rdx, args[3]); // new.target
|
||||
__ bind(&done);
|
||||
__ PopReturnAddressTo(rcx);
|
||||
__ leaq(rsp,
|
||||
@ -2137,9 +2140,9 @@ void Builtins::Generate_CallOrConstructForwardVarargs(MacroAssembler* masm,
|
||||
__ PopReturnAddressTo(rcx);
|
||||
__ bind(&loop);
|
||||
{
|
||||
StackArgumentsAccessor args(rbx, r8, ARGUMENTS_DONT_CONTAIN_RECEIVER);
|
||||
__ Push(args.GetArgumentOperand(0));
|
||||
__ decl(r8);
|
||||
__ Push(Operand(rbx, r8, times_system_pointer_size,
|
||||
kFPOnStackSize + kPCOnStackSize));
|
||||
__ j(not_zero, &loop);
|
||||
}
|
||||
__ PushReturnAddressFrom(rcx);
|
||||
@ -2162,7 +2165,7 @@ void Builtins::Generate_CallFunction(MacroAssembler* masm,
|
||||
// -- rdi : the function to call (checked to be a JSFunction)
|
||||
// -----------------------------------
|
||||
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
__ AssertFunction(rdi);
|
||||
|
||||
// ES6 section 9.2.1 [[Call]] ( thisArgument, argumentsList)
|
||||
@ -2375,7 +2378,7 @@ void Builtins::Generate_CallBoundFunctionImpl(MacroAssembler* masm) {
|
||||
__ AssertBoundFunction(rdi);
|
||||
|
||||
// Patch the receiver to [[BoundThis]].
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
__ LoadAnyTaggedField(rbx,
|
||||
FieldOperand(rdi, JSBoundFunction::kBoundThisOffset));
|
||||
__ movq(args.GetReceiverOperand(), rbx);
|
||||
@ -2396,7 +2399,7 @@ void Builtins::Generate_Call(MacroAssembler* masm, ConvertReceiverMode mode) {
|
||||
// -- rax : the number of arguments (not including the receiver)
|
||||
// -- rdi : the target to call (can be any Object)
|
||||
// -----------------------------------
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
|
||||
Label non_callable;
|
||||
__ JumpIfSmi(rdi, &non_callable);
|
||||
@ -2501,7 +2504,7 @@ void Builtins::Generate_Construct(MacroAssembler* masm) {
|
||||
// the JSFunction on which new was invoked initially)
|
||||
// -- rdi : the constructor to call (can be any Object)
|
||||
// -----------------------------------
|
||||
StackArgumentsAccessor args(rsp, rax);
|
||||
StackArgumentsAccessor args(rax);
|
||||
|
||||
// Check if target is a Smi.
|
||||
Label non_constructor;
|
||||
|
@ -31,6 +31,20 @@
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
Operand StackArgumentsAccessor::GetArgumentOperand(int index) const {
|
||||
DCHECK_GE(index, 0);
|
||||
#ifdef V8_REVERSE_JSARGS
|
||||
// arg[0] = esp + kPCOnStackSize;
|
||||
// arg[i] = arg[0] + i * kSystemPointerSize;
|
||||
return Operand(esp, kPCOnStackSize + index * kSystemPointerSize);
|
||||
#else
|
||||
// arg[0] = (esp + kPCOnStackSize) + argc * kSystemPointerSize;
|
||||
// arg[i] = arg[0] - i * kSystemPointerSize;
|
||||
return Operand(esp, argc_, times_system_pointer_size,
|
||||
kPCOnStackSize - index * kSystemPointerSize);
|
||||
#endif
|
||||
}
|
||||
|
||||
// -------------------------------------------------------------------------
|
||||
// MacroAssembler implementation.
|
||||
|
||||
@ -1095,9 +1109,14 @@ void MacroAssembler::CallDebugOnFunctionCall(Register fun, Register new_target,
|
||||
}
|
||||
Push(fun);
|
||||
Push(fun);
|
||||
// Arguments are located 2 words below the base pointer.
|
||||
#ifdef V8_REVERSE_JSARGS
|
||||
Operand receiver_op = Operand(ebp, kSystemPointerSize * 2);
|
||||
#else
|
||||
Operand receiver_op =
|
||||
Operand(ebp, actual_parameter_count, times_system_pointer_size,
|
||||
kSystemPointerSize * 2);
|
||||
#endif
|
||||
Push(receiver_op);
|
||||
CallRuntime(Runtime::kDebugOnFunctionCall);
|
||||
Pop(fun);
|
||||
|
@ -24,6 +24,26 @@ using MemOperand = Operand;
|
||||
enum RememberedSetAction { EMIT_REMEMBERED_SET, OMIT_REMEMBERED_SET };
|
||||
enum SmiCheck { INLINE_SMI_CHECK, OMIT_SMI_CHECK };
|
||||
|
||||
// Convenient class to access arguments below the stack pointer.
|
||||
class StackArgumentsAccessor {
|
||||
public:
|
||||
// argc = the number of arguments not including the receiver.
|
||||
explicit StackArgumentsAccessor(Register argc) : argc_(argc) {
|
||||
DCHECK_NE(argc_, no_reg);
|
||||
}
|
||||
|
||||
// Argument 0 is the receiver (despite argc not including the receiver).
|
||||
Operand operator[](int index) const { return GetArgumentOperand(index); }
|
||||
|
||||
Operand GetArgumentOperand(int index) const;
|
||||
Operand GetReceiverOperand() const { return GetArgumentOperand(0); }
|
||||
|
||||
private:
|
||||
const Register argc_;
|
||||
|
||||
DISALLOW_IMPLICIT_CONSTRUCTORS(StackArgumentsAccessor);
|
||||
};
|
||||
|
||||
class V8_EXPORT_PRIVATE TurboAssembler : public TurboAssemblerBase {
|
||||
public:
|
||||
using TurboAssemblerBase::TurboAssemblerBase;
|
||||
|
@ -34,28 +34,18 @@
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
Operand StackArgumentsAccessor::GetArgumentOperand(int index) {
|
||||
Operand StackArgumentsAccessor::GetArgumentOperand(int index) const {
|
||||
DCHECK_GE(index, 0);
|
||||
int receiver = (receiver_mode_ == ARGUMENTS_CONTAIN_RECEIVER) ? 1 : 0;
|
||||
int displacement_to_last_argument =
|
||||
base_reg_ == rsp ? kPCOnStackSize : kFPOnStackSize + kPCOnStackSize;
|
||||
displacement_to_last_argument += extra_displacement_to_last_argument_;
|
||||
if (argument_count_reg_ == no_reg) {
|
||||
// argument[0] is at base_reg_ + displacement_to_last_argument +
|
||||
// (argument_count_immediate_ + receiver - 1) * kSystemPointerSize.
|
||||
DCHECK_GT(argument_count_immediate_ + receiver, 0);
|
||||
return Operand(base_reg_,
|
||||
displacement_to_last_argument +
|
||||
(argument_count_immediate_ + receiver - 1 - index) *
|
||||
kSystemPointerSize);
|
||||
} else {
|
||||
// argument[0] is at base_reg_ + displacement_to_last_argument +
|
||||
// argument_count_reg_ * times_system_pointer_size + (receiver - 1) *
|
||||
// kSystemPointerSize.
|
||||
return Operand(base_reg_, argument_count_reg_, times_system_pointer_size,
|
||||
displacement_to_last_argument +
|
||||
(receiver - 1 - index) * kSystemPointerSize);
|
||||
}
|
||||
#ifdef V8_REVERSE_JSARGS
|
||||
// arg[0] = rsp + kPCOnStackSize;
|
||||
// arg[i] = arg[0] + i * kSystemPointerSize;
|
||||
return Operand(rsp, kPCOnStackSize + index * kSystemPointerSize);
|
||||
#else
|
||||
// arg[0] = (rsp + kPCOnStackSize) + argc * kSystemPointerSize;
|
||||
// arg[i] = arg[0] - i * kSystemPointerSize;
|
||||
return Operand(rsp, argc_, times_system_pointer_size,
|
||||
kPCOnStackSize - index * kSystemPointerSize);
|
||||
#endif
|
||||
}
|
||||
|
||||
void MacroAssembler::Load(Register destination, ExternalReference source) {
|
||||
@ -2371,8 +2361,15 @@ void MacroAssembler::CallDebugOnFunctionCall(Register fun, Register new_target,
|
||||
}
|
||||
Push(fun);
|
||||
Push(fun);
|
||||
Push(
|
||||
StackArgumentsAccessor(rbp, actual_parameter_count).GetReceiverOperand());
|
||||
// Arguments are located 2 words below the base pointer.
|
||||
#ifdef V8_REVERSE_JSARGS
|
||||
Operand receiver_op = Operand(rbp, kSystemPointerSize * 2);
|
||||
#else
|
||||
Operand receiver_op =
|
||||
Operand(rbp, actual_parameter_count, times_system_pointer_size,
|
||||
kSystemPointerSize * 2);
|
||||
#endif
|
||||
Push(receiver_op);
|
||||
CallRuntime(Runtime::kDebugOnFunctionCall);
|
||||
Pop(fun);
|
||||
if (new_target.is_valid()) {
|
||||
|
@ -33,36 +33,22 @@ struct SmiIndex {
|
||||
ScaleFactor scale;
|
||||
};
|
||||
|
||||
enum StackArgumentsAccessorReceiverMode {
|
||||
ARGUMENTS_CONTAIN_RECEIVER,
|
||||
ARGUMENTS_DONT_CONTAIN_RECEIVER
|
||||
};
|
||||
|
||||
// Convenient class to access arguments below the stack pointer.
|
||||
class StackArgumentsAccessor {
|
||||
public:
|
||||
StackArgumentsAccessor(Register base_reg, Register argument_count_reg,
|
||||
StackArgumentsAccessorReceiverMode receiver_mode =
|
||||
ARGUMENTS_CONTAIN_RECEIVER,
|
||||
int extra_displacement_to_last_argument = 0)
|
||||
: base_reg_(base_reg),
|
||||
argument_count_reg_(argument_count_reg),
|
||||
argument_count_immediate_(0),
|
||||
receiver_mode_(receiver_mode),
|
||||
extra_displacement_to_last_argument_(
|
||||
extra_displacement_to_last_argument) {}
|
||||
|
||||
Operand GetArgumentOperand(int index);
|
||||
Operand GetReceiverOperand() {
|
||||
DCHECK(receiver_mode_ == ARGUMENTS_CONTAIN_RECEIVER);
|
||||
return GetArgumentOperand(0);
|
||||
// argc = the number of arguments not including the receiver.
|
||||
explicit StackArgumentsAccessor(Register argc) : argc_(argc) {
|
||||
DCHECK_NE(argc_, no_reg);
|
||||
}
|
||||
|
||||
// Argument 0 is the receiver (despite argc not including the receiver).
|
||||
Operand operator[](int index) const { return GetArgumentOperand(index); }
|
||||
|
||||
Operand GetArgumentOperand(int index) const;
|
||||
Operand GetReceiverOperand() const { return GetArgumentOperand(0); }
|
||||
|
||||
private:
|
||||
const Register base_reg_;
|
||||
const Register argument_count_reg_;
|
||||
const int argument_count_immediate_;
|
||||
const StackArgumentsAccessorReceiverMode receiver_mode_;
|
||||
const int extra_displacement_to_last_argument_;
|
||||
const Register argc_;
|
||||
|
||||
DISALLOW_IMPLICIT_CONSTRUCTORS(StackArgumentsAccessor);
|
||||
};
|
||||
|
Loading…
Reference in New Issue
Block a user