Chromium Code Reviews| Index: src/x64/code-stubs-x64.cc | 
| diff --git a/src/x64/code-stubs-x64.cc b/src/x64/code-stubs-x64.cc | 
| index 83a1c779aebc18044e8e79c9ba8780109994c7ef..79c0b07d4d0656fa8c8d98272764e1442e2f2f23 100644 | 
| --- a/src/x64/code-stubs-x64.cc | 
| +++ b/src/x64/code-stubs-x64.cc | 
| @@ -1752,13 +1752,12 @@ void CallICStub::HandleArrayCase(MacroAssembler* masm, Label* miss) { | 
| // rdi - function | 
| // rdx - slot id | 
| // rbx - vector | 
| + // rax - number of arguments if argc_in_register() is true. | 
| // rcx - allocation site (loaded from vector[slot]). | 
| __ LoadNativeContextSlot(Context::ARRAY_FUNCTION_INDEX, r8); | 
| __ cmpp(rdi, r8); | 
| __ j(not_equal, miss); | 
| - __ movp(rax, Immediate(arg_count())); | 
| - | 
| // Increment the call count for monomorphic function calls. | 
| __ SmiAddConstant(FieldOperand(rbx, rdx, times_pointer_size, | 
| FixedArray::kHeaderSize + kPointerSize), | 
| @@ -1766,8 +1765,13 @@ void CallICStub::HandleArrayCase(MacroAssembler* masm, Label* miss) { | 
| __ movp(rbx, rcx); | 
| __ movp(rdx, rdi); | 
| - ArrayConstructorStub stub(masm->isolate(), arg_count()); | 
| - __ TailCallStub(&stub); | 
| + if (argc_in_register()) { | 
| + ArrayConstructorStub stub(masm->isolate()); | 
| + __ TailCallStub(&stub); | 
| + } else { | 
| + ArrayConstructorStub stub(masm->isolate(), arg_count()); | 
| + __ TailCallStub(&stub); | 
| + } | 
| } | 
| @@ -1776,12 +1780,14 @@ void CallICStub::Generate(MacroAssembler* masm) { | 
| // -- rdi - function | 
| // -- rdx - slot id | 
| // -- rbx - vector | 
| + // -- rax - number of arguments if argc_in_register() is true. | 
| // ----------------------------------- | 
| Isolate* isolate = masm->isolate(); | 
| Label extra_checks_or_miss, call, call_function; | 
| - int argc = arg_count(); | 
| - StackArgumentsAccessor args(rsp, argc); | 
| - ParameterCount actual(argc); | 
| + if (!argc_in_register()) { | 
| + int argc = arg_count(); | 
| + __ Set(rax, argc); | 
| + } | 
| // The checks. First, does rdi match the recorded monomorphic target? | 
| __ SmiToInteger32(rdx, rdx); | 
| @@ -1815,7 +1821,6 @@ void CallICStub::Generate(MacroAssembler* masm) { | 
| Smi::FromInt(CallICNexus::kCallCountIncrement)); | 
| __ bind(&call_function); | 
| - __ Set(rax, argc); | 
| __ Jump(masm->isolate()->builtins()->CallFunction(convert_mode(), | 
| tail_call_mode()), | 
| RelocInfo::CODE_TARGET); | 
| @@ -1854,7 +1859,6 @@ void CallICStub::Generate(MacroAssembler* masm) { | 
| TypeFeedbackVector::MegamorphicSentinel(isolate)); | 
| __ bind(&call); | 
| - __ Set(rax, argc); | 
| __ Jump(masm->isolate()->builtins()->Call(convert_mode(), tail_call_mode()), | 
| RelocInfo::CODE_TARGET); | 
| @@ -1892,10 +1896,16 @@ void CallICStub::Generate(MacroAssembler* masm) { | 
| FrameScope scope(masm, StackFrame::INTERNAL); | 
| CreateWeakCellStub create_stub(isolate); | 
| 
 
mvstanton
2016/02/15 11:13:45
Wow, is it just a bug that rax wasn't being saved?
 
mythria
2016/02/17 11:02:48
Yes :(
 
 | 
| + __ Integer32ToSmi(rax, rax); | 
| + __ Push(rax); | 
| __ Integer32ToSmi(rdx, rdx); | 
| __ Push(rdi); | 
| + | 
| __ CallStub(&create_stub); | 
| + | 
| __ Pop(rdi); | 
| + __ Pop(rax); | 
| + __ SmiToInteger32(rax, rax); | 
| } | 
| __ jmp(&call_function); | 
| @@ -1915,6 +1925,10 @@ void CallICStub::Generate(MacroAssembler* masm) { | 
| void CallICStub::GenerateMiss(MacroAssembler* masm) { | 
| FrameScope scope(masm, StackFrame::INTERNAL); | 
| + // Store the number of arguments to be used later. | 
| + __ Integer32ToSmi(rax, rax); | 
| + __ Push(rax); | 
| + | 
| // Push the receiver and the function and feedback info. | 
| __ Push(rdi); | 
| __ Push(rbx); | 
| @@ -1926,6 +1940,10 @@ void CallICStub::GenerateMiss(MacroAssembler* masm) { | 
| // Move result to edi and exit the internal frame. | 
| __ movp(rdi, rax); | 
| + // rdi, rbx, rdx are arguments to CallIC_Miss. They will be popped by | 
| + // Runtime_CallIC_Miss. | 
| + __ Pop(rax); | 
| + __ SmiToInteger32(rax, rax); | 
| } |