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

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

Issue 2363513003: [fullcodegen] Refactor code that calls store ICs. (Closed)
Patch Set: Created 4 years, 2 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
« no previous file with comments | « src/full-codegen/full-codegen.cc ('k') | src/full-codegen/mips/full-codegen-mips.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 #if V8_TARGET_ARCH_IA32 5 #if V8_TARGET_ARCH_IA32
6 6
7 #include "src/full-codegen/full-codegen.h" 7 #include "src/full-codegen/full-codegen.h"
8 #include "src/ast/compile-time-value.h" 8 #include "src/ast/compile-time-value.h"
9 #include "src/ast/scopes.h" 9 #include "src/ast/scopes.h"
10 #include "src/code-factory.h" 10 #include "src/code-factory.h"
(...skipping 1074 matching lines...) Expand 10 before | Expand all | Expand 10 after
1085 PrepareForBailoutForId(stmt->ExitId(), BailoutState::NO_REGISTERS); 1085 PrepareForBailoutForId(stmt->ExitId(), BailoutState::NO_REGISTERS);
1086 __ bind(&exit); 1086 __ bind(&exit);
1087 decrement_loop_depth(); 1087 decrement_loop_depth();
1088 } 1088 }
1089 1089
1090 1090
1091 void FullCodeGenerator::EmitSetHomeObject(Expression* initializer, int offset, 1091 void FullCodeGenerator::EmitSetHomeObject(Expression* initializer, int offset,
1092 FeedbackVectorSlot slot) { 1092 FeedbackVectorSlot slot) {
1093 DCHECK(NeedsHomeObject(initializer)); 1093 DCHECK(NeedsHomeObject(initializer));
1094 __ mov(StoreDescriptor::ReceiverRegister(), Operand(esp, 0)); 1094 __ mov(StoreDescriptor::ReceiverRegister(), Operand(esp, 0));
1095 __ mov(StoreDescriptor::NameRegister(),
1096 Immediate(isolate()->factory()->home_object_symbol()));
1097 __ mov(StoreDescriptor::ValueRegister(), Operand(esp, offset * kPointerSize)); 1095 __ mov(StoreDescriptor::ValueRegister(), Operand(esp, offset * kPointerSize));
1098 EmitLoadStoreICSlot(slot); 1096 CallStoreIC(slot, isolate()->factory()->home_object_symbol());
1099 CallStoreIC();
1100 } 1097 }
1101 1098
1102 1099
1103 void FullCodeGenerator::EmitSetHomeObjectAccumulator(Expression* initializer, 1100 void FullCodeGenerator::EmitSetHomeObjectAccumulator(Expression* initializer,
1104 int offset, 1101 int offset,
1105 FeedbackVectorSlot slot) { 1102 FeedbackVectorSlot slot) {
1106 DCHECK(NeedsHomeObject(initializer)); 1103 DCHECK(NeedsHomeObject(initializer));
1107 __ mov(StoreDescriptor::ReceiverRegister(), eax); 1104 __ mov(StoreDescriptor::ReceiverRegister(), eax);
1108 __ mov(StoreDescriptor::NameRegister(),
1109 Immediate(isolate()->factory()->home_object_symbol()));
1110 __ mov(StoreDescriptor::ValueRegister(), Operand(esp, offset * kPointerSize)); 1105 __ mov(StoreDescriptor::ValueRegister(), Operand(esp, offset * kPointerSize));
1111 EmitLoadStoreICSlot(slot); 1106 CallStoreIC(slot, isolate()->factory()->home_object_symbol());
1112 CallStoreIC();
1113 } 1107 }
1114 1108
1115 1109
1116 void FullCodeGenerator::EmitLoadGlobalCheckExtensions(VariableProxy* proxy, 1110 void FullCodeGenerator::EmitLoadGlobalCheckExtensions(VariableProxy* proxy,
1117 TypeofMode typeof_mode, 1111 TypeofMode typeof_mode,
1118 Label* slow) { 1112 Label* slow) {
1119 Register context = esi; 1113 Register context = esi;
1120 Register temp = edx; 1114 Register temp = edx;
1121 1115
1122 int to_check = scope()->ContextChainLengthUntilOutermostSloppyEval(); 1116 int to_check = scope()->ContextChainLengthUntilOutermostSloppyEval();
(...skipping 214 matching lines...) Expand 10 before | Expand all | Expand 10 after
1337 DCHECK(!CompileTimeValue::IsCompileTimeValue(value)); 1331 DCHECK(!CompileTimeValue::IsCompileTimeValue(value));
1338 // Fall through. 1332 // Fall through.
1339 case ObjectLiteral::Property::COMPUTED: 1333 case ObjectLiteral::Property::COMPUTED:
1340 // It is safe to use [[Put]] here because the boilerplate already 1334 // It is safe to use [[Put]] here because the boilerplate already
1341 // contains computed properties with an uninitialized value. 1335 // contains computed properties with an uninitialized value.
1342 if (key->IsStringLiteral()) { 1336 if (key->IsStringLiteral()) {
1343 DCHECK(key->IsPropertyName()); 1337 DCHECK(key->IsPropertyName());
1344 if (property->emit_store()) { 1338 if (property->emit_store()) {
1345 VisitForAccumulatorValue(value); 1339 VisitForAccumulatorValue(value);
1346 DCHECK(StoreDescriptor::ValueRegister().is(eax)); 1340 DCHECK(StoreDescriptor::ValueRegister().is(eax));
1347 __ mov(StoreDescriptor::NameRegister(), Immediate(key->value()));
1348 __ mov(StoreDescriptor::ReceiverRegister(), Operand(esp, 0)); 1341 __ mov(StoreDescriptor::ReceiverRegister(), Operand(esp, 0));
1349 EmitLoadStoreICSlot(property->GetSlot(0)); 1342 CallStoreIC(property->GetSlot(0), key->value());
1350 CallStoreIC();
1351 PrepareForBailoutForId(key->id(), BailoutState::NO_REGISTERS); 1343 PrepareForBailoutForId(key->id(), BailoutState::NO_REGISTERS);
1352 if (NeedsHomeObject(value)) { 1344 if (NeedsHomeObject(value)) {
1353 EmitSetHomeObjectAccumulator(value, 0, property->GetSlot(1)); 1345 EmitSetHomeObjectAccumulator(value, 0, property->GetSlot(1));
1354 } 1346 }
1355 } else { 1347 } else {
1356 VisitForEffect(value); 1348 VisitForEffect(value);
1357 } 1349 }
1358 break; 1350 break;
1359 } 1351 }
1360 PushOperand(Operand(esp, 0)); // Duplicate receiver. 1352 PushOperand(Operand(esp, 0)); // Duplicate receiver.
(...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after
1531 1523
1532 if (!result_saved) { 1524 if (!result_saved) {
1533 PushOperand(eax); // array literal. 1525 PushOperand(eax); // array literal.
1534 result_saved = true; 1526 result_saved = true;
1535 } 1527 }
1536 VisitForAccumulatorValue(subexpr); 1528 VisitForAccumulatorValue(subexpr);
1537 1529
1538 __ mov(StoreDescriptor::NameRegister(), 1530 __ mov(StoreDescriptor::NameRegister(),
1539 Immediate(Smi::FromInt(array_index))); 1531 Immediate(Smi::FromInt(array_index)));
1540 __ mov(StoreDescriptor::ReceiverRegister(), Operand(esp, 0)); 1532 __ mov(StoreDescriptor::ReceiverRegister(), Operand(esp, 0));
1541 EmitLoadStoreICSlot(expr->LiteralFeedbackSlot()); 1533 CallKeyedStoreIC(expr->LiteralFeedbackSlot());
1542 CallKeyedStoreIC();
1543 PrepareForBailoutForId(expr->GetIdForElement(array_index), 1534 PrepareForBailoutForId(expr->GetIdForElement(array_index),
1544 BailoutState::NO_REGISTERS); 1535 BailoutState::NO_REGISTERS);
1545 } 1536 }
1546 1537
1547 if (result_saved) { 1538 if (result_saved) {
1548 context()->PlugTOS(); 1539 context()->PlugTOS();
1549 } else { 1540 } else {
1550 context()->Plug(eax); 1541 context()->Plug(eax);
1551 } 1542 }
1552 } 1543 }
(...skipping 402 matching lines...) Expand 10 before | Expand all | Expand 10 after
1955 Variable* var = expr->AsVariableProxy()->var(); 1946 Variable* var = expr->AsVariableProxy()->var();
1956 EffectContext context(this); 1947 EffectContext context(this);
1957 EmitVariableAssignment(var, Token::ASSIGN, slot); 1948 EmitVariableAssignment(var, Token::ASSIGN, slot);
1958 break; 1949 break;
1959 } 1950 }
1960 case NAMED_PROPERTY: { 1951 case NAMED_PROPERTY: {
1961 PushOperand(eax); // Preserve value. 1952 PushOperand(eax); // Preserve value.
1962 VisitForAccumulatorValue(prop->obj()); 1953 VisitForAccumulatorValue(prop->obj());
1963 __ Move(StoreDescriptor::ReceiverRegister(), eax); 1954 __ Move(StoreDescriptor::ReceiverRegister(), eax);
1964 PopOperand(StoreDescriptor::ValueRegister()); // Restore value. 1955 PopOperand(StoreDescriptor::ValueRegister()); // Restore value.
1965 __ mov(StoreDescriptor::NameRegister(), 1956 CallStoreIC(slot, prop->key()->AsLiteral()->value());
1966 prop->key()->AsLiteral()->value());
1967 EmitLoadStoreICSlot(slot);
1968 CallStoreIC();
1969 break; 1957 break;
1970 } 1958 }
1971 case NAMED_SUPER_PROPERTY: { 1959 case NAMED_SUPER_PROPERTY: {
1972 PushOperand(eax); 1960 PushOperand(eax);
1973 VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var()); 1961 VisitForStackValue(prop->obj()->AsSuperPropertyReference()->this_var());
1974 VisitForAccumulatorValue( 1962 VisitForAccumulatorValue(
1975 prop->obj()->AsSuperPropertyReference()->home_object()); 1963 prop->obj()->AsSuperPropertyReference()->home_object());
1976 // stack: value, this; eax: home_object 1964 // stack: value, this; eax: home_object
1977 Register scratch = ecx; 1965 Register scratch = ecx;
1978 Register scratch2 = edx; 1966 Register scratch2 = edx;
(...skipping 26 matching lines...) Expand all
2005 EmitKeyedSuperPropertyStore(prop); 1993 EmitKeyedSuperPropertyStore(prop);
2006 break; 1994 break;
2007 } 1995 }
2008 case KEYED_PROPERTY: { 1996 case KEYED_PROPERTY: {
2009 PushOperand(eax); // Preserve value. 1997 PushOperand(eax); // Preserve value.
2010 VisitForStackValue(prop->obj()); 1998 VisitForStackValue(prop->obj());
2011 VisitForAccumulatorValue(prop->key()); 1999 VisitForAccumulatorValue(prop->key());
2012 __ Move(StoreDescriptor::NameRegister(), eax); 2000 __ Move(StoreDescriptor::NameRegister(), eax);
2013 PopOperand(StoreDescriptor::ReceiverRegister()); // Receiver. 2001 PopOperand(StoreDescriptor::ReceiverRegister()); // Receiver.
2014 PopOperand(StoreDescriptor::ValueRegister()); // Restore value. 2002 PopOperand(StoreDescriptor::ValueRegister()); // Restore value.
2015 EmitLoadStoreICSlot(slot); 2003 CallKeyedStoreIC(slot);
2016 CallKeyedStoreIC();
2017 break; 2004 break;
2018 } 2005 }
2019 } 2006 }
2020 context()->Plug(eax); 2007 context()->Plug(eax);
2021 } 2008 }
2022 2009
2023 2010
2024 void FullCodeGenerator::EmitStoreToStackLocalOrContextSlot( 2011 void FullCodeGenerator::EmitStoreToStackLocalOrContextSlot(
2025 Variable* var, MemOperand location) { 2012 Variable* var, MemOperand location) {
2026 __ mov(location, eax); 2013 __ mov(location, eax);
2027 if (var->IsContextSlot()) { 2014 if (var->IsContextSlot()) {
2028 __ mov(edx, eax); 2015 __ mov(edx, eax);
2029 int offset = Context::SlotOffset(var->index()); 2016 int offset = Context::SlotOffset(var->index());
2030 __ RecordWriteContextSlot(ecx, offset, edx, ebx, kDontSaveFPRegs); 2017 __ RecordWriteContextSlot(ecx, offset, edx, ebx, kDontSaveFPRegs);
2031 } 2018 }
2032 } 2019 }
2033 2020
2034 2021
2035 void FullCodeGenerator::EmitVariableAssignment(Variable* var, Token::Value op, 2022 void FullCodeGenerator::EmitVariableAssignment(Variable* var, Token::Value op,
2036 FeedbackVectorSlot slot) { 2023 FeedbackVectorSlot slot) {
2037 if (var->IsUnallocated()) { 2024 if (var->IsUnallocated()) {
2038 // Global var, const, or let. 2025 // Global var, const, or let.
2039 __ mov(StoreDescriptor::NameRegister(), var->name());
2040 __ mov(StoreDescriptor::ReceiverRegister(), NativeContextOperand()); 2026 __ mov(StoreDescriptor::ReceiverRegister(), NativeContextOperand());
2041 __ mov(StoreDescriptor::ReceiverRegister(), 2027 __ mov(StoreDescriptor::ReceiverRegister(),
2042 ContextOperand(StoreDescriptor::ReceiverRegister(), 2028 ContextOperand(StoreDescriptor::ReceiverRegister(),
2043 Context::EXTENSION_INDEX)); 2029 Context::EXTENSION_INDEX));
2044 EmitLoadStoreICSlot(slot); 2030 CallStoreIC(slot, var->name());
2045 CallStoreIC();
2046 2031
2047 } else if (IsLexicalVariableMode(var->mode()) && op != Token::INIT) { 2032 } else if (IsLexicalVariableMode(var->mode()) && op != Token::INIT) {
2048 DCHECK(!var->IsLookupSlot()); 2033 DCHECK(!var->IsLookupSlot());
2049 DCHECK(var->IsStackAllocated() || var->IsContextSlot()); 2034 DCHECK(var->IsStackAllocated() || var->IsContextSlot());
2050 MemOperand location = VarOperand(var, ecx); 2035 MemOperand location = VarOperand(var, ecx);
2051 // Perform an initialization check for lexically declared variables. 2036 // Perform an initialization check for lexically declared variables.
2052 if (var->binding_needs_init()) { 2037 if (var->binding_needs_init()) {
2053 Label assign; 2038 Label assign;
2054 __ mov(edx, location); 2039 __ mov(edx, location);
2055 __ cmp(edx, isolate()->factory()->the_hole_value()); 2040 __ cmp(edx, isolate()->factory()->the_hole_value());
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after
2103 2088
2104 2089
2105 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) { 2090 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) {
2106 // Assignment to a property, using a named store IC. 2091 // Assignment to a property, using a named store IC.
2107 // eax : value 2092 // eax : value
2108 // esp[0] : receiver 2093 // esp[0] : receiver
2109 Property* prop = expr->target()->AsProperty(); 2094 Property* prop = expr->target()->AsProperty();
2110 DCHECK(prop != NULL); 2095 DCHECK(prop != NULL);
2111 DCHECK(prop->key()->IsLiteral()); 2096 DCHECK(prop->key()->IsLiteral());
2112 2097
2113 __ mov(StoreDescriptor::NameRegister(), prop->key()->AsLiteral()->value());
2114 PopOperand(StoreDescriptor::ReceiverRegister()); 2098 PopOperand(StoreDescriptor::ReceiverRegister());
2115 EmitLoadStoreICSlot(expr->AssignmentSlot()); 2099 CallStoreIC(expr->AssignmentSlot(), prop->key()->AsLiteral()->value());
2116 CallStoreIC();
2117 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER); 2100 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER);
2118 context()->Plug(eax); 2101 context()->Plug(eax);
2119 } 2102 }
2120 2103
2121 2104
2122 void FullCodeGenerator::EmitNamedSuperPropertyStore(Property* prop) { 2105 void FullCodeGenerator::EmitNamedSuperPropertyStore(Property* prop) {
2123 // Assignment to named property of super. 2106 // Assignment to named property of super.
2124 // eax : value 2107 // eax : value
2125 // stack : receiver ('this'), home_object 2108 // stack : receiver ('this'), home_object
2126 DCHECK(prop != NULL); 2109 DCHECK(prop != NULL);
(...skipping 22 matching lines...) Expand all
2149 2132
2150 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) { 2133 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) {
2151 // Assignment to a property, using a keyed store IC. 2134 // Assignment to a property, using a keyed store IC.
2152 // eax : value 2135 // eax : value
2153 // esp[0] : key 2136 // esp[0] : key
2154 // esp[kPointerSize] : receiver 2137 // esp[kPointerSize] : receiver
2155 2138
2156 PopOperand(StoreDescriptor::NameRegister()); // Key. 2139 PopOperand(StoreDescriptor::NameRegister()); // Key.
2157 PopOperand(StoreDescriptor::ReceiverRegister()); 2140 PopOperand(StoreDescriptor::ReceiverRegister());
2158 DCHECK(StoreDescriptor::ValueRegister().is(eax)); 2141 DCHECK(StoreDescriptor::ValueRegister().is(eax));
2159 EmitLoadStoreICSlot(expr->AssignmentSlot()); 2142 CallKeyedStoreIC(expr->AssignmentSlot());
2160 CallKeyedStoreIC();
2161 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER); 2143 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER);
2162 context()->Plug(eax); 2144 context()->Plug(eax);
2163 } 2145 }
2164 2146
2165 2147
2166 void FullCodeGenerator::CallIC(Handle<Code> code, 2148 void FullCodeGenerator::CallIC(Handle<Code> code,
2167 TypeFeedbackId ast_id) { 2149 TypeFeedbackId ast_id) {
2168 ic_total_count_++; 2150 ic_total_count_++;
2169 __ call(code, RelocInfo::CODE_TARGET, ast_id); 2151 __ call(code, RelocInfo::CODE_TARGET, ast_id);
2170 } 2152 }
(...skipping 1024 matching lines...) Expand 10 before | Expand all | Expand 10 after
3195 } else { 3177 } else {
3196 // Perform the assignment as if via '='. 3178 // Perform the assignment as if via '='.
3197 EmitVariableAssignment(expr->expression()->AsVariableProxy()->var(), 3179 EmitVariableAssignment(expr->expression()->AsVariableProxy()->var(),
3198 Token::ASSIGN, expr->CountSlot()); 3180 Token::ASSIGN, expr->CountSlot());
3199 PrepareForBailoutForId(expr->AssignmentId(), 3181 PrepareForBailoutForId(expr->AssignmentId(),
3200 BailoutState::TOS_REGISTER); 3182 BailoutState::TOS_REGISTER);
3201 context()->Plug(eax); 3183 context()->Plug(eax);
3202 } 3184 }
3203 break; 3185 break;
3204 case NAMED_PROPERTY: { 3186 case NAMED_PROPERTY: {
3205 __ mov(StoreDescriptor::NameRegister(),
3206 prop->key()->AsLiteral()->value());
3207 PopOperand(StoreDescriptor::ReceiverRegister()); 3187 PopOperand(StoreDescriptor::ReceiverRegister());
3208 EmitLoadStoreICSlot(expr->CountSlot()); 3188 CallStoreIC(expr->CountSlot(), prop->key()->AsLiteral()->value());
3209 CallStoreIC();
3210 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER); 3189 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER);
3211 if (expr->is_postfix()) { 3190 if (expr->is_postfix()) {
3212 if (!context()->IsEffect()) { 3191 if (!context()->IsEffect()) {
3213 context()->PlugTOS(); 3192 context()->PlugTOS();
3214 } 3193 }
3215 } else { 3194 } else {
3216 context()->Plug(eax); 3195 context()->Plug(eax);
3217 } 3196 }
3218 break; 3197 break;
3219 } 3198 }
(...skipping 17 matching lines...) Expand all
3237 context()->PlugTOS(); 3216 context()->PlugTOS();
3238 } 3217 }
3239 } else { 3218 } else {
3240 context()->Plug(eax); 3219 context()->Plug(eax);
3241 } 3220 }
3242 break; 3221 break;
3243 } 3222 }
3244 case KEYED_PROPERTY: { 3223 case KEYED_PROPERTY: {
3245 PopOperand(StoreDescriptor::NameRegister()); 3224 PopOperand(StoreDescriptor::NameRegister());
3246 PopOperand(StoreDescriptor::ReceiverRegister()); 3225 PopOperand(StoreDescriptor::ReceiverRegister());
3247 EmitLoadStoreICSlot(expr->CountSlot()); 3226 CallKeyedStoreIC(expr->CountSlot());
3248 CallKeyedStoreIC();
3249 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER); 3227 PrepareForBailoutForId(expr->AssignmentId(), BailoutState::TOS_REGISTER);
3250 if (expr->is_postfix()) { 3228 if (expr->is_postfix()) {
3251 // Result is on the stack 3229 // Result is on the stack
3252 if (!context()->IsEffect()) { 3230 if (!context()->IsEffect()) {
3253 context()->PlugTOS(); 3231 context()->PlugTOS();
3254 } 3232 }
3255 } else { 3233 } else {
3256 context()->Plug(eax); 3234 context()->Plug(eax);
3257 } 3235 }
3258 break; 3236 break;
(...skipping 362 matching lines...) Expand 10 before | Expand all | Expand 10 after
3621 isolate->builtins()->OnStackReplacement()->entry(), 3599 isolate->builtins()->OnStackReplacement()->entry(),
3622 Assembler::target_address_at(call_target_address, unoptimized_code)); 3600 Assembler::target_address_at(call_target_address, unoptimized_code));
3623 return ON_STACK_REPLACEMENT; 3601 return ON_STACK_REPLACEMENT;
3624 } 3602 }
3625 3603
3626 3604
3627 } // namespace internal 3605 } // namespace internal
3628 } // namespace v8 3606 } // namespace v8
3629 3607
3630 #endif // V8_TARGET_ARCH_IA32 3608 #endif // V8_TARGET_ARCH_IA32
OLDNEW
« no previous file with comments | « src/full-codegen/full-codegen.cc ('k') | src/full-codegen/mips/full-codegen-mips.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698