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

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

Issue 527963002: Implement loads and calls from 'super' (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Rebased before landing Created 6 years, 3 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
« no previous file with comments | « src/hydrogen.cc ('k') | src/messages.js » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "src/v8.h" 5 #include "src/v8.h"
6 6
7 #if V8_TARGET_ARCH_IA32 7 #if V8_TARGET_ARCH_IA32
8 8
9 #include "src/code-factory.h" 9 #include "src/code-factory.h"
10 #include "src/code-stubs.h" 10 #include "src/code-stubs.h"
(...skipping 1260 matching lines...) Expand 10 before | Expand all | Expand 10 after
1271 context()->Plug(eax); 1271 context()->Plug(eax);
1272 } 1272 }
1273 1273
1274 1274
1275 void FullCodeGenerator::VisitVariableProxy(VariableProxy* expr) { 1275 void FullCodeGenerator::VisitVariableProxy(VariableProxy* expr) {
1276 Comment cmnt(masm_, "[ VariableProxy"); 1276 Comment cmnt(masm_, "[ VariableProxy");
1277 EmitVariableLoad(expr); 1277 EmitVariableLoad(expr);
1278 } 1278 }
1279 1279
1280 1280
1281 void FullCodeGenerator::EmitLoadHomeObject(SuperReference* expr) {
1282 Comment cnmt(masm_, "[ SuperReference ");
1283
1284 __ mov(LoadDescriptor::ReceiverRegister(),
1285 Operand(ebp, JavaScriptFrameConstants::kFunctionOffset));
1286
1287 Handle<Symbol> home_object_symbol(isolate()->heap()->home_object_symbol());
1288 __ mov(LoadDescriptor::NameRegister(), home_object_symbol);
1289
1290 CallLoadIC(NOT_CONTEXTUAL, expr->HomeObjectFeedbackId());
1291
1292 __ cmp(eax, isolate()->factory()->undefined_value());
1293 Label done;
1294 __ j(not_equal, &done);
1295 __ CallRuntime(Runtime::kThrowNonMethodError, 0);
1296 __ bind(&done);
1297 }
1298
1299
1281 void FullCodeGenerator::EmitLoadGlobalCheckExtensions(VariableProxy* proxy, 1300 void FullCodeGenerator::EmitLoadGlobalCheckExtensions(VariableProxy* proxy,
1282 TypeofState typeof_state, 1301 TypeofState typeof_state,
1283 Label* slow) { 1302 Label* slow) {
1284 Register context = esi; 1303 Register context = esi;
1285 Register temp = edx; 1304 Register temp = edx;
1286 1305
1287 Scope* s = scope(); 1306 Scope* s = scope();
1288 while (s != NULL) { 1307 while (s != NULL) {
1289 if (s->num_heap_slots() > 0) { 1308 if (s->num_heap_slots() > 0) {
1290 if (s->calls_sloppy_eval()) { 1309 if (s->calls_sloppy_eval()) {
(...skipping 933 matching lines...) Expand 10 before | Expand all | Expand 10 after
2224 if (FLAG_vector_ics) { 2243 if (FLAG_vector_ics) {
2225 __ mov(VectorLoadICDescriptor::SlotRegister(), 2244 __ mov(VectorLoadICDescriptor::SlotRegister(),
2226 Immediate(Smi::FromInt(prop->PropertyFeedbackSlot()))); 2245 Immediate(Smi::FromInt(prop->PropertyFeedbackSlot())));
2227 CallLoadIC(NOT_CONTEXTUAL); 2246 CallLoadIC(NOT_CONTEXTUAL);
2228 } else { 2247 } else {
2229 CallLoadIC(NOT_CONTEXTUAL, prop->PropertyFeedbackId()); 2248 CallLoadIC(NOT_CONTEXTUAL, prop->PropertyFeedbackId());
2230 } 2249 }
2231 } 2250 }
2232 2251
2233 2252
2253 void FullCodeGenerator::EmitNamedSuperPropertyLoad(Property* prop) {
2254 SetSourcePosition(prop->position());
2255 Literal* key = prop->key()->AsLiteral();
2256 DCHECK(!key->value()->IsSmi());
2257 DCHECK(prop->IsSuperAccess());
2258
2259 SuperReference* super_ref = prop->obj()->AsSuperReference();
2260 EmitLoadHomeObject(super_ref);
2261 __ push(eax);
2262 VisitForStackValue(super_ref->this_var());
2263 __ push(Immediate(key->value()));
2264 __ CallRuntime(Runtime::kLoadFromSuper, 3);
2265 }
2266
2267
2234 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) { 2268 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) {
2235 SetSourcePosition(prop->position()); 2269 SetSourcePosition(prop->position());
2236 Handle<Code> ic = CodeFactory::KeyedLoadIC(isolate()).code(); 2270 Handle<Code> ic = CodeFactory::KeyedLoadIC(isolate()).code();
2237 if (FLAG_vector_ics) { 2271 if (FLAG_vector_ics) {
2238 __ mov(VectorLoadICDescriptor::SlotRegister(), 2272 __ mov(VectorLoadICDescriptor::SlotRegister(),
2239 Immediate(Smi::FromInt(prop->PropertyFeedbackSlot()))); 2273 Immediate(Smi::FromInt(prop->PropertyFeedbackSlot())));
2240 CallIC(ic); 2274 CallIC(ic);
2241 } else { 2275 } else {
2242 CallIC(ic, prop->PropertyFeedbackId()); 2276 CallIC(ic, prop->PropertyFeedbackId());
2243 } 2277 }
(...skipping 269 matching lines...) Expand 10 before | Expand all | Expand 10 after
2513 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2547 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2514 context()->Plug(eax); 2548 context()->Plug(eax);
2515 } 2549 }
2516 2550
2517 2551
2518 void FullCodeGenerator::VisitProperty(Property* expr) { 2552 void FullCodeGenerator::VisitProperty(Property* expr) {
2519 Comment cmnt(masm_, "[ Property"); 2553 Comment cmnt(masm_, "[ Property");
2520 Expression* key = expr->key(); 2554 Expression* key = expr->key();
2521 2555
2522 if (key->IsPropertyName()) { 2556 if (key->IsPropertyName()) {
2523 VisitForAccumulatorValue(expr->obj()); 2557 if (!expr->IsSuperAccess()) {
2524 __ Move(LoadDescriptor::ReceiverRegister(), result_register()); 2558 VisitForAccumulatorValue(expr->obj());
2525 EmitNamedPropertyLoad(expr); 2559 __ Move(LoadDescriptor::ReceiverRegister(), result_register());
2560 EmitNamedPropertyLoad(expr);
2561 } else {
2562 EmitNamedSuperPropertyLoad(expr);
2563 }
2526 PrepareForBailoutForId(expr->LoadId(), TOS_REG); 2564 PrepareForBailoutForId(expr->LoadId(), TOS_REG);
2527 context()->Plug(eax); 2565 context()->Plug(eax);
2528 } else { 2566 } else {
2529 VisitForStackValue(expr->obj()); 2567 VisitForStackValue(expr->obj());
2530 VisitForAccumulatorValue(expr->key()); 2568 VisitForAccumulatorValue(expr->key());
2531 __ pop(LoadDescriptor::ReceiverRegister()); // Object. 2569 __ pop(LoadDescriptor::ReceiverRegister()); // Object.
2532 __ Move(LoadDescriptor::NameRegister(), result_register()); // Key. 2570 __ Move(LoadDescriptor::NameRegister(), result_register()); // Key.
2533 EmitKeyedPropertyLoad(expr); 2571 EmitKeyedPropertyLoad(expr);
2534 context()->Plug(eax); 2572 context()->Plug(eax);
2535 } 2573 }
(...skipping 18 matching lines...) Expand all
2554 { StackValueContext context(this); 2592 { StackValueContext context(this);
2555 EmitVariableLoad(callee->AsVariableProxy()); 2593 EmitVariableLoad(callee->AsVariableProxy());
2556 PrepareForBailout(callee, NO_REGISTERS); 2594 PrepareForBailout(callee, NO_REGISTERS);
2557 } 2595 }
2558 // Push undefined as receiver. This is patched in the method prologue if it 2596 // Push undefined as receiver. This is patched in the method prologue if it
2559 // is a sloppy mode method. 2597 // is a sloppy mode method.
2560 __ push(Immediate(isolate()->factory()->undefined_value())); 2598 __ push(Immediate(isolate()->factory()->undefined_value()));
2561 } else { 2599 } else {
2562 // Load the function from the receiver. 2600 // Load the function from the receiver.
2563 DCHECK(callee->IsProperty()); 2601 DCHECK(callee->IsProperty());
2602 DCHECK(!callee->AsProperty()->IsSuperAccess());
2564 __ mov(LoadDescriptor::ReceiverRegister(), Operand(esp, 0)); 2603 __ mov(LoadDescriptor::ReceiverRegister(), Operand(esp, 0));
2565 EmitNamedPropertyLoad(callee->AsProperty()); 2604 EmitNamedPropertyLoad(callee->AsProperty());
2566 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG); 2605 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG);
2567 // Push the target function under the receiver. 2606 // Push the target function under the receiver.
2568 __ push(Operand(esp, 0)); 2607 __ push(Operand(esp, 0));
2569 __ mov(Operand(esp, kPointerSize), eax); 2608 __ mov(Operand(esp, kPointerSize), eax);
2570 } 2609 }
2571 2610
2572 EmitCall(expr, call_type); 2611 EmitCall(expr, call_type);
2573 } 2612 }
2574 2613
2575 2614
2615 void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
2616 Expression* callee = expr->expression();
2617 DCHECK(callee->IsProperty());
2618 Property* prop = callee->AsProperty();
2619 DCHECK(prop->IsSuperAccess());
2620
2621 SetSourcePosition(prop->position());
2622 Literal* key = prop->key()->AsLiteral();
2623 DCHECK(!key->value()->IsSmi());
2624 // Load the function from the receiver.
2625 SuperReference* super_ref = callee->AsProperty()->obj()->AsSuperReference();
2626 EmitLoadHomeObject(super_ref);
2627 __ push(eax);
2628 VisitForAccumulatorValue(super_ref->this_var());
2629 __ push(eax);
2630 __ push(Operand(esp, kPointerSize));
2631 __ push(eax);
2632 __ push(Immediate(key->value()));
2633 // Stack here:
2634 // - home_object
2635 // - this (receiver)
2636 // - home_object <-- LoadFromSuper will pop here and below.
2637 // - this (receiver)
2638 // - key
2639 __ CallRuntime(Runtime::kLoadFromSuper, 3);
2640
2641 // Replace home_object with target function.
2642 __ mov(Operand(esp, kPointerSize), eax);
2643
2644 // Stack here:
2645 // - target function
2646 // - this (receiver)
2647 EmitCall(expr, CallICState::METHOD);
2648 }
2649
2650
2576 // Code common for calls using the IC. 2651 // Code common for calls using the IC.
2577 void FullCodeGenerator::EmitKeyedCallWithLoadIC(Call* expr, 2652 void FullCodeGenerator::EmitKeyedCallWithLoadIC(Call* expr,
2578 Expression* key) { 2653 Expression* key) {
2579 // Load the key. 2654 // Load the key.
2580 VisitForAccumulatorValue(key); 2655 VisitForAccumulatorValue(key);
2581 2656
2582 Expression* callee = expr->expression(); 2657 Expression* callee = expr->expression();
2583 2658
2584 // Load the function from the receiver. 2659 // Load the function from the receiver.
2585 DCHECK(callee->IsProperty()); 2660 DCHECK(callee->IsProperty());
(...skipping 140 matching lines...) Expand 10 before | Expand all | Expand 10 after
2726 __ push(Immediate(isolate()->factory()->undefined_value())); 2801 __ push(Immediate(isolate()->factory()->undefined_value()));
2727 __ bind(&call); 2802 __ bind(&call);
2728 } 2803 }
2729 2804
2730 // The receiver is either the global receiver or an object found by 2805 // The receiver is either the global receiver or an object found by
2731 // LoadContextSlot. 2806 // LoadContextSlot.
2732 EmitCall(expr); 2807 EmitCall(expr);
2733 2808
2734 } else if (call_type == Call::PROPERTY_CALL) { 2809 } else if (call_type == Call::PROPERTY_CALL) {
2735 Property* property = callee->AsProperty(); 2810 Property* property = callee->AsProperty();
2736 { PreservePositionScope scope(masm()->positions_recorder()); 2811 bool is_named_call = property->key()->IsPropertyName();
2737 VisitForStackValue(property->obj()); 2812 // super.x() is handled in EmitCallWithLoadIC.
2813 if (property->IsSuperAccess() && is_named_call) {
2814 EmitSuperCallWithLoadIC(expr);
2815 } else {
2816 {
2817 PreservePositionScope scope(masm()->positions_recorder());
2818 VisitForStackValue(property->obj());
2819 }
2820 if (is_named_call) {
2821 EmitCallWithLoadIC(expr);
2822 } else {
2823 EmitKeyedCallWithLoadIC(expr, property->key());
2824 }
2738 } 2825 }
2739 if (property->key()->IsPropertyName()) {
2740 EmitCallWithLoadIC(expr);
2741 } else {
2742 EmitKeyedCallWithLoadIC(expr, property->key());
2743 }
2744
2745 } else { 2826 } else {
2746 DCHECK(call_type == Call::OTHER_CALL); 2827 DCHECK(call_type == Call::OTHER_CALL);
2747 // Call to an arbitrary expression not handled specially above. 2828 // Call to an arbitrary expression not handled specially above.
2748 { PreservePositionScope scope(masm()->positions_recorder()); 2829 { PreservePositionScope scope(masm()->positions_recorder());
2749 VisitForStackValue(callee); 2830 VisitForStackValue(callee);
2750 } 2831 }
2751 __ push(Immediate(isolate()->factory()->undefined_value())); 2832 __ push(Immediate(isolate()->factory()->undefined_value()));
2752 // Emit function call. 2833 // Emit function call.
2753 EmitCall(expr); 2834 EmitCall(expr);
2754 } 2835 }
(...skipping 2068 matching lines...) Expand 10 before | Expand all | Expand 10 after
4823 DCHECK_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(), 4904 DCHECK_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(),
4824 Assembler::target_address_at(call_target_address, 4905 Assembler::target_address_at(call_target_address,
4825 unoptimized_code)); 4906 unoptimized_code));
4826 return OSR_AFTER_STACK_CHECK; 4907 return OSR_AFTER_STACK_CHECK;
4827 } 4908 }
4828 4909
4829 4910
4830 } } // namespace v8::internal 4911 } } // namespace v8::internal
4831 4912
4832 #endif // V8_TARGET_ARCH_IA32 4913 #endif // V8_TARGET_ARCH_IA32
OLDNEW
« no previous file with comments | « src/hydrogen.cc ('k') | src/messages.js » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698