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

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

Issue 486213003: Move register conventions out of the IC classes. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: REBASE. Created 6 years, 4 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/x64/debug-x64.cc ('k') | src/x64/lithium-codegen-x64.cc » ('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_X64 7 #if V8_TARGET_ARCH_X64
8 8
9 #include "src/code-stubs.h" 9 #include "src/code-stubs.h"
10 #include "src/codegen.h" 10 #include "src/codegen.h"
(...skipping 1344 matching lines...) Expand 10 before | Expand all | Expand 10 after
1355 __ cmpp(ContextOperand(temp, Context::EXTENSION_INDEX), Immediate(0)); 1355 __ cmpp(ContextOperand(temp, Context::EXTENSION_INDEX), Immediate(0));
1356 __ j(not_equal, slow); 1356 __ j(not_equal, slow);
1357 // Load next context in chain. 1357 // Load next context in chain.
1358 __ movp(temp, ContextOperand(temp, Context::PREVIOUS_INDEX)); 1358 __ movp(temp, ContextOperand(temp, Context::PREVIOUS_INDEX));
1359 __ jmp(&next); 1359 __ jmp(&next);
1360 __ bind(&fast); 1360 __ bind(&fast);
1361 } 1361 }
1362 1362
1363 // All extension objects were empty and it is safe to use a global 1363 // All extension objects were empty and it is safe to use a global
1364 // load IC call. 1364 // load IC call.
1365 __ movp(LoadIC::ReceiverRegister(), GlobalObjectOperand()); 1365 __ movp(LoadConvention::ReceiverRegister(), GlobalObjectOperand());
1366 __ Move(LoadIC::NameRegister(), proxy->var()->name()); 1366 __ Move(LoadConvention::NameRegister(), proxy->var()->name());
1367 if (FLAG_vector_ics) { 1367 if (FLAG_vector_ics) {
1368 __ Move(LoadIC::SlotRegister(), 1368 __ Move(VectorLoadConvention::SlotRegister(),
1369 Smi::FromInt(proxy->VariableFeedbackSlot())); 1369 Smi::FromInt(proxy->VariableFeedbackSlot()));
1370 } 1370 }
1371 1371
1372 ContextualMode mode = (typeof_state == INSIDE_TYPEOF) 1372 ContextualMode mode = (typeof_state == INSIDE_TYPEOF)
1373 ? NOT_CONTEXTUAL 1373 ? NOT_CONTEXTUAL
1374 : CONTEXTUAL; 1374 : CONTEXTUAL;
1375 CallLoadIC(mode); 1375 CallLoadIC(mode);
1376 } 1376 }
1377 1377
1378 1378
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after
1441 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) { 1441 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) {
1442 // Record position before possible IC call. 1442 // Record position before possible IC call.
1443 SetSourcePosition(proxy->position()); 1443 SetSourcePosition(proxy->position());
1444 Variable* var = proxy->var(); 1444 Variable* var = proxy->var();
1445 1445
1446 // Three cases: global variables, lookup variables, and all other types of 1446 // Three cases: global variables, lookup variables, and all other types of
1447 // variables. 1447 // variables.
1448 switch (var->location()) { 1448 switch (var->location()) {
1449 case Variable::UNALLOCATED: { 1449 case Variable::UNALLOCATED: {
1450 Comment cmnt(masm_, "[ Global variable"); 1450 Comment cmnt(masm_, "[ Global variable");
1451 __ Move(LoadIC::NameRegister(), var->name()); 1451 __ Move(LoadConvention::NameRegister(), var->name());
1452 __ movp(LoadIC::ReceiverRegister(), GlobalObjectOperand()); 1452 __ movp(LoadConvention::ReceiverRegister(), GlobalObjectOperand());
1453 if (FLAG_vector_ics) { 1453 if (FLAG_vector_ics) {
1454 __ Move(LoadIC::SlotRegister(), 1454 __ Move(VectorLoadConvention::SlotRegister(),
1455 Smi::FromInt(proxy->VariableFeedbackSlot())); 1455 Smi::FromInt(proxy->VariableFeedbackSlot()));
1456 } 1456 }
1457 CallLoadIC(CONTEXTUAL); 1457 CallLoadIC(CONTEXTUAL);
1458 context()->Plug(rax); 1458 context()->Plug(rax);
1459 break; 1459 break;
1460 } 1460 }
1461 1461
1462 case Variable::PARAMETER: 1462 case Variable::PARAMETER:
1463 case Variable::LOCAL: 1463 case Variable::LOCAL:
1464 case Variable::CONTEXT: { 1464 case Variable::CONTEXT: {
(...skipping 194 matching lines...) Expand 10 before | Expand all | Expand 10 after
1659 switch (property->kind()) { 1659 switch (property->kind()) {
1660 case ObjectLiteral::Property::CONSTANT: 1660 case ObjectLiteral::Property::CONSTANT:
1661 UNREACHABLE(); 1661 UNREACHABLE();
1662 case ObjectLiteral::Property::MATERIALIZED_LITERAL: 1662 case ObjectLiteral::Property::MATERIALIZED_LITERAL:
1663 DCHECK(!CompileTimeValue::IsCompileTimeValue(value)); 1663 DCHECK(!CompileTimeValue::IsCompileTimeValue(value));
1664 // Fall through. 1664 // Fall through.
1665 case ObjectLiteral::Property::COMPUTED: 1665 case ObjectLiteral::Property::COMPUTED:
1666 if (key->value()->IsInternalizedString()) { 1666 if (key->value()->IsInternalizedString()) {
1667 if (property->emit_store()) { 1667 if (property->emit_store()) {
1668 VisitForAccumulatorValue(value); 1668 VisitForAccumulatorValue(value);
1669 DCHECK(StoreIC::ValueRegister().is(rax)); 1669 DCHECK(StoreConvention::ValueRegister().is(rax));
1670 __ Move(StoreIC::NameRegister(), key->value()); 1670 __ Move(StoreConvention::NameRegister(), key->value());
1671 __ movp(StoreIC::ReceiverRegister(), Operand(rsp, 0)); 1671 __ movp(StoreConvention::ReceiverRegister(), Operand(rsp, 0));
1672 CallStoreIC(key->LiteralFeedbackId()); 1672 CallStoreIC(key->LiteralFeedbackId());
1673 PrepareForBailoutForId(key->id(), NO_REGISTERS); 1673 PrepareForBailoutForId(key->id(), NO_REGISTERS);
1674 } else { 1674 } else {
1675 VisitForEffect(value); 1675 VisitForEffect(value);
1676 } 1676 }
1677 break; 1677 break;
1678 } 1678 }
1679 __ Push(Operand(rsp, 0)); // Duplicate receiver. 1679 __ Push(Operand(rsp, 0)); // Duplicate receiver.
1680 VisitForStackValue(key); 1680 VisitForStackValue(key);
1681 VisitForStackValue(value); 1681 VisitForStackValue(value);
(...skipping 158 matching lines...) Expand 10 before | Expand all | Expand 10 after
1840 1840
1841 // Evaluate LHS expression. 1841 // Evaluate LHS expression.
1842 switch (assign_type) { 1842 switch (assign_type) {
1843 case VARIABLE: 1843 case VARIABLE:
1844 // Nothing to do here. 1844 // Nothing to do here.
1845 break; 1845 break;
1846 case NAMED_PROPERTY: 1846 case NAMED_PROPERTY:
1847 if (expr->is_compound()) { 1847 if (expr->is_compound()) {
1848 // We need the receiver both on the stack and in the register. 1848 // We need the receiver both on the stack and in the register.
1849 VisitForStackValue(property->obj()); 1849 VisitForStackValue(property->obj());
1850 __ movp(LoadIC::ReceiverRegister(), Operand(rsp, 0)); 1850 __ movp(LoadConvention::ReceiverRegister(), Operand(rsp, 0));
1851 } else { 1851 } else {
1852 VisitForStackValue(property->obj()); 1852 VisitForStackValue(property->obj());
1853 } 1853 }
1854 break; 1854 break;
1855 case KEYED_PROPERTY: { 1855 case KEYED_PROPERTY: {
1856 if (expr->is_compound()) { 1856 if (expr->is_compound()) {
1857 VisitForStackValue(property->obj()); 1857 VisitForStackValue(property->obj());
1858 VisitForStackValue(property->key()); 1858 VisitForStackValue(property->key());
1859 __ movp(LoadIC::ReceiverRegister(), Operand(rsp, kPointerSize)); 1859 __ movp(LoadConvention::ReceiverRegister(), Operand(rsp, kPointerSize));
1860 __ movp(LoadIC::NameRegister(), Operand(rsp, 0)); 1860 __ movp(LoadConvention::NameRegister(), Operand(rsp, 0));
1861 } else { 1861 } else {
1862 VisitForStackValue(property->obj()); 1862 VisitForStackValue(property->obj());
1863 VisitForStackValue(property->key()); 1863 VisitForStackValue(property->key());
1864 } 1864 }
1865 break; 1865 break;
1866 } 1866 }
1867 } 1867 }
1868 1868
1869 // For compound assignments we need another deoptimization point after the 1869 // For compound assignments we need another deoptimization point after the
1870 // variable/property load. 1870 // variable/property load.
(...skipping 120 matching lines...) Expand 10 before | Expand all | Expand 10 after
1991 1991
1992 case Yield::DELEGATING: { 1992 case Yield::DELEGATING: {
1993 VisitForStackValue(expr->generator_object()); 1993 VisitForStackValue(expr->generator_object());
1994 1994
1995 // Initial stack layout is as follows: 1995 // Initial stack layout is as follows:
1996 // [sp + 1 * kPointerSize] iter 1996 // [sp + 1 * kPointerSize] iter
1997 // [sp + 0 * kPointerSize] g 1997 // [sp + 0 * kPointerSize] g
1998 1998
1999 Label l_catch, l_try, l_suspend, l_continuation, l_resume; 1999 Label l_catch, l_try, l_suspend, l_continuation, l_resume;
2000 Label l_next, l_call, l_loop; 2000 Label l_next, l_call, l_loop;
2001 Register load_receiver = LoadIC::ReceiverRegister(); 2001 Register load_receiver = LoadConvention::ReceiverRegister();
2002 Register load_name = LoadIC::NameRegister(); 2002 Register load_name = LoadConvention::NameRegister();
2003 2003
2004 // Initial send value is undefined. 2004 // Initial send value is undefined.
2005 __ LoadRoot(rax, Heap::kUndefinedValueRootIndex); 2005 __ LoadRoot(rax, Heap::kUndefinedValueRootIndex);
2006 __ jmp(&l_next); 2006 __ jmp(&l_next);
2007 2007
2008 // catch (e) { receiver = iter; f = 'throw'; arg = e; goto l_call; } 2008 // catch (e) { receiver = iter; f = 'throw'; arg = e; goto l_call; }
2009 __ bind(&l_catch); 2009 __ bind(&l_catch);
2010 handler_table()->set(expr->index(), Smi::FromInt(l_catch.pos())); 2010 handler_table()->set(expr->index(), Smi::FromInt(l_catch.pos()));
2011 __ LoadRoot(load_name, Heap::kthrow_stringRootIndex); // "throw" 2011 __ LoadRoot(load_name, Heap::kthrow_stringRootIndex); // "throw"
2012 __ Push(load_name); 2012 __ Push(load_name);
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
2049 2049
2050 __ LoadRoot(load_name, Heap::knext_stringRootIndex); 2050 __ LoadRoot(load_name, Heap::knext_stringRootIndex);
2051 __ Push(load_name); // "next" 2051 __ Push(load_name); // "next"
2052 __ Push(Operand(rsp, 2 * kPointerSize)); // iter 2052 __ Push(Operand(rsp, 2 * kPointerSize)); // iter
2053 __ Push(rax); // received 2053 __ Push(rax); // received
2054 2054
2055 // result = receiver[f](arg); 2055 // result = receiver[f](arg);
2056 __ bind(&l_call); 2056 __ bind(&l_call);
2057 __ movp(load_receiver, Operand(rsp, kPointerSize)); 2057 __ movp(load_receiver, Operand(rsp, kPointerSize));
2058 if (FLAG_vector_ics) { 2058 if (FLAG_vector_ics) {
2059 __ Move(LoadIC::SlotRegister(), 2059 __ Move(VectorLoadConvention::SlotRegister(),
2060 Smi::FromInt(expr->KeyedLoadFeedbackSlot())); 2060 Smi::FromInt(expr->KeyedLoadFeedbackSlot()));
2061 } 2061 }
2062 Handle<Code> ic = isolate()->builtins()->KeyedLoadIC_Initialize(); 2062 Handle<Code> ic = isolate()->builtins()->KeyedLoadIC_Initialize();
2063 CallIC(ic, TypeFeedbackId::None()); 2063 CallIC(ic, TypeFeedbackId::None());
2064 __ movp(rdi, rax); 2064 __ movp(rdi, rax);
2065 __ movp(Operand(rsp, 2 * kPointerSize), rdi); 2065 __ movp(Operand(rsp, 2 * kPointerSize), rdi);
2066 CallFunctionStub stub(isolate(), 1, CALL_AS_METHOD); 2066 CallFunctionStub stub(isolate(), 1, CALL_AS_METHOD);
2067 __ CallStub(&stub); 2067 __ CallStub(&stub);
2068 2068
2069 __ movp(rsi, Operand(rbp, StandardFrameConstants::kContextOffset)); 2069 __ movp(rsi, Operand(rbp, StandardFrameConstants::kContextOffset));
2070 __ Drop(1); // The function is still on the stack; drop it. 2070 __ Drop(1); // The function is still on the stack; drop it.
2071 2071
2072 // if (!result.done) goto l_try; 2072 // if (!result.done) goto l_try;
2073 __ bind(&l_loop); 2073 __ bind(&l_loop);
2074 __ Move(load_receiver, rax); 2074 __ Move(load_receiver, rax);
2075 __ Push(load_receiver); // save result 2075 __ Push(load_receiver); // save result
2076 __ LoadRoot(load_name, Heap::kdone_stringRootIndex); // "done" 2076 __ LoadRoot(load_name, Heap::kdone_stringRootIndex); // "done"
2077 if (FLAG_vector_ics) { 2077 if (FLAG_vector_ics) {
2078 __ Move(LoadIC::SlotRegister(), Smi::FromInt(expr->DoneFeedbackSlot())); 2078 __ Move(VectorLoadConvention::SlotRegister(),
2079 Smi::FromInt(expr->DoneFeedbackSlot()));
2079 } 2080 }
2080 CallLoadIC(NOT_CONTEXTUAL); // rax=result.done 2081 CallLoadIC(NOT_CONTEXTUAL); // rax=result.done
2081 Handle<Code> bool_ic = ToBooleanStub::GetUninitialized(isolate()); 2082 Handle<Code> bool_ic = ToBooleanStub::GetUninitialized(isolate());
2082 CallIC(bool_ic); 2083 CallIC(bool_ic);
2083 __ testp(result_register(), result_register()); 2084 __ testp(result_register(), result_register());
2084 __ j(zero, &l_try); 2085 __ j(zero, &l_try);
2085 2086
2086 // result.value 2087 // result.value
2087 __ Pop(load_receiver); // result 2088 __ Pop(load_receiver); // result
2088 __ LoadRoot(load_name, Heap::kvalue_stringRootIndex); // "value" 2089 __ LoadRoot(load_name, Heap::kvalue_stringRootIndex); // "value"
2089 if (FLAG_vector_ics) { 2090 if (FLAG_vector_ics) {
2090 __ Move(LoadIC::SlotRegister(), 2091 __ Move(VectorLoadConvention::SlotRegister(),
2091 Smi::FromInt(expr->ValueFeedbackSlot())); 2092 Smi::FromInt(expr->ValueFeedbackSlot()));
2092 } 2093 }
2093 CallLoadIC(NOT_CONTEXTUAL); // result.value in rax 2094 CallLoadIC(NOT_CONTEXTUAL); // result.value in rax
2094 context()->DropAndPlug(2, rax); // drop iter and g 2095 context()->DropAndPlug(2, rax); // drop iter and g
2095 break; 2096 break;
2096 } 2097 }
2097 } 2098 }
2098 } 2099 }
2099 2100
2100 2101
(...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after
2243 // Only the value field needs a write barrier, as the other values are in the 2244 // Only the value field needs a write barrier, as the other values are in the
2244 // root set. 2245 // root set.
2245 __ RecordWriteField(rax, JSGeneratorObject::kResultValuePropertyOffset, 2246 __ RecordWriteField(rax, JSGeneratorObject::kResultValuePropertyOffset,
2246 rcx, rdx, kDontSaveFPRegs); 2247 rcx, rdx, kDontSaveFPRegs);
2247 } 2248 }
2248 2249
2249 2250
2250 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) { 2251 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) {
2251 SetSourcePosition(prop->position()); 2252 SetSourcePosition(prop->position());
2252 Literal* key = prop->key()->AsLiteral(); 2253 Literal* key = prop->key()->AsLiteral();
2253 __ Move(LoadIC::NameRegister(), key->value()); 2254 __ Move(LoadConvention::NameRegister(), key->value());
2254 if (FLAG_vector_ics) { 2255 if (FLAG_vector_ics) {
2255 __ Move(LoadIC::SlotRegister(), Smi::FromInt(prop->PropertyFeedbackSlot())); 2256 __ Move(VectorLoadConvention::SlotRegister(),
2257 Smi::FromInt(prop->PropertyFeedbackSlot()));
2256 CallLoadIC(NOT_CONTEXTUAL); 2258 CallLoadIC(NOT_CONTEXTUAL);
2257 } else { 2259 } else {
2258 CallLoadIC(NOT_CONTEXTUAL, prop->PropertyFeedbackId()); 2260 CallLoadIC(NOT_CONTEXTUAL, prop->PropertyFeedbackId());
2259 } 2261 }
2260 } 2262 }
2261 2263
2262 2264
2263 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) { 2265 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) {
2264 SetSourcePosition(prop->position()); 2266 SetSourcePosition(prop->position());
2265 Handle<Code> ic = isolate()->builtins()->KeyedLoadIC_Initialize(); 2267 Handle<Code> ic = isolate()->builtins()->KeyedLoadIC_Initialize();
2266 if (FLAG_vector_ics) { 2268 if (FLAG_vector_ics) {
2267 __ Move(LoadIC::SlotRegister(), Smi::FromInt(prop->PropertyFeedbackSlot())); 2269 __ Move(VectorLoadConvention::SlotRegister(),
2270 Smi::FromInt(prop->PropertyFeedbackSlot()));
2268 CallIC(ic); 2271 CallIC(ic);
2269 } else { 2272 } else {
2270 CallIC(ic, prop->PropertyFeedbackId()); 2273 CallIC(ic, prop->PropertyFeedbackId());
2271 } 2274 }
2272 } 2275 }
2273 2276
2274 2277
2275 void FullCodeGenerator::EmitInlineSmiBinaryOp(BinaryOperation* expr, 2278 void FullCodeGenerator::EmitInlineSmiBinaryOp(BinaryOperation* expr,
2276 Token::Value op, 2279 Token::Value op,
2277 OverwriteMode mode, 2280 OverwriteMode mode,
(...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after
2362 switch (assign_type) { 2365 switch (assign_type) {
2363 case VARIABLE: { 2366 case VARIABLE: {
2364 Variable* var = expr->AsVariableProxy()->var(); 2367 Variable* var = expr->AsVariableProxy()->var();
2365 EffectContext context(this); 2368 EffectContext context(this);
2366 EmitVariableAssignment(var, Token::ASSIGN); 2369 EmitVariableAssignment(var, Token::ASSIGN);
2367 break; 2370 break;
2368 } 2371 }
2369 case NAMED_PROPERTY: { 2372 case NAMED_PROPERTY: {
2370 __ Push(rax); // Preserve value. 2373 __ Push(rax); // Preserve value.
2371 VisitForAccumulatorValue(prop->obj()); 2374 VisitForAccumulatorValue(prop->obj());
2372 __ Move(StoreIC::ReceiverRegister(), rax); 2375 __ Move(StoreConvention::ReceiverRegister(), rax);
2373 __ Pop(StoreIC::ValueRegister()); // Restore value. 2376 __ Pop(StoreConvention::ValueRegister()); // Restore value.
2374 __ Move(StoreIC::NameRegister(), prop->key()->AsLiteral()->value()); 2377 __ Move(StoreConvention::NameRegister(),
2378 prop->key()->AsLiteral()->value());
2375 CallStoreIC(); 2379 CallStoreIC();
2376 break; 2380 break;
2377 } 2381 }
2378 case KEYED_PROPERTY: { 2382 case KEYED_PROPERTY: {
2379 __ Push(rax); // Preserve value. 2383 __ Push(rax); // Preserve value.
2380 VisitForStackValue(prop->obj()); 2384 VisitForStackValue(prop->obj());
2381 VisitForAccumulatorValue(prop->key()); 2385 VisitForAccumulatorValue(prop->key());
2382 __ Move(KeyedStoreIC::NameRegister(), rax); 2386 __ Move(StoreConvention::NameRegister(), rax);
2383 __ Pop(KeyedStoreIC::ReceiverRegister()); 2387 __ Pop(StoreConvention::ReceiverRegister());
2384 __ Pop(KeyedStoreIC::ValueRegister()); // Restore value. 2388 __ Pop(StoreConvention::ValueRegister()); // Restore value.
2385 Handle<Code> ic = strict_mode() == SLOPPY 2389 Handle<Code> ic = strict_mode() == SLOPPY
2386 ? isolate()->builtins()->KeyedStoreIC_Initialize() 2390 ? isolate()->builtins()->KeyedStoreIC_Initialize()
2387 : isolate()->builtins()->KeyedStoreIC_Initialize_Strict(); 2391 : isolate()->builtins()->KeyedStoreIC_Initialize_Strict();
2388 CallIC(ic); 2392 CallIC(ic);
2389 break; 2393 break;
2390 } 2394 }
2391 } 2395 }
2392 context()->Plug(rax); 2396 context()->Plug(rax);
2393 } 2397 }
2394 2398
2395 2399
2396 void FullCodeGenerator::EmitStoreToStackLocalOrContextSlot( 2400 void FullCodeGenerator::EmitStoreToStackLocalOrContextSlot(
2397 Variable* var, MemOperand location) { 2401 Variable* var, MemOperand location) {
2398 __ movp(location, rax); 2402 __ movp(location, rax);
2399 if (var->IsContextSlot()) { 2403 if (var->IsContextSlot()) {
2400 __ movp(rdx, rax); 2404 __ movp(rdx, rax);
2401 __ RecordWriteContextSlot( 2405 __ RecordWriteContextSlot(
2402 rcx, Context::SlotOffset(var->index()), rdx, rbx, kDontSaveFPRegs); 2406 rcx, Context::SlotOffset(var->index()), rdx, rbx, kDontSaveFPRegs);
2403 } 2407 }
2404 } 2408 }
2405 2409
2406 2410
2407 void FullCodeGenerator::EmitVariableAssignment(Variable* var, 2411 void FullCodeGenerator::EmitVariableAssignment(Variable* var,
2408 Token::Value op) { 2412 Token::Value op) {
2409 if (var->IsUnallocated()) { 2413 if (var->IsUnallocated()) {
2410 // Global var, const, or let. 2414 // Global var, const, or let.
2411 __ Move(StoreIC::NameRegister(), var->name()); 2415 __ Move(StoreConvention::NameRegister(), var->name());
2412 __ movp(StoreIC::ReceiverRegister(), GlobalObjectOperand()); 2416 __ movp(StoreConvention::ReceiverRegister(), GlobalObjectOperand());
2413 CallStoreIC(); 2417 CallStoreIC();
2414 2418
2415 } else if (op == Token::INIT_CONST_LEGACY) { 2419 } else if (op == Token::INIT_CONST_LEGACY) {
2416 // Const initializers need a write barrier. 2420 // Const initializers need a write barrier.
2417 DCHECK(!var->IsParameter()); // No const parameters. 2421 DCHECK(!var->IsParameter()); // No const parameters.
2418 if (var->IsLookupSlot()) { 2422 if (var->IsLookupSlot()) {
2419 __ Push(rax); 2423 __ Push(rax);
2420 __ Push(rsi); 2424 __ Push(rsi);
2421 __ Push(var->name()); 2425 __ Push(var->name());
2422 __ CallRuntime(Runtime::kInitializeLegacyConstLookupSlot, 3); 2426 __ CallRuntime(Runtime::kInitializeLegacyConstLookupSlot, 3);
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
2472 2476
2473 2477
2474 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) { 2478 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) {
2475 // Assignment to a property, using a named store IC. 2479 // Assignment to a property, using a named store IC.
2476 Property* prop = expr->target()->AsProperty(); 2480 Property* prop = expr->target()->AsProperty();
2477 DCHECK(prop != NULL); 2481 DCHECK(prop != NULL);
2478 DCHECK(prop->key()->IsLiteral()); 2482 DCHECK(prop->key()->IsLiteral());
2479 2483
2480 // Record source code position before IC call. 2484 // Record source code position before IC call.
2481 SetSourcePosition(expr->position()); 2485 SetSourcePosition(expr->position());
2482 __ Move(StoreIC::NameRegister(), prop->key()->AsLiteral()->value()); 2486 __ Move(StoreConvention::NameRegister(), prop->key()->AsLiteral()->value());
2483 __ Pop(StoreIC::ReceiverRegister()); 2487 __ Pop(StoreConvention::ReceiverRegister());
2484 CallStoreIC(expr->AssignmentFeedbackId()); 2488 CallStoreIC(expr->AssignmentFeedbackId());
2485 2489
2486 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2490 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2487 context()->Plug(rax); 2491 context()->Plug(rax);
2488 } 2492 }
2489 2493
2490 2494
2491 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) { 2495 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) {
2492 // Assignment to a property, using a keyed store IC. 2496 // Assignment to a property, using a keyed store IC.
2493 2497
2494 __ Pop(KeyedStoreIC::NameRegister()); // Key. 2498 __ Pop(StoreConvention::NameRegister()); // Key.
2495 __ Pop(KeyedStoreIC::ReceiverRegister()); 2499 __ Pop(StoreConvention::ReceiverRegister());
2496 DCHECK(KeyedStoreIC::ValueRegister().is(rax)); 2500 DCHECK(StoreConvention::ValueRegister().is(rax));
2497 // Record source code position before IC call. 2501 // Record source code position before IC call.
2498 SetSourcePosition(expr->position()); 2502 SetSourcePosition(expr->position());
2499 Handle<Code> ic = strict_mode() == SLOPPY 2503 Handle<Code> ic = strict_mode() == SLOPPY
2500 ? isolate()->builtins()->KeyedStoreIC_Initialize() 2504 ? isolate()->builtins()->KeyedStoreIC_Initialize()
2501 : isolate()->builtins()->KeyedStoreIC_Initialize_Strict(); 2505 : isolate()->builtins()->KeyedStoreIC_Initialize_Strict();
2502 CallIC(ic, expr->AssignmentFeedbackId()); 2506 CallIC(ic, expr->AssignmentFeedbackId());
2503 2507
2504 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2508 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2505 context()->Plug(rax); 2509 context()->Plug(rax);
2506 } 2510 }
2507 2511
2508 2512
2509 void FullCodeGenerator::VisitProperty(Property* expr) { 2513 void FullCodeGenerator::VisitProperty(Property* expr) {
2510 Comment cmnt(masm_, "[ Property"); 2514 Comment cmnt(masm_, "[ Property");
2511 Expression* key = expr->key(); 2515 Expression* key = expr->key();
2512 2516
2513 if (key->IsPropertyName()) { 2517 if (key->IsPropertyName()) {
2514 VisitForAccumulatorValue(expr->obj()); 2518 VisitForAccumulatorValue(expr->obj());
2515 DCHECK(!rax.is(LoadIC::ReceiverRegister())); 2519 DCHECK(!rax.is(LoadConvention::ReceiverRegister()));
2516 __ movp(LoadIC::ReceiverRegister(), rax); 2520 __ movp(LoadConvention::ReceiverRegister(), rax);
2517 EmitNamedPropertyLoad(expr); 2521 EmitNamedPropertyLoad(expr);
2518 PrepareForBailoutForId(expr->LoadId(), TOS_REG); 2522 PrepareForBailoutForId(expr->LoadId(), TOS_REG);
2519 context()->Plug(rax); 2523 context()->Plug(rax);
2520 } else { 2524 } else {
2521 VisitForStackValue(expr->obj()); 2525 VisitForStackValue(expr->obj());
2522 VisitForAccumulatorValue(expr->key()); 2526 VisitForAccumulatorValue(expr->key());
2523 __ Move(LoadIC::NameRegister(), rax); 2527 __ Move(LoadConvention::NameRegister(), rax);
2524 __ Pop(LoadIC::ReceiverRegister()); 2528 __ Pop(LoadConvention::ReceiverRegister());
2525 EmitKeyedPropertyLoad(expr); 2529 EmitKeyedPropertyLoad(expr);
2526 context()->Plug(rax); 2530 context()->Plug(rax);
2527 } 2531 }
2528 } 2532 }
2529 2533
2530 2534
2531 void FullCodeGenerator::CallIC(Handle<Code> code, 2535 void FullCodeGenerator::CallIC(Handle<Code> code,
2532 TypeFeedbackId ast_id) { 2536 TypeFeedbackId ast_id) {
2533 ic_total_count_++; 2537 ic_total_count_++;
2534 __ call(code, RelocInfo::CODE_TARGET, ast_id); 2538 __ call(code, RelocInfo::CODE_TARGET, ast_id);
(...skipping 12 matching lines...) Expand all
2547 { StackValueContext context(this); 2551 { StackValueContext context(this);
2548 EmitVariableLoad(callee->AsVariableProxy()); 2552 EmitVariableLoad(callee->AsVariableProxy());
2549 PrepareForBailout(callee, NO_REGISTERS); 2553 PrepareForBailout(callee, NO_REGISTERS);
2550 } 2554 }
2551 // Push undefined as receiver. This is patched in the method prologue if it 2555 // Push undefined as receiver. This is patched in the method prologue if it
2552 // is a sloppy mode method. 2556 // is a sloppy mode method.
2553 __ Push(isolate()->factory()->undefined_value()); 2557 __ Push(isolate()->factory()->undefined_value());
2554 } else { 2558 } else {
2555 // Load the function from the receiver. 2559 // Load the function from the receiver.
2556 DCHECK(callee->IsProperty()); 2560 DCHECK(callee->IsProperty());
2557 __ movp(LoadIC::ReceiverRegister(), Operand(rsp, 0)); 2561 __ movp(LoadConvention::ReceiverRegister(), Operand(rsp, 0));
2558 EmitNamedPropertyLoad(callee->AsProperty()); 2562 EmitNamedPropertyLoad(callee->AsProperty());
2559 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG); 2563 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG);
2560 // Push the target function under the receiver. 2564 // Push the target function under the receiver.
2561 __ Push(Operand(rsp, 0)); 2565 __ Push(Operand(rsp, 0));
2562 __ movp(Operand(rsp, kPointerSize), rax); 2566 __ movp(Operand(rsp, kPointerSize), rax);
2563 } 2567 }
2564 2568
2565 EmitCall(expr, call_type); 2569 EmitCall(expr, call_type);
2566 } 2570 }
2567 2571
2568 2572
2569 // Common code for calls using the IC. 2573 // Common code for calls using the IC.
2570 void FullCodeGenerator::EmitKeyedCallWithLoadIC(Call* expr, 2574 void FullCodeGenerator::EmitKeyedCallWithLoadIC(Call* expr,
2571 Expression* key) { 2575 Expression* key) {
2572 // Load the key. 2576 // Load the key.
2573 VisitForAccumulatorValue(key); 2577 VisitForAccumulatorValue(key);
2574 2578
2575 Expression* callee = expr->expression(); 2579 Expression* callee = expr->expression();
2576 2580
2577 // Load the function from the receiver. 2581 // Load the function from the receiver.
2578 DCHECK(callee->IsProperty()); 2582 DCHECK(callee->IsProperty());
2579 __ movp(LoadIC::ReceiverRegister(), Operand(rsp, 0)); 2583 __ movp(LoadConvention::ReceiverRegister(), Operand(rsp, 0));
2580 __ Move(LoadIC::NameRegister(), rax); 2584 __ Move(LoadConvention::NameRegister(), rax);
2581 EmitKeyedPropertyLoad(callee->AsProperty()); 2585 EmitKeyedPropertyLoad(callee->AsProperty());
2582 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG); 2586 PrepareForBailoutForId(callee->AsProperty()->LoadId(), TOS_REG);
2583 2587
2584 // Push the target function under the receiver. 2588 // Push the target function under the receiver.
2585 __ Push(Operand(rsp, 0)); 2589 __ Push(Operand(rsp, 0));
2586 __ movp(Operand(rsp, kPointerSize), rax); 2590 __ movp(Operand(rsp, kPointerSize), rax);
2587 2591
2588 EmitCall(expr, CallIC::METHOD); 2592 EmitCall(expr, CallIC::METHOD);
2589 } 2593 }
2590 2594
(...skipping 1457 matching lines...) Expand 10 before | Expand all | Expand 10 after
4048 Comment cmnt(masm_, "[ CallRuntime"); 4052 Comment cmnt(masm_, "[ CallRuntime");
4049 ZoneList<Expression*>* args = expr->arguments(); 4053 ZoneList<Expression*>* args = expr->arguments();
4050 int arg_count = args->length(); 4054 int arg_count = args->length();
4051 4055
4052 if (expr->is_jsruntime()) { 4056 if (expr->is_jsruntime()) {
4053 // Push the builtins object as receiver. 4057 // Push the builtins object as receiver.
4054 __ movp(rax, GlobalObjectOperand()); 4058 __ movp(rax, GlobalObjectOperand());
4055 __ Push(FieldOperand(rax, GlobalObject::kBuiltinsOffset)); 4059 __ Push(FieldOperand(rax, GlobalObject::kBuiltinsOffset));
4056 4060
4057 // Load the function from the receiver. 4061 // Load the function from the receiver.
4058 __ movp(LoadIC::ReceiverRegister(), Operand(rsp, 0)); 4062 __ movp(LoadConvention::ReceiverRegister(), Operand(rsp, 0));
4059 __ Move(LoadIC::NameRegister(), expr->name()); 4063 __ Move(LoadConvention::NameRegister(), expr->name());
4060 if (FLAG_vector_ics) { 4064 if (FLAG_vector_ics) {
4061 __ Move(LoadIC::SlotRegister(), 4065 __ Move(VectorLoadConvention::SlotRegister(),
4062 Smi::FromInt(expr->CallRuntimeFeedbackSlot())); 4066 Smi::FromInt(expr->CallRuntimeFeedbackSlot()));
4063 CallLoadIC(NOT_CONTEXTUAL); 4067 CallLoadIC(NOT_CONTEXTUAL);
4064 } else { 4068 } else {
4065 CallLoadIC(NOT_CONTEXTUAL, expr->CallRuntimeFeedbackId()); 4069 CallLoadIC(NOT_CONTEXTUAL, expr->CallRuntimeFeedbackId());
4066 } 4070 }
4067 4071
4068 // Push the target function under the receiver. 4072 // Push the target function under the receiver.
4069 __ Push(Operand(rsp, 0)); 4073 __ Push(Operand(rsp, 0));
4070 __ movp(Operand(rsp, kPointerSize), rax); 4074 __ movp(Operand(rsp, kPointerSize), rax);
4071 4075
(...skipping 162 matching lines...) Expand 10 before | Expand all | Expand 10 after
4234 DCHECK(expr->expression()->AsVariableProxy()->var() != NULL); 4238 DCHECK(expr->expression()->AsVariableProxy()->var() != NULL);
4235 AccumulatorValueContext context(this); 4239 AccumulatorValueContext context(this);
4236 EmitVariableLoad(expr->expression()->AsVariableProxy()); 4240 EmitVariableLoad(expr->expression()->AsVariableProxy());
4237 } else { 4241 } else {
4238 // Reserve space for result of postfix operation. 4242 // Reserve space for result of postfix operation.
4239 if (expr->is_postfix() && !context()->IsEffect()) { 4243 if (expr->is_postfix() && !context()->IsEffect()) {
4240 __ Push(Smi::FromInt(0)); 4244 __ Push(Smi::FromInt(0));
4241 } 4245 }
4242 if (assign_type == NAMED_PROPERTY) { 4246 if (assign_type == NAMED_PROPERTY) {
4243 VisitForStackValue(prop->obj()); 4247 VisitForStackValue(prop->obj());
4244 __ movp(LoadIC::ReceiverRegister(), Operand(rsp, 0)); 4248 __ movp(LoadConvention::ReceiverRegister(), Operand(rsp, 0));
4245 EmitNamedPropertyLoad(prop); 4249 EmitNamedPropertyLoad(prop);
4246 } else { 4250 } else {
4247 VisitForStackValue(prop->obj()); 4251 VisitForStackValue(prop->obj());
4248 VisitForStackValue(prop->key()); 4252 VisitForStackValue(prop->key());
4249 // Leave receiver on stack 4253 // Leave receiver on stack
4250 __ movp(LoadIC::ReceiverRegister(), Operand(rsp, kPointerSize)); 4254 __ movp(LoadConvention::ReceiverRegister(), Operand(rsp, kPointerSize));
4251 // Copy of key, needed for later store. 4255 // Copy of key, needed for later store.
4252 __ movp(LoadIC::NameRegister(), Operand(rsp, 0)); 4256 __ movp(LoadConvention::NameRegister(), Operand(rsp, 0));
4253 EmitKeyedPropertyLoad(prop); 4257 EmitKeyedPropertyLoad(prop);
4254 } 4258 }
4255 } 4259 }
4256 4260
4257 // We need a second deoptimization point after loading the value 4261 // We need a second deoptimization point after loading the value
4258 // in case evaluating the property load my have a side effect. 4262 // in case evaluating the property load my have a side effect.
4259 if (assign_type == VARIABLE) { 4263 if (assign_type == VARIABLE) {
4260 PrepareForBailout(expr->expression(), TOS_REG); 4264 PrepareForBailout(expr->expression(), TOS_REG);
4261 } else { 4265 } else {
4262 PrepareForBailoutForId(prop->LoadId(), TOS_REG); 4266 PrepareForBailoutForId(prop->LoadId(), TOS_REG);
(...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after
4354 } 4358 }
4355 } else { 4359 } else {
4356 // Perform the assignment as if via '='. 4360 // Perform the assignment as if via '='.
4357 EmitVariableAssignment(expr->expression()->AsVariableProxy()->var(), 4361 EmitVariableAssignment(expr->expression()->AsVariableProxy()->var(),
4358 Token::ASSIGN); 4362 Token::ASSIGN);
4359 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 4363 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
4360 context()->Plug(rax); 4364 context()->Plug(rax);
4361 } 4365 }
4362 break; 4366 break;
4363 case NAMED_PROPERTY: { 4367 case NAMED_PROPERTY: {
4364 __ Move(StoreIC::NameRegister(), prop->key()->AsLiteral()->value()); 4368 __ Move(StoreConvention::NameRegister(),
4365 __ Pop(StoreIC::ReceiverRegister()); 4369 prop->key()->AsLiteral()->value());
4370 __ Pop(StoreConvention::ReceiverRegister());
4366 CallStoreIC(expr->CountStoreFeedbackId()); 4371 CallStoreIC(expr->CountStoreFeedbackId());
4367 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 4372 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
4368 if (expr->is_postfix()) { 4373 if (expr->is_postfix()) {
4369 if (!context()->IsEffect()) { 4374 if (!context()->IsEffect()) {
4370 context()->PlugTOS(); 4375 context()->PlugTOS();
4371 } 4376 }
4372 } else { 4377 } else {
4373 context()->Plug(rax); 4378 context()->Plug(rax);
4374 } 4379 }
4375 break; 4380 break;
4376 } 4381 }
4377 case KEYED_PROPERTY: { 4382 case KEYED_PROPERTY: {
4378 __ Pop(KeyedStoreIC::NameRegister()); 4383 __ Pop(StoreConvention::NameRegister());
4379 __ Pop(KeyedStoreIC::ReceiverRegister()); 4384 __ Pop(StoreConvention::ReceiverRegister());
4380 Handle<Code> ic = strict_mode() == SLOPPY 4385 Handle<Code> ic = strict_mode() == SLOPPY
4381 ? isolate()->builtins()->KeyedStoreIC_Initialize() 4386 ? isolate()->builtins()->KeyedStoreIC_Initialize()
4382 : isolate()->builtins()->KeyedStoreIC_Initialize_Strict(); 4387 : isolate()->builtins()->KeyedStoreIC_Initialize_Strict();
4383 CallIC(ic, expr->CountStoreFeedbackId()); 4388 CallIC(ic, expr->CountStoreFeedbackId());
4384 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 4389 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
4385 if (expr->is_postfix()) { 4390 if (expr->is_postfix()) {
4386 if (!context()->IsEffect()) { 4391 if (!context()->IsEffect()) {
4387 context()->PlugTOS(); 4392 context()->PlugTOS();
4388 } 4393 }
4389 } else { 4394 } else {
4390 context()->Plug(rax); 4395 context()->Plug(rax);
4391 } 4396 }
4392 break; 4397 break;
4393 } 4398 }
4394 } 4399 }
4395 } 4400 }
4396 4401
4397 4402
4398 void FullCodeGenerator::VisitForTypeofValue(Expression* expr) { 4403 void FullCodeGenerator::VisitForTypeofValue(Expression* expr) {
4399 VariableProxy* proxy = expr->AsVariableProxy(); 4404 VariableProxy* proxy = expr->AsVariableProxy();
4400 DCHECK(!context()->IsEffect()); 4405 DCHECK(!context()->IsEffect());
4401 DCHECK(!context()->IsTest()); 4406 DCHECK(!context()->IsTest());
4402 4407
4403 if (proxy != NULL && proxy->var()->IsUnallocated()) { 4408 if (proxy != NULL && proxy->var()->IsUnallocated()) {
4404 Comment cmnt(masm_, "[ Global variable"); 4409 Comment cmnt(masm_, "[ Global variable");
4405 __ Move(LoadIC::NameRegister(), proxy->name()); 4410 __ Move(LoadConvention::NameRegister(), proxy->name());
4406 __ movp(LoadIC::ReceiverRegister(), GlobalObjectOperand()); 4411 __ movp(LoadConvention::ReceiverRegister(), GlobalObjectOperand());
4407 if (FLAG_vector_ics) { 4412 if (FLAG_vector_ics) {
4408 __ Move(LoadIC::SlotRegister(), 4413 __ Move(VectorLoadConvention::SlotRegister(),
4409 Smi::FromInt(proxy->VariableFeedbackSlot())); 4414 Smi::FromInt(proxy->VariableFeedbackSlot()));
4410 } 4415 }
4411 // Use a regular load, not a contextual load, to avoid a reference 4416 // Use a regular load, not a contextual load, to avoid a reference
4412 // error. 4417 // error.
4413 CallLoadIC(NOT_CONTEXTUAL); 4418 CallLoadIC(NOT_CONTEXTUAL);
4414 PrepareForBailout(expr, TOS_REG); 4419 PrepareForBailout(expr, TOS_REG);
4415 context()->Plug(rax); 4420 context()->Plug(rax);
4416 } else if (proxy != NULL && proxy->var()->IsLookupSlot()) { 4421 } else if (proxy != NULL && proxy->var()->IsLookupSlot()) {
4417 Comment cmnt(masm_, "[ Lookup slot"); 4422 Comment cmnt(masm_, "[ Lookup slot");
4418 Label done, slow; 4423 Label done, slow;
(...skipping 412 matching lines...) Expand 10 before | Expand all | Expand 10 after
4831 DCHECK_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(), 4836 DCHECK_EQ(isolate->builtins()->OsrAfterStackCheck()->entry(),
4832 Assembler::target_address_at(call_target_address, 4837 Assembler::target_address_at(call_target_address,
4833 unoptimized_code)); 4838 unoptimized_code));
4834 return OSR_AFTER_STACK_CHECK; 4839 return OSR_AFTER_STACK_CHECK;
4835 } 4840 }
4836 4841
4837 4842
4838 } } // namespace v8::internal 4843 } } // namespace v8::internal
4839 4844
4840 #endif // V8_TARGET_ARCH_X64 4845 #endif // V8_TARGET_ARCH_X64
OLDNEW
« no previous file with comments | « src/x64/debug-x64.cc ('k') | src/x64/lithium-codegen-x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698