Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(3)

Side by Side Diff: src/ia32/full-codegen-ia32.cc

Issue 172523002: Create a function call IC (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Rebase Created 6 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 2550 matching lines...) Expand 10 before | Expand all | Expand 10 after
2561 2561
2562 2562
2563 2563
2564 2564
2565 // Code common for calls using the IC. 2565 // Code common for calls using the IC.
2566 void FullCodeGenerator::EmitCallWithIC(Call* expr) { 2566 void FullCodeGenerator::EmitCallWithIC(Call* expr) {
2567 Expression* callee = expr->expression(); 2567 Expression* callee = expr->expression();
2568 ZoneList<Expression*>* args = expr->arguments(); 2568 ZoneList<Expression*>* args = expr->arguments();
2569 int arg_count = args->length(); 2569 int arg_count = args->length();
2570 2570
2571 CallFunctionFlags flags; 2571 bool call_as_method = !callee->IsVariableProxy();
2572 // Get the target function. 2572 // Get the target function.
2573 if (callee->IsVariableProxy()) { 2573 if (!call_as_method) {
2574 { StackValueContext context(this); 2574 { StackValueContext context(this);
2575 EmitVariableLoad(callee->AsVariableProxy()); 2575 EmitVariableLoad(callee->AsVariableProxy());
2576 PrepareForBailout(callee, NO_REGISTERS); 2576 PrepareForBailout(callee, NO_REGISTERS);
2577 } 2577 }
2578 // Push undefined as receiver. This is patched in the method prologue if it 2578 // Push undefined as receiver. This is patched in the method prologue if it
2579 // is a classic mode method. 2579 // is a classic mode method.
2580 __ push(Immediate(isolate()->factory()->undefined_value())); 2580 __ push(Immediate(isolate()->factory()->undefined_value()));
2581 flags = NO_CALL_FUNCTION_FLAGS;
2582 } else { 2581 } else {
2583 // Load the function from the receiver. 2582 // Load the function from the receiver.
2584 ASSERT(callee->IsProperty()); 2583 ASSERT(callee->IsProperty());
2585 __ mov(edx, Operand(esp, 0)); 2584 __ mov(edx, Operand(esp, 0));
2586 EmitNamedPropertyLoad(callee->AsProperty()); 2585 EmitNamedPropertyLoad(callee->AsProperty());
2587 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG); 2586 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG);
2588 // Push the target function under the receiver. 2587 // Push the target function under the receiver.
2589 __ push(Operand(esp, 0)); 2588 __ push(Operand(esp, 0));
2590 __ mov(Operand(esp, kPointerSize), eax); 2589 __ mov(Operand(esp, kPointerSize), eax);
2591 flags = CALL_AS_METHOD;
2592 } 2590 }
2593 2591
2594 // Load the arguments. 2592 // Load the arguments.
2595 { PreservePositionScope scope(masm()->positions_recorder()); 2593 { PreservePositionScope scope(masm()->positions_recorder());
2596 for (int i = 0; i < arg_count; i++) { 2594 for (int i = 0; i < arg_count; i++) {
2597 VisitForStackValue(args->at(i)); 2595 VisitForStackValue(args->at(i));
2598 } 2596 }
2599 } 2597 }
2600 2598
2601 // Record source position of the IC call. 2599 // Record source position of the IC call.
2602 SetSourcePosition(expr->position()); 2600 SetSourcePosition(expr->position());
2603 CallFunctionStub stub(arg_count, flags); 2601 Handle<Code> ic = CallIC::initialize_stub(isolate(), arg_count,
2602 call_as_method);
2603 Handle<Object> uninitialized =
2604 TypeFeedbackInfo::UninitializedSentinel(isolate());
2605 StoreFeedbackVectorSlot(expr->CallFeedbackSlot(), uninitialized);
2606 __ LoadHeapObject(ebx, FeedbackVector());
2607 __ mov(edx, Immediate(Smi::FromInt(expr->CallFeedbackSlot())));
2604 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize)); 2608 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize));
2605 __ CallStub(&stub); 2609 CallIC(ic); // NOTE: no type feedback id.
Toon Verwaest 2014/03/10 13:50:44 What about something like: // Don't assign a type
mvstanton 2014/03/20 15:51:53 Done.
2610
2606 RecordJSReturnSite(expr); 2611 RecordJSReturnSite(expr);
2607 2612
2608 // Restore context register. 2613 // Restore context register.
2609 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset)); 2614 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset));
2610 2615
2611 context()->DropAndPlug(1, eax); 2616 context()->DropAndPlug(1, eax);
2612 } 2617 }
2613 2618
2614 2619
2615 // Code common for calls using the IC. 2620 // Code common for calls using the IC.
(...skipping 20 matching lines...) Expand all
2636 2641
2637 // Load the arguments. 2642 // Load the arguments.
2638 { PreservePositionScope scope(masm()->positions_recorder()); 2643 { PreservePositionScope scope(masm()->positions_recorder());
2639 for (int i = 0; i < arg_count; i++) { 2644 for (int i = 0; i < arg_count; i++) {
2640 VisitForStackValue(args->at(i)); 2645 VisitForStackValue(args->at(i));
2641 } 2646 }
2642 } 2647 }
2643 2648
2644 // Record source position of the IC call. 2649 // Record source position of the IC call.
2645 SetSourcePosition(expr->position()); 2650 SetSourcePosition(expr->position());
2646 CallFunctionStub stub(arg_count, CALL_AS_METHOD); 2651
2652 Handle<Code> ic = CallIC::initialize_stub(isolate(), arg_count,
Toon Verwaest 2014/03/10 13:50:44 Doesn't this fit on one line? Otherwise ... CallI
mvstanton 2014/03/20 15:51:53 Done.
2653 true);
2654 Handle<Object> uninitialized =
2655 TypeFeedbackInfo::UninitializedSentinel(isolate());
2656 StoreFeedbackVectorSlot(expr->CallFeedbackSlot(), uninitialized);
2657 __ LoadHeapObject(ebx, FeedbackVector());
2658 __ mov(edx, Immediate(Smi::FromInt(expr->CallFeedbackSlot())));
2647 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize)); 2659 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize));
2648 __ CallStub(&stub); 2660 CallIC(ic); // NOTE: no type feedback id.
2661
2649 RecordJSReturnSite(expr); 2662 RecordJSReturnSite(expr);
2650 2663
2651 // Restore context register. 2664 // Restore context register.
2652 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset)); 2665 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset));
2653 2666
2654 context()->DropAndPlug(1, eax); 2667 context()->DropAndPlug(1, eax);
2655 } 2668 }
2656 2669
2657 2670
2658 void FullCodeGenerator::EmitCallWithStub(Call* expr) { 2671 void FullCodeGenerator::EmitCallWithStub(Call* expr) {
Toon Verwaest 2014/03/10 13:50:44 I guess we can now remove this function and just u
mvstanton 2014/03/20 15:51:53 Cool, this refactored very nicely.
2659 // Code common for calls using the call stub. 2672 // Code common for calls using the call stub.
2660 ZoneList<Expression*>* args = expr->arguments(); 2673 ZoneList<Expression*>* args = expr->arguments();
2661 int arg_count = args->length(); 2674 int arg_count = args->length();
2662 { PreservePositionScope scope(masm()->positions_recorder()); 2675 { PreservePositionScope scope(masm()->positions_recorder());
2663 for (int i = 0; i < arg_count; i++) { 2676 for (int i = 0; i < arg_count; i++) {
2664 VisitForStackValue(args->at(i)); 2677 VisitForStackValue(args->at(i));
2665 } 2678 }
2666 } 2679 }
2667 // Record source position for debugger. 2680 // Record source position for debugger.
2668 SetSourcePosition(expr->position()); 2681 SetSourcePosition(expr->position());
2669 2682
2670 Handle<Object> uninitialized = 2683 Handle<Object> uninitialized =
2671 TypeFeedbackInfo::UninitializedSentinel(isolate()); 2684 TypeFeedbackInfo::UninitializedSentinel(isolate());
2672 StoreFeedbackVectorSlot(expr->CallFeedbackSlot(), uninitialized); 2685 StoreFeedbackVectorSlot(expr->CallFeedbackSlot(), uninitialized);
2673 __ LoadHeapObject(ebx, FeedbackVector()); 2686 __ LoadHeapObject(ebx, FeedbackVector());
2674 __ mov(edx, Immediate(Smi::FromInt(expr->CallFeedbackSlot()))); 2687 __ mov(edx, Immediate(Smi::FromInt(expr->CallFeedbackSlot())));
2675 2688
2676 // Record call targets in unoptimized code. 2689 // Record call targets in unoptimized code.
2677 CallFunctionStub stub(arg_count, RECORD_CALL_TARGET); 2690 Handle<Code> ic = CallIC::initialize_stub(isolate(), arg_count,
2691 false);
2678 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize)); 2692 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize));
2679 __ CallStub(&stub); 2693 CallIC(ic); // NOTE: no type feedback id.
2680 2694
2681 RecordJSReturnSite(expr); 2695 RecordJSReturnSite(expr);
2682 // Restore context register. 2696 // Restore context register.
2683 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset)); 2697 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset));
2684 context()->DropAndPlug(1, eax); 2698 context()->DropAndPlug(1, eax);
2685 } 2699 }
2686 2700
2687 2701
2688 void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) { 2702 void FullCodeGenerator::EmitResolvePossiblyDirectEval(int arg_count) {
2689 // Push copy of the first argument or undefined if it doesn't exist. 2703 // Push copy of the first argument or undefined if it doesn't exist.
(...skipping 2221 matching lines...) Expand 10 before | Expand all | Expand 10 after
4911 4925
4912 ASSERT_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(), 4926 ASSERT_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(),
4913 Assembler::target_address_at(call_target_address)); 4927 Assembler::target_address_at(call_target_address));
4914 return OSR_AFTER_STACK_CHECK; 4928 return OSR_AFTER_STACK_CHECK;
4915 } 4929 }
4916 4930
4917 4931
4918 } } // namespace v8::internal 4932 } } // namespace v8::internal
4919 4933
4920 #endif // V8_TARGET_ARCH_IA32 4934 #endif // V8_TARGET_ARCH_IA32
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698