Commit 85cd0d87 authored by jgruber's avatar jgruber Committed by Commit Bot

Refactor InterpreterPushArgsThenConstruct

This reorders arguments in preparation for removing ebx from its
calling convention (in a follow-up some args will be passed on the
stack).

Drive-by: Improve readability in the code handling different cases
(array,spread,...).

Bug: v8:6666
Change-Id: I0160f8efafd0fd0e841739578e01c32b38adb66e
Reviewed-on: https://chromium-review.googlesource.com/1196884Reviewed-by: 's avatarRoss McIlroy <rmcilroy@chromium.org>
Commit-Queue: Jakob Gruber <jgruber@chromium.org>
Cr-Commit-Position: refs/heads/master@{#55557}
parent e034c1ad
......@@ -237,10 +237,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
r0, // argument count (not including receiver)
r3, // new target
r4, // address of the first argument
r1, // constructor to call
r3, // new target
r2, // allocation site feedback if available, undefined otherwise
r4 // address of the first argument
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
......@@ -242,10 +242,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
x0, // argument count (not including receiver)
x3, // new target
x4, // address of the first argument
x1, // constructor to call
x3, // new target
x2, // allocation site feedback if available, undefined otherwise
x4 // address of the first argument
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
......@@ -1110,29 +1110,26 @@ void Builtins::Generate_InterpreterPushArgsThenConstructImpl(
__ Pop(edx);
__ Pop(edi);
if (mode == InterpreterPushArgsMode::kWithFinalSpread) {
__ PopReturnAddressTo(ebx);
__ Pop(ecx); // Pass the spread in a register
__ PushReturnAddressFrom(ebx);
__ sub(eax, Immediate(1)); // Subtract one for spread
} else {
__ AssertUndefinedOrAllocationSite(ebx);
}
// Call the appropriate constructor. Arguments are already in registers.
if (mode == InterpreterPushArgsMode::kArrayFunction) {
// Tail call to the array construct stub (still in the caller
// context at this point).
// Tail call to the array construct stub (still in the caller context at
// this point).
__ AssertUndefinedOrAllocationSite(ebx);
__ AssertFunction(edi);
__ MoveForRootRegisterRefactoring(kJavaScriptCallExtraArg1Register, ebx);
Handle<Code> code = BUILTIN_CODE(masm->isolate(), ArrayConstructorImpl);
__ Jump(code, RelocInfo::CODE_TARGET);
} else if (mode == InterpreterPushArgsMode::kWithFinalSpread) {
// Call the constructor with unmodified eax, edi, edx values.
__ PopReturnAddressTo(ebx);
__ Pop(ecx); // Pass the spread in a register
__ PushReturnAddressFrom(ebx);
__ sub(eax, Immediate(1)); // Subtract one for spread
__ Jump(BUILTIN_CODE(masm->isolate(), ConstructWithSpread),
RelocInfo::CODE_TARGET);
} else {
DCHECK_EQ(InterpreterPushArgsMode::kOther, mode);
// Call the constructor with unmodified eax, edi, edx values.
__ AssertUndefinedOrAllocationSite(ebx);
__ Jump(BUILTIN_CODE(masm->isolate(), Construct), RelocInfo::CODE_TARGET);
}
......
......@@ -246,10 +246,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
eax, // argument count (not including receiver)
edx, // new target
edi, // constructor
ebx, // allocation site feedback
ecx, // address of first argument
edi, // constructor to call
edx, // new target
ebx, // allocation site feedback if available, undefined otherwise
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
......@@ -1004,13 +1004,13 @@ class InterpreterPushArgsThenCallDescriptor : public CallInterfaceDescriptor {
class InterpreterPushArgsThenConstructDescriptor
: public CallInterfaceDescriptor {
public:
DEFINE_PARAMETERS(kNumberOfArguments, kNewTarget, kConstructor,
kFeedbackElement, kFirstArgument)
DEFINE_PARAMETERS(kNumberOfArguments, kFirstArgument, kConstructor,
kNewTarget, kFeedbackElement)
DEFINE_PARAMETER_TYPES(MachineType::Int32(), // kNumberOfArguments
MachineType::AnyTagged(), // kNewTarget
MachineType::Pointer(), // kFirstArgument
MachineType::AnyTagged(), // kConstructor
MachineType::AnyTagged(), // kFeedbackElement
MachineType::Pointer()) // kFirstArgument
MachineType::AnyTagged(), // kNewTarget
MachineType::AnyTagged()) // kFeedbackElement
DECLARE_DESCRIPTOR(InterpreterPushArgsThenConstructDescriptor,
CallInterfaceDescriptor)
};
......
......@@ -1074,8 +1074,8 @@ Node* InterpreterAssembler::Construct(Node* target, Node* context,
isolate(), InterpreterPushArgsMode::kArrayFunction);
Node* code_target = HeapConstant(callable.code());
var_result.Bind(CallStub(callable.descriptor(), code_target, context,
args.reg_count(), new_target, target,
var_site.value(), args.base_reg_location()));
args.reg_count(), args.base_reg_location(), target,
new_target, var_site.value()));
Goto(&return_result);
}
......@@ -1087,8 +1087,8 @@ Node* InterpreterAssembler::Construct(Node* target, Node* context,
isolate(), InterpreterPushArgsMode::kOther);
Node* code_target = HeapConstant(callable.code());
var_result.Bind(CallStub(callable.descriptor(), code_target, context,
args.reg_count(), new_target, target,
UndefinedConstant(), args.base_reg_location()));
args.reg_count(), args.base_reg_location(), target,
new_target, UndefinedConstant()));
Goto(&return_result);
}
......@@ -1212,8 +1212,8 @@ Node* InterpreterAssembler::ConstructWithSpread(Node* target, Node* context,
isolate(), InterpreterPushArgsMode::kWithFinalSpread);
Node* code_target = HeapConstant(callable.code());
return CallStub(callable.descriptor(), code_target, context, args.reg_count(),
new_target, target, UndefinedConstant(),
args.base_reg_location());
args.base_reg_location(), target, new_target,
UndefinedConstant());
}
Node* InterpreterAssembler::CallRuntimeN(Node* function_id, Node* context,
......
......@@ -238,10 +238,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
a0, // argument count (not including receiver)
a3, // new target
t4, // address of the first argument
a1, // constructor to call
a2, // allocation site feedback if available, undefined otherwise.
t4 // address of the first argument
a3, // new target
a2, // allocation site feedback if available, undefined otherwise
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
......@@ -238,10 +238,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
a0, // argument count (not including receiver)
a3, // new target
a4, // address of the first argument
a1, // constructor to call
a2, // allocation site feedback if available, undefined otherwise.
a4 // address of the first argument
a3, // new target
a2, // allocation site feedback if available, undefined otherwise
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
......@@ -238,10 +238,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
r3, // argument count (not including receiver)
r6, // new target
r7, // address of the first argument
r4, // constructor to call
r6, // new target
r5, // allocation site feedback if available, undefined otherwise
r7 // address of the first argument
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
......@@ -236,10 +236,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
r2, // argument count (not including receiver)
r5, // new target
r6, // address of the first argument
r3, // constructor to call
r5, // new target
r4, // allocation site feedback if available, undefined otherwise
r6 // address of the first argument
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
......@@ -239,10 +239,10 @@ void InterpreterPushArgsThenConstructDescriptor::InitializePlatformSpecific(
CallInterfaceDescriptorData* data) {
Register registers[] = {
rax, // argument count (not including receiver)
rcx, // address of first argument
rdi, // constructor to call
rdx, // new target
rdi, // constructor
rbx, // allocation site feedback if available, undefined otherwise
rcx, // address of first argument
};
data->InitializePlatformSpecific(arraysize(registers), registers);
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment