X87: Fix pushing of register in CallConstructStub outside frame.
port 1f295980b7
(r29787).
original commit message:
This fixes a recent regression where the register holding the original
receiver was pushed onto the stack before the internal frame within the
CallStubInRecordCallTarget helper was created. That in turn confused
the stack walker when allocations in these stubs failed.
BUG=
Review URL: https://codereview.chromium.org/1247493004
Cr-Commit-Position: refs/heads/master@{#29828}
This commit is contained in:
parent
6d542bfcc2
commit
5cdb1cee4b
@ -1603,38 +1603,57 @@ void CompareICStub::GenerateGeneric(MacroAssembler* masm) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void CallStubInRecordCallTarget(MacroAssembler* masm, CodeStub* stub) {
|
static void CallStubInRecordCallTarget(MacroAssembler* masm, CodeStub* stub,
|
||||||
|
bool is_super) {
|
||||||
// eax : number of arguments to the construct function
|
// eax : number of arguments to the construct function
|
||||||
// ebx : Feedback vector
|
// ebx : feedback vector
|
||||||
// edx : slot in feedback vector (Smi)
|
// edx : slot in feedback vector (Smi)
|
||||||
// edi : the function to call
|
// edi : the function to call
|
||||||
FrameScope scope(masm, StackFrame::INTERNAL);
|
// esp[0]: original receiver (for IsSuperConstructorCall)
|
||||||
|
if (is_super) {
|
||||||
|
__ pop(ecx);
|
||||||
|
}
|
||||||
|
|
||||||
// Number-of-arguments register must be smi-tagged to call out.
|
{
|
||||||
__ SmiTag(eax);
|
FrameScope scope(masm, StackFrame::INTERNAL);
|
||||||
__ push(eax);
|
|
||||||
__ push(edi);
|
|
||||||
__ push(edx);
|
|
||||||
__ push(ebx);
|
|
||||||
|
|
||||||
__ CallStub(stub);
|
// Number-of-arguments register must be smi-tagged to call out.
|
||||||
|
__ SmiTag(eax);
|
||||||
|
__ push(eax);
|
||||||
|
__ push(edi);
|
||||||
|
__ push(edx);
|
||||||
|
__ push(ebx);
|
||||||
|
if (is_super) {
|
||||||
|
__ push(ecx);
|
||||||
|
}
|
||||||
|
|
||||||
__ pop(ebx);
|
__ CallStub(stub);
|
||||||
__ pop(edx);
|
|
||||||
__ pop(edi);
|
if (is_super) {
|
||||||
__ pop(eax);
|
__ pop(ecx);
|
||||||
__ SmiUntag(eax);
|
}
|
||||||
|
__ pop(ebx);
|
||||||
|
__ pop(edx);
|
||||||
|
__ pop(edi);
|
||||||
|
__ pop(eax);
|
||||||
|
__ SmiUntag(eax);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (is_super) {
|
||||||
|
__ push(ecx);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
static void GenerateRecordCallTarget(MacroAssembler* masm) {
|
static void GenerateRecordCallTarget(MacroAssembler* masm, bool is_super) {
|
||||||
// Cache the called function in a feedback vector slot. Cache states
|
// Cache the called function in a feedback vector slot. Cache states
|
||||||
// are uninitialized, monomorphic (indicated by a JSFunction), and
|
// are uninitialized, monomorphic (indicated by a JSFunction), and
|
||||||
// megamorphic.
|
// megamorphic.
|
||||||
// eax : number of arguments to the construct function
|
// eax : number of arguments to the construct function
|
||||||
// ebx : Feedback vector
|
// ebx : feedback vector
|
||||||
// edx : slot in feedback vector (Smi)
|
// edx : slot in feedback vector (Smi)
|
||||||
// edi : the function to call
|
// edi : the function to call
|
||||||
|
// esp[0]: original receiver (for IsSuperConstructorCall)
|
||||||
Isolate* isolate = masm->isolate();
|
Isolate* isolate = masm->isolate();
|
||||||
Label initialize, done, miss, megamorphic, not_array_function;
|
Label initialize, done, miss, megamorphic, not_array_function;
|
||||||
|
|
||||||
@ -1703,14 +1722,14 @@ static void GenerateRecordCallTarget(MacroAssembler* masm) {
|
|||||||
// Create an AllocationSite if we don't already have it, store it in the
|
// Create an AllocationSite if we don't already have it, store it in the
|
||||||
// slot.
|
// slot.
|
||||||
CreateAllocationSiteStub create_stub(isolate);
|
CreateAllocationSiteStub create_stub(isolate);
|
||||||
CallStubInRecordCallTarget(masm, &create_stub);
|
CallStubInRecordCallTarget(masm, &create_stub, is_super);
|
||||||
__ jmp(&done);
|
__ jmp(&done);
|
||||||
|
|
||||||
__ bind(¬_array_function);
|
__ bind(¬_array_function);
|
||||||
}
|
}
|
||||||
|
|
||||||
CreateWeakCellStub create_stub(isolate);
|
CreateWeakCellStub create_stub(isolate);
|
||||||
CallStubInRecordCallTarget(masm, &create_stub);
|
CallStubInRecordCallTarget(masm, &create_stub, is_super);
|
||||||
__ bind(&done);
|
__ bind(&done);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1850,7 +1869,7 @@ void CallConstructStub::Generate(MacroAssembler* masm) {
|
|||||||
__ j(not_equal, &slow);
|
__ j(not_equal, &slow);
|
||||||
|
|
||||||
if (RecordCallTarget()) {
|
if (RecordCallTarget()) {
|
||||||
GenerateRecordCallTarget(masm);
|
GenerateRecordCallTarget(masm, IsSuperConstructorCall());
|
||||||
|
|
||||||
if (FLAG_pretenuring_call_new) {
|
if (FLAG_pretenuring_call_new) {
|
||||||
// Put the AllocationSite from the feedback vector into ebx.
|
// Put the AllocationSite from the feedback vector into ebx.
|
||||||
@ -1892,7 +1911,7 @@ void CallConstructStub::Generate(MacroAssembler* masm) {
|
|||||||
// edi: called object
|
// edi: called object
|
||||||
// eax: number of arguments
|
// eax: number of arguments
|
||||||
// ecx: object map
|
// ecx: object map
|
||||||
// esp[0]: original receiver
|
// esp[0]: original receiver (for IsSuperConstructorCall)
|
||||||
Label do_call;
|
Label do_call;
|
||||||
__ bind(&slow);
|
__ bind(&slow);
|
||||||
__ CmpInstanceType(ecx, JS_FUNCTION_PROXY_TYPE);
|
__ CmpInstanceType(ecx, JS_FUNCTION_PROXY_TYPE);
|
||||||
|
Loading…
Reference in New Issue
Block a user