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

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

Issue 1218493005: Debugger: use debug break slots instead of ICs (except for calls). (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: addressed comments Created 5 years, 5 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/ia32/debug-ia32.cc ('k') | src/mips/debug-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 #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 451 matching lines...) Expand 10 before | Expand all | Expand 10 after
462 __ call(isolate()->builtins()->InterruptCheck(), 462 __ call(isolate()->builtins()->InterruptCheck(),
463 RelocInfo::CODE_TARGET); 463 RelocInfo::CODE_TARGET);
464 __ pop(eax); 464 __ pop(eax);
465 EmitProfilingCounterReset(); 465 EmitProfilingCounterReset();
466 __ bind(&ok); 466 __ bind(&ok);
467 #ifdef DEBUG 467 #ifdef DEBUG
468 // Add a label for checking the size of the code used for returning. 468 // Add a label for checking the size of the code used for returning.
469 Label check_exit_codesize; 469 Label check_exit_codesize;
470 masm_->bind(&check_exit_codesize); 470 masm_->bind(&check_exit_codesize);
471 #endif 471 #endif
472 SetSourcePosition(function()->end_position() - 1); 472 SetReturnPosition(function());
473 __ RecordJSReturn(); 473 __ RecordJSReturn();
474 // Do not use the leave instruction here because it is too short to 474 // Do not use the leave instruction here because it is too short to
475 // patch with the code required by the debugger. 475 // patch with the code required by the debugger.
476 __ mov(esp, ebp); 476 __ mov(esp, ebp);
477 int no_frame_start = masm_->pc_offset(); 477 int no_frame_start = masm_->pc_offset();
478 __ pop(ebp); 478 __ pop(ebp);
479 479
480 int arg_count = info_->scope()->num_parameters() + 1; 480 int arg_count = info_->scope()->num_parameters() + 1;
481 int arguments_bytes = arg_count * kPointerSize; 481 int arguments_bytes = arg_count * kPointerSize;
482 __ Ret(arguments_bytes, ecx); 482 __ Ret(arguments_bytes, ecx);
(...skipping 532 matching lines...) Expand 10 before | Expand all | Expand 10 after
1015 __ or_(ecx, eax); 1015 __ or_(ecx, eax);
1016 patch_site.EmitJumpIfNotSmi(ecx, &slow_case, Label::kNear); 1016 patch_site.EmitJumpIfNotSmi(ecx, &slow_case, Label::kNear);
1017 1017
1018 __ cmp(edx, eax); 1018 __ cmp(edx, eax);
1019 __ j(not_equal, &next_test); 1019 __ j(not_equal, &next_test);
1020 __ Drop(1); // Switch value is no longer needed. 1020 __ Drop(1); // Switch value is no longer needed.
1021 __ jmp(clause->body_target()); 1021 __ jmp(clause->body_target());
1022 __ bind(&slow_case); 1022 __ bind(&slow_case);
1023 } 1023 }
1024 1024
1025 // Record position before stub call for type feedback. 1025 SetExpressionPosition(clause);
1026 SetSourcePosition(clause->position());
1027 Handle<Code> ic = CodeFactory::CompareIC(isolate(), Token::EQ_STRICT, 1026 Handle<Code> ic = CodeFactory::CompareIC(isolate(), Token::EQ_STRICT,
1028 strength(language_mode())).code(); 1027 strength(language_mode())).code();
1029 CallIC(ic, clause->CompareId()); 1028 CallIC(ic, clause->CompareId());
1030 patch_site.EmitPatchInfo(); 1029 patch_site.EmitPatchInfo();
1031 1030
1032 Label skip; 1031 Label skip;
1033 __ jmp(&skip, Label::kNear); 1032 __ jmp(&skip, Label::kNear);
1034 PrepareForBailout(clause, TOS_REG); 1033 PrepareForBailout(clause, TOS_REG);
1035 __ cmp(eax, isolate()->factory()->true_value()); 1034 __ cmp(eax, isolate()->factory()->true_value());
1036 __ j(not_equal, &next_test); 1035 __ j(not_equal, &next_test);
(...skipping 26 matching lines...) Expand all
1063 VisitStatements(clause->statements()); 1062 VisitStatements(clause->statements());
1064 } 1063 }
1065 1064
1066 __ bind(nested_statement.break_label()); 1065 __ bind(nested_statement.break_label());
1067 PrepareForBailoutForId(stmt->ExitId(), NO_REGISTERS); 1066 PrepareForBailoutForId(stmt->ExitId(), NO_REGISTERS);
1068 } 1067 }
1069 1068
1070 1069
1071 void FullCodeGenerator::VisitForInStatement(ForInStatement* stmt) { 1070 void FullCodeGenerator::VisitForInStatement(ForInStatement* stmt) {
1072 Comment cmnt(masm_, "[ ForInStatement"); 1071 Comment cmnt(masm_, "[ ForInStatement");
1072 SetStatementPosition(stmt, SKIP_BREAK);
1073
1073 FeedbackVectorSlot slot = stmt->ForInFeedbackSlot(); 1074 FeedbackVectorSlot slot = stmt->ForInFeedbackSlot();
1074 1075
1075 SetStatementPosition(stmt);
1076
1077 Label loop, exit; 1076 Label loop, exit;
1078 ForIn loop_statement(this, stmt); 1077 ForIn loop_statement(this, stmt);
1079 increment_loop_depth(); 1078 increment_loop_depth();
1080 1079
1081 // Get the object to enumerate over. If the object is null or undefined, skip 1080 // Get the object to enumerate over. If the object is null or undefined, skip
1082 // over the loop. See ECMA-262 version 5, section 12.6.4. 1081 // over the loop. See ECMA-262 version 5, section 12.6.4.
1083 SetExpressionPosition(stmt->enumerable()); 1082 SetExpressionAsStatementPosition(stmt->enumerable());
1084 VisitForAccumulatorValue(stmt->enumerable()); 1083 VisitForAccumulatorValue(stmt->enumerable());
1085 __ cmp(eax, isolate()->factory()->undefined_value()); 1084 __ cmp(eax, isolate()->factory()->undefined_value());
1086 __ j(equal, &exit); 1085 __ j(equal, &exit);
1087 __ cmp(eax, isolate()->factory()->null_value()); 1086 __ cmp(eax, isolate()->factory()->null_value());
1088 __ j(equal, &exit); 1087 __ j(equal, &exit);
1089 1088
1090 PrepareForBailoutForId(stmt->PrepareId(), TOS_REG); 1089 PrepareForBailoutForId(stmt->PrepareId(), TOS_REG);
1091 1090
1092 // Convert the object to a JS object. 1091 // Convert the object to a JS object.
1093 Label convert, done_convert; 1092 Label convert, done_convert;
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after
1168 __ bind(&non_proxy); 1167 __ bind(&non_proxy);
1169 __ push(ebx); // Smi 1168 __ push(ebx); // Smi
1170 __ push(eax); // Array 1169 __ push(eax); // Array
1171 __ mov(eax, FieldOperand(eax, FixedArray::kLengthOffset)); 1170 __ mov(eax, FieldOperand(eax, FixedArray::kLengthOffset));
1172 __ push(eax); // Fixed array length (as smi). 1171 __ push(eax); // Fixed array length (as smi).
1173 __ push(Immediate(Smi::FromInt(0))); // Initial index. 1172 __ push(Immediate(Smi::FromInt(0))); // Initial index.
1174 1173
1175 // Generate code for doing the condition check. 1174 // Generate code for doing the condition check.
1176 PrepareForBailoutForId(stmt->BodyId(), NO_REGISTERS); 1175 PrepareForBailoutForId(stmt->BodyId(), NO_REGISTERS);
1177 __ bind(&loop); 1176 __ bind(&loop);
1178 SetExpressionPosition(stmt->each()); 1177 SetExpressionAsStatementPosition(stmt->each());
1179 1178
1180 __ mov(eax, Operand(esp, 0 * kPointerSize)); // Get the current index. 1179 __ mov(eax, Operand(esp, 0 * kPointerSize)); // Get the current index.
1181 __ cmp(eax, Operand(esp, 1 * kPointerSize)); // Compare to the array length. 1180 __ cmp(eax, Operand(esp, 1 * kPointerSize)); // Compare to the array length.
1182 __ j(above_equal, loop_statement.break_label()); 1181 __ j(above_equal, loop_statement.break_label());
1183 1182
1184 // Get the current entry of the array into register ebx. 1183 // Get the current entry of the array into register ebx.
1185 __ mov(ebx, Operand(esp, 2 * kPointerSize)); 1184 __ mov(ebx, Operand(esp, 2 * kPointerSize));
1186 __ mov(ebx, FieldOperand(ebx, eax, times_2, FixedArray::kHeaderSize)); 1185 __ mov(ebx, FieldOperand(ebx, eax, times_2, FixedArray::kHeaderSize));
1187 1186
1188 // Get the expected map from the stack or a smi in the 1187 // Get the expected map from the stack or a smi in the
(...skipping 224 matching lines...) Expand 10 before | Expand all | Expand 10 after
1413 __ push(Immediate(var->name())); 1412 __ push(Immediate(var->name()));
1414 __ CallRuntime(Runtime::kThrowReferenceError, 1); 1413 __ CallRuntime(Runtime::kThrowReferenceError, 1);
1415 } 1414 }
1416 } 1415 }
1417 __ jmp(done); 1416 __ jmp(done);
1418 } 1417 }
1419 } 1418 }
1420 1419
1421 1420
1422 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) { 1421 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) {
1423 // Record position before possible IC call. 1422 SetExpressionPosition(proxy);
1424 SetSourcePosition(proxy->position());
1425 PrepareForBailoutForId(proxy->BeforeId(), NO_REGISTERS); 1423 PrepareForBailoutForId(proxy->BeforeId(), NO_REGISTERS);
1426 Variable* var = proxy->var(); 1424 Variable* var = proxy->var();
1427 1425
1428 // Three cases: global variables, lookup variables, and all other types of 1426 // Three cases: global variables, lookup variables, and all other types of
1429 // variables. 1427 // variables.
1430 switch (var->location()) { 1428 switch (var->location()) {
1431 case Variable::UNALLOCATED: { 1429 case Variable::UNALLOCATED: {
1432 Comment cmnt(masm_, "[ Global variable"); 1430 Comment cmnt(masm_, "[ Global variable");
1433 __ mov(LoadDescriptor::ReceiverRegister(), GlobalObjectOperand()); 1431 __ mov(LoadDescriptor::ReceiverRegister(), GlobalObjectOperand());
1434 __ mov(LoadDescriptor::NameRegister(), var->name()); 1432 __ mov(LoadDescriptor::NameRegister(), var->name());
(...skipping 477 matching lines...) Expand 10 before | Expand all | Expand 10 after
1912 } else { 1910 } else {
1913 context()->Plug(eax); 1911 context()->Plug(eax);
1914 } 1912 }
1915 } 1913 }
1916 1914
1917 1915
1918 void FullCodeGenerator::VisitAssignment(Assignment* expr) { 1916 void FullCodeGenerator::VisitAssignment(Assignment* expr) {
1919 DCHECK(expr->target()->IsValidReferenceExpression()); 1917 DCHECK(expr->target()->IsValidReferenceExpression());
1920 1918
1921 Comment cmnt(masm_, "[ Assignment"); 1919 Comment cmnt(masm_, "[ Assignment");
1920 SetExpressionPosition(expr, INSERT_BREAK);
1922 1921
1923 Property* property = expr->target()->AsProperty(); 1922 Property* property = expr->target()->AsProperty();
1924 LhsKind assign_type = Property::GetAssignType(property); 1923 LhsKind assign_type = Property::GetAssignType(property);
1925 1924
1926 // Evaluate LHS expression. 1925 // Evaluate LHS expression.
1927 switch (assign_type) { 1926 switch (assign_type) {
1928 case VARIABLE: 1927 case VARIABLE:
1929 // Nothing to do here. 1928 // Nothing to do here.
1930 break; 1929 break;
1931 case NAMED_SUPER_PROPERTY: 1930 case NAMED_SUPER_PROPERTY:
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
2001 EmitKeyedPropertyLoad(property); 2000 EmitKeyedPropertyLoad(property);
2002 PrepareForBailoutForId(property->LoadId(), TOS_REG); 2001 PrepareForBailoutForId(property->LoadId(), TOS_REG);
2003 break; 2002 break;
2004 } 2003 }
2005 } 2004 }
2006 2005
2007 Token::Value op = expr->binary_op(); 2006 Token::Value op = expr->binary_op();
2008 __ push(eax); // Left operand goes on the stack. 2007 __ push(eax); // Left operand goes on the stack.
2009 VisitForAccumulatorValue(expr->value()); 2008 VisitForAccumulatorValue(expr->value());
2010 2009
2011 SetSourcePosition(expr->position() + 1);
2012 if (ShouldInlineSmiCase(op)) { 2010 if (ShouldInlineSmiCase(op)) {
2013 EmitInlineSmiBinaryOp(expr->binary_operation(), 2011 EmitInlineSmiBinaryOp(expr->binary_operation(),
2014 op, 2012 op,
2015 expr->target(), 2013 expr->target(),
2016 expr->value()); 2014 expr->value());
2017 } else { 2015 } else {
2018 EmitBinaryOp(expr->binary_operation(), op); 2016 EmitBinaryOp(expr->binary_operation(), op);
2019 } 2017 }
2020 2018
2021 // Deoptimization point in case the binary operation may have side effects. 2019 // Deoptimization point in case the binary operation may have side effects.
2022 PrepareForBailout(expr->binary_operation(), TOS_REG); 2020 PrepareForBailout(expr->binary_operation(), TOS_REG);
2023 } else { 2021 } else {
2024 VisitForAccumulatorValue(expr->value()); 2022 VisitForAccumulatorValue(expr->value());
2025 } 2023 }
2026 2024
2027 // Record source position before possible IC call. 2025 SetExpressionPosition(expr);
2028 SetSourcePosition(expr->position());
2029 2026
2030 // Store the value. 2027 // Store the value.
2031 switch (assign_type) { 2028 switch (assign_type) {
2032 case VARIABLE: 2029 case VARIABLE:
2033 EmitVariableAssignment(expr->target()->AsVariableProxy()->var(), 2030 EmitVariableAssignment(expr->target()->AsVariableProxy()->var(),
2034 expr->op(), expr->AssignmentSlot()); 2031 expr->op(), expr->AssignmentSlot());
2035 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2032 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2036 context()->Plug(eax); 2033 context()->Plug(eax);
2037 break; 2034 break;
2038 case NAMED_PROPERTY: 2035 case NAMED_PROPERTY:
2039 EmitNamedPropertyAssignment(expr); 2036 EmitNamedPropertyAssignment(expr);
2040 break; 2037 break;
2041 case NAMED_SUPER_PROPERTY: 2038 case NAMED_SUPER_PROPERTY:
2042 EmitNamedSuperPropertyStore(property); 2039 EmitNamedSuperPropertyStore(property);
2043 context()->Plug(result_register()); 2040 context()->Plug(result_register());
2044 break; 2041 break;
2045 case KEYED_SUPER_PROPERTY: 2042 case KEYED_SUPER_PROPERTY:
2046 EmitKeyedSuperPropertyStore(property); 2043 EmitKeyedSuperPropertyStore(property);
2047 context()->Plug(result_register()); 2044 context()->Plug(result_register());
2048 break; 2045 break;
2049 case KEYED_PROPERTY: 2046 case KEYED_PROPERTY:
2050 EmitKeyedPropertyAssignment(expr); 2047 EmitKeyedPropertyAssignment(expr);
2051 break; 2048 break;
2052 } 2049 }
2053 } 2050 }
2054 2051
2055 2052
2056 void FullCodeGenerator::VisitYield(Yield* expr) { 2053 void FullCodeGenerator::VisitYield(Yield* expr) {
2057 Comment cmnt(masm_, "[ Yield"); 2054 Comment cmnt(masm_, "[ Yield");
2055 SetExpressionPosition(expr);
2056
2058 // Evaluate yielded value first; the initial iterator definition depends on 2057 // Evaluate yielded value first; the initial iterator definition depends on
2059 // this. It stays on the stack while we update the iterator. 2058 // this. It stays on the stack while we update the iterator.
2060 VisitForStackValue(expr->expression()); 2059 VisitForStackValue(expr->expression());
2061 2060
2062 switch (expr->yield_kind()) { 2061 switch (expr->yield_kind()) {
2063 case Yield::kSuspend: 2062 case Yield::kSuspend:
2064 // Pop value from top-of-stack slot; box result into result register. 2063 // Pop value from top-of-stack slot; box result into result register.
2065 EmitCreateIteratorResult(false); 2064 EmitCreateIteratorResult(false);
2066 __ push(result_register()); 2065 __ push(result_register());
2067 // Fall through. 2066 // Fall through.
(...skipping 265 matching lines...) Expand 10 before | Expand all | Expand 10 after
2333 __ mov(FieldOperand(eax, JSGeneratorObject::kResultDonePropertyOffset), edx); 2332 __ mov(FieldOperand(eax, JSGeneratorObject::kResultDonePropertyOffset), edx);
2334 2333
2335 // Only the value field needs a write barrier, as the other values are in the 2334 // Only the value field needs a write barrier, as the other values are in the
2336 // root set. 2335 // root set.
2337 __ RecordWriteField(eax, JSGeneratorObject::kResultValuePropertyOffset, 2336 __ RecordWriteField(eax, JSGeneratorObject::kResultValuePropertyOffset,
2338 ecx, edx, kDontSaveFPRegs); 2337 ecx, edx, kDontSaveFPRegs);
2339 } 2338 }
2340 2339
2341 2340
2342 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) { 2341 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) {
2343 SetSourcePosition(prop->position()); 2342 SetExpressionPosition(prop);
2344 Literal* key = prop->key()->AsLiteral(); 2343 Literal* key = prop->key()->AsLiteral();
2345 DCHECK(!key->value()->IsSmi()); 2344 DCHECK(!key->value()->IsSmi());
2346 DCHECK(!prop->IsSuperAccess()); 2345 DCHECK(!prop->IsSuperAccess());
2347 2346
2348 __ mov(LoadDescriptor::NameRegister(), Immediate(key->value())); 2347 __ mov(LoadDescriptor::NameRegister(), Immediate(key->value()));
2349 __ mov(LoadDescriptor::SlotRegister(), 2348 __ mov(LoadDescriptor::SlotRegister(),
2350 Immediate(SmiFromSlot(prop->PropertyFeedbackSlot()))); 2349 Immediate(SmiFromSlot(prop->PropertyFeedbackSlot())));
2351 CallLoadIC(NOT_CONTEXTUAL, language_mode()); 2350 CallLoadIC(NOT_CONTEXTUAL, language_mode());
2352 } 2351 }
2353 2352
2354 2353
2355 void FullCodeGenerator::EmitNamedSuperPropertyLoad(Property* prop) { 2354 void FullCodeGenerator::EmitNamedSuperPropertyLoad(Property* prop) {
2356 // Stack: receiver, home_object. 2355 // Stack: receiver, home_object.
2357 SetSourcePosition(prop->position()); 2356 SetExpressionPosition(prop);
2358 Literal* key = prop->key()->AsLiteral(); 2357 Literal* key = prop->key()->AsLiteral();
2359 DCHECK(!key->value()->IsSmi()); 2358 DCHECK(!key->value()->IsSmi());
2360 DCHECK(prop->IsSuperAccess()); 2359 DCHECK(prop->IsSuperAccess());
2361 2360
2362 __ push(Immediate(key->value())); 2361 __ push(Immediate(key->value()));
2363 __ push(Immediate(Smi::FromInt(language_mode()))); 2362 __ push(Immediate(Smi::FromInt(language_mode())));
2364 __ CallRuntime(Runtime::kLoadFromSuper, 4); 2363 __ CallRuntime(Runtime::kLoadFromSuper, 4);
2365 } 2364 }
2366 2365
2367 2366
2368 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) { 2367 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) {
2369 SetSourcePosition(prop->position()); 2368 SetExpressionPosition(prop);
2370 Handle<Code> ic = CodeFactory::KeyedLoadIC(isolate(), language_mode()).code(); 2369 Handle<Code> ic = CodeFactory::KeyedLoadIC(isolate(), language_mode()).code();
2371 __ mov(LoadDescriptor::SlotRegister(), 2370 __ mov(LoadDescriptor::SlotRegister(),
2372 Immediate(SmiFromSlot(prop->PropertyFeedbackSlot()))); 2371 Immediate(SmiFromSlot(prop->PropertyFeedbackSlot())));
2373 CallIC(ic); 2372 CallIC(ic);
2374 } 2373 }
2375 2374
2376 2375
2377 void FullCodeGenerator::EmitKeyedSuperPropertyLoad(Property* prop) { 2376 void FullCodeGenerator::EmitKeyedSuperPropertyLoad(Property* prop) {
2378 // Stack: receiver, home_object, key. 2377 // Stack: receiver, home_object, key.
2378 SetExpressionPosition(prop);
2379 __ push(Immediate(Smi::FromInt(language_mode()))); 2379 __ push(Immediate(Smi::FromInt(language_mode())));
2380 SetSourcePosition(prop->position());
2381
2382 __ CallRuntime(Runtime::kLoadKeyedFromSuper, 4); 2380 __ CallRuntime(Runtime::kLoadKeyedFromSuper, 4);
2383 } 2381 }
2384 2382
2385 2383
2386 void FullCodeGenerator::EmitInlineSmiBinaryOp(BinaryOperation* expr, 2384 void FullCodeGenerator::EmitInlineSmiBinaryOp(BinaryOperation* expr,
2387 Token::Value op, 2385 Token::Value op,
2388 Expression* left, 2386 Expression* left,
2389 Expression* right) { 2387 Expression* right) {
2390 // Do combined smi check of the operands. Left operand is on the 2388 // Do combined smi check of the operands. Left operand is on the
2391 // stack. Right operand is in eax. 2389 // stack. Right operand is in eax.
(...skipping 339 matching lines...) Expand 10 before | Expand all | Expand 10 after
2731 } 2729 }
2732 // Silently ignore store in sloppy mode. 2730 // Silently ignore store in sloppy mode.
2733 } 2731 }
2734 } 2732 }
2735 2733
2736 2734
2737 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) { 2735 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) {
2738 // Assignment to a property, using a named store IC. 2736 // Assignment to a property, using a named store IC.
2739 // eax : value 2737 // eax : value
2740 // esp[0] : receiver 2738 // esp[0] : receiver
2741
2742 Property* prop = expr->target()->AsProperty(); 2739 Property* prop = expr->target()->AsProperty();
2743 DCHECK(prop != NULL); 2740 DCHECK(prop != NULL);
2744 DCHECK(prop->key()->IsLiteral()); 2741 DCHECK(prop->key()->IsLiteral());
2745 2742
2746 // Record source code position before IC call.
2747 SetSourcePosition(expr->position());
2748 __ mov(StoreDescriptor::NameRegister(), prop->key()->AsLiteral()->value()); 2743 __ mov(StoreDescriptor::NameRegister(), prop->key()->AsLiteral()->value());
2749 __ pop(StoreDescriptor::ReceiverRegister()); 2744 __ pop(StoreDescriptor::ReceiverRegister());
2750 if (FLAG_vector_stores) { 2745 if (FLAG_vector_stores) {
2751 EmitLoadStoreICSlot(expr->AssignmentSlot()); 2746 EmitLoadStoreICSlot(expr->AssignmentSlot());
2752 CallStoreIC(); 2747 CallStoreIC();
2753 } else { 2748 } else {
2754 CallStoreIC(expr->AssignmentFeedbackId()); 2749 CallStoreIC(expr->AssignmentFeedbackId());
2755 } 2750 }
2756 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2751 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2757 context()->Plug(eax); 2752 context()->Plug(eax);
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
2789 2784
2790 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) { 2785 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) {
2791 // Assignment to a property, using a keyed store IC. 2786 // Assignment to a property, using a keyed store IC.
2792 // eax : value 2787 // eax : value
2793 // esp[0] : key 2788 // esp[0] : key
2794 // esp[kPointerSize] : receiver 2789 // esp[kPointerSize] : receiver
2795 2790
2796 __ pop(StoreDescriptor::NameRegister()); // Key. 2791 __ pop(StoreDescriptor::NameRegister()); // Key.
2797 __ pop(StoreDescriptor::ReceiverRegister()); 2792 __ pop(StoreDescriptor::ReceiverRegister());
2798 DCHECK(StoreDescriptor::ValueRegister().is(eax)); 2793 DCHECK(StoreDescriptor::ValueRegister().is(eax));
2799 // Record source code position before IC call.
2800 SetSourcePosition(expr->position());
2801 Handle<Code> ic = 2794 Handle<Code> ic =
2802 CodeFactory::KeyedStoreIC(isolate(), language_mode()).code(); 2795 CodeFactory::KeyedStoreIC(isolate(), language_mode()).code();
2803 if (FLAG_vector_stores) { 2796 if (FLAG_vector_stores) {
2804 EmitLoadStoreICSlot(expr->AssignmentSlot()); 2797 EmitLoadStoreICSlot(expr->AssignmentSlot());
2805 CallIC(ic); 2798 CallIC(ic);
2806 } else { 2799 } else {
2807 CallIC(ic, expr->AssignmentFeedbackId()); 2800 CallIC(ic, expr->AssignmentFeedbackId());
2808 } 2801 }
2809 2802
2810 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2803 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2811 context()->Plug(eax); 2804 context()->Plug(eax);
2812 } 2805 }
2813 2806
2814 2807
2815 void FullCodeGenerator::VisitProperty(Property* expr) { 2808 void FullCodeGenerator::VisitProperty(Property* expr) {
2816 Comment cmnt(masm_, "[ Property"); 2809 Comment cmnt(masm_, "[ Property");
2810 SetExpressionPosition(expr);
2811
2817 Expression* key = expr->key(); 2812 Expression* key = expr->key();
2818 2813
2819 if (key->IsPropertyName()) { 2814 if (key->IsPropertyName()) {
2820 if (!expr->IsSuperAccess()) { 2815 if (!expr->IsSuperAccess()) {
2821 VisitForAccumulatorValue(expr->obj()); 2816 VisitForAccumulatorValue(expr->obj());
2822 __ Move(LoadDescriptor::ReceiverRegister(), result_register()); 2817 __ Move(LoadDescriptor::ReceiverRegister(), result_register());
2823 EmitNamedPropertyLoad(expr); 2818 EmitNamedPropertyLoad(expr);
2824 } else { 2819 } else {
2825 VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var()); 2820 VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
2826 VisitForStackValue( 2821 VisitForStackValue(
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
2879 // Push the target function under the receiver. 2874 // Push the target function under the receiver.
2880 __ push(Operand(esp, 0)); 2875 __ push(Operand(esp, 0));
2881 __ mov(Operand(esp, kPointerSize), eax); 2876 __ mov(Operand(esp, kPointerSize), eax);
2882 } 2877 }
2883 2878
2884 EmitCall(expr, call_type); 2879 EmitCall(expr, call_type);
2885 } 2880 }
2886 2881
2887 2882
2888 void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) { 2883 void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
2884 SetExpressionPosition(expr);
2889 Expression* callee = expr->expression(); 2885 Expression* callee = expr->expression();
2890 DCHECK(callee->IsProperty()); 2886 DCHECK(callee->IsProperty());
2891 Property* prop = callee->AsProperty(); 2887 Property* prop = callee->AsProperty();
2892 DCHECK(prop->IsSuperAccess()); 2888 DCHECK(prop->IsSuperAccess());
2893 2889
2894 SetSourcePosition(prop->position());
2895 Literal* key = prop->key()->AsLiteral(); 2890 Literal* key = prop->key()->AsLiteral();
2896 DCHECK(!key->value()->IsSmi()); 2891 DCHECK(!key->value()->IsSmi());
2897 // Load the function from the receiver. 2892 // Load the function from the receiver.
2898 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference(); 2893 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
2899 VisitForStackValue(super_ref->home_object()); 2894 VisitForStackValue(super_ref->home_object());
2900 VisitForAccumulatorValue(super_ref->this_var()); 2895 VisitForAccumulatorValue(super_ref->this_var());
2901 __ push(eax); 2896 __ push(eax);
2902 __ push(eax); 2897 __ push(eax);
2903 __ push(Operand(esp, kPointerSize * 2)); 2898 __ push(Operand(esp, kPointerSize * 2));
2904 __ push(Immediate(key->value())); 2899 __ push(Immediate(key->value()));
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
2944 EmitCall(expr, CallICState::METHOD); 2939 EmitCall(expr, CallICState::METHOD);
2945 } 2940 }
2946 2941
2947 2942
2948 void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) { 2943 void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
2949 Expression* callee = expr->expression(); 2944 Expression* callee = expr->expression();
2950 DCHECK(callee->IsProperty()); 2945 DCHECK(callee->IsProperty());
2951 Property* prop = callee->AsProperty(); 2946 Property* prop = callee->AsProperty();
2952 DCHECK(prop->IsSuperAccess()); 2947 DCHECK(prop->IsSuperAccess());
2953 2948
2954 SetSourcePosition(prop->position()); 2949 SetExpressionPosition(prop);
2955 // Load the function from the receiver. 2950 // Load the function from the receiver.
2956 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference(); 2951 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
2957 VisitForStackValue(super_ref->home_object()); 2952 VisitForStackValue(super_ref->home_object());
2958 VisitForAccumulatorValue(super_ref->this_var()); 2953 VisitForAccumulatorValue(super_ref->this_var());
2959 __ push(eax); 2954 __ push(eax);
2960 __ push(eax); 2955 __ push(eax);
2961 __ push(Operand(esp, kPointerSize * 2)); 2956 __ push(Operand(esp, kPointerSize * 2));
2962 VisitForStackValue(prop->key()); 2957 VisitForStackValue(prop->key());
2963 __ push(Immediate(Smi::FromInt(language_mode()))); 2958 __ push(Immediate(Smi::FromInt(language_mode())));
2964 // Stack here: 2959 // Stack here:
(...skipping 12 matching lines...) Expand all
2977 // - target function 2972 // - target function
2978 // - this (receiver) 2973 // - this (receiver)
2979 EmitCall(expr, CallICState::METHOD); 2974 EmitCall(expr, CallICState::METHOD);
2980 } 2975 }
2981 2976
2982 2977
2983 void FullCodeGenerator::EmitCall(Call* expr, CallICState::CallType call_type) { 2978 void FullCodeGenerator::EmitCall(Call* expr, CallICState::CallType call_type) {
2984 // Load the arguments. 2979 // Load the arguments.
2985 ZoneList<Expression*>* args = expr->arguments(); 2980 ZoneList<Expression*>* args = expr->arguments();
2986 int arg_count = args->length(); 2981 int arg_count = args->length();
2987 { PreservePositionScope scope(masm()->positions_recorder()); 2982 for (int i = 0; i < arg_count; i++) {
2988 for (int i = 0; i < arg_count; i++) { 2983 VisitForStackValue(args->at(i));
2989 VisitForStackValue(args->at(i));
2990 }
2991 } 2984 }
2992 2985
2993 // Record source position of the IC call. 2986 SetExpressionPosition(expr);
2994 SetSourcePosition(expr->position());
2995 Handle<Code> ic = CodeFactory::CallIC(isolate(), arg_count, call_type).code(); 2987 Handle<Code> ic = CodeFactory::CallIC(isolate(), arg_count, call_type).code();
2996 __ Move(edx, Immediate(SmiFromSlot(expr->CallFeedbackICSlot()))); 2988 __ Move(edx, Immediate(SmiFromSlot(expr->CallFeedbackICSlot())));
2997 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize)); 2989 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize));
2998 // Don't assign a type feedback id to the IC, since type feedback is provided 2990 // Don't assign a type feedback id to the IC, since type feedback is provided
2999 // by the vector above. 2991 // by the vector above.
3000 CallIC(ic); 2992 CallIC(ic);
3001 2993
3002 RecordJSReturnSite(expr); 2994 RecordJSReturnSite(expr);
3003 2995
3004 // Restore context register. 2996 // Restore context register.
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
3044 3036
3045 EmitVariableAssignment(this_var, Token::INIT_CONST, slot); 3037 EmitVariableAssignment(this_var, Token::INIT_CONST, slot);
3046 } 3038 }
3047 3039
3048 3040
3049 // See http://www.ecma-international.org/ecma-262/6.0/#sec-function-calls. 3041 // See http://www.ecma-international.org/ecma-262/6.0/#sec-function-calls.
3050 void FullCodeGenerator::PushCalleeAndWithBaseObject(Call* expr) { 3042 void FullCodeGenerator::PushCalleeAndWithBaseObject(Call* expr) {
3051 VariableProxy* callee = expr->expression()->AsVariableProxy(); 3043 VariableProxy* callee = expr->expression()->AsVariableProxy();
3052 if (callee->var()->IsLookupSlot()) { 3044 if (callee->var()->IsLookupSlot()) {
3053 Label slow, done; 3045 Label slow, done;
3054 SetSourcePosition(callee->position()); 3046 SetExpressionPosition(callee);
3055 { 3047 // Generate code for loading from variables potentially shadowed by
3056 PreservePositionScope scope(masm()->positions_recorder()); 3048 // eval-introduced variables.
3057 // Generate code for loading from variables potentially shadowed by 3049 EmitDynamicLookupFastCase(callee, NOT_INSIDE_TYPEOF, &slow, &done);
3058 // eval-introduced variables. 3050
3059 EmitDynamicLookupFastCase(callee, NOT_INSIDE_TYPEOF, &slow, &done);
3060 }
3061 __ bind(&slow); 3051 __ bind(&slow);
3062 // Call the runtime to find the function to call (returned in eax) and 3052 // Call the runtime to find the function to call (returned in eax) and
3063 // the object holding it (returned in edx). 3053 // the object holding it (returned in edx).
3064 __ push(context_register()); 3054 __ push(context_register());
3065 __ push(Immediate(callee->name())); 3055 __ push(Immediate(callee->name()));
3066 __ CallRuntime(Runtime::kLoadLookupSlot, 2); 3056 __ CallRuntime(Runtime::kLoadLookupSlot, 2);
3067 __ push(eax); // Function. 3057 __ push(eax); // Function.
3068 __ push(edx); // Receiver. 3058 __ push(edx); // Receiver.
3069 PrepareForBailoutForId(expr->LookupId(), NO_REGISTERS); 3059 PrepareForBailoutForId(expr->LookupId(), NO_REGISTERS);
3070 3060
(...skipping 28 matching lines...) Expand all
3099 Comment cmnt(masm_, "[ Call"); 3089 Comment cmnt(masm_, "[ Call");
3100 Expression* callee = expr->expression(); 3090 Expression* callee = expr->expression();
3101 Call::CallType call_type = expr->GetCallType(isolate()); 3091 Call::CallType call_type = expr->GetCallType(isolate());
3102 3092
3103 if (call_type == Call::POSSIBLY_EVAL_CALL) { 3093 if (call_type == Call::POSSIBLY_EVAL_CALL) {
3104 // In a call to eval, we first call RuntimeHidden_ResolvePossiblyDirectEval 3094 // In a call to eval, we first call RuntimeHidden_ResolvePossiblyDirectEval
3105 // to resolve the function we need to call. Then we call the resolved 3095 // to resolve the function we need to call. Then we call the resolved
3106 // function using the given arguments. 3096 // function using the given arguments.
3107 ZoneList<Expression*>* args = expr->arguments(); 3097 ZoneList<Expression*>* args = expr->arguments();
3108 int arg_count = args->length(); 3098 int arg_count = args->length();
3109 { PreservePositionScope pos_scope(masm()->positions_recorder());
3110 PushCalleeAndWithBaseObject(expr);
3111 3099
3112 // Push the arguments. 3100 PushCalleeAndWithBaseObject(expr);
3113 for (int i = 0; i < arg_count; i++) {
3114 VisitForStackValue(args->at(i));
3115 }
3116 3101
3117 // Push a copy of the function (found below the arguments) and 3102 // Push the arguments.
3118 // resolve eval. 3103 for (int i = 0; i < arg_count; i++) {
3119 __ push(Operand(esp, (arg_count + 1) * kPointerSize)); 3104 VisitForStackValue(args->at(i));
3120 EmitResolvePossiblyDirectEval(arg_count); 3105 }
3121 3106
3122 // Touch up the stack with the resolved function. 3107 // Push a copy of the function (found below the arguments) and
3123 __ mov(Operand(esp, (arg_count + 1) * kPointerSize), eax); 3108 // resolve eval.
3109 __ push(Operand(esp, (arg_count + 1) * kPointerSize));
3110 EmitResolvePossiblyDirectEval(arg_count);
3124 3111
3125 PrepareForBailoutForId(expr->EvalId(), NO_REGISTERS); 3112 // Touch up the stack with the resolved function.
3126 } 3113 __ mov(Operand(esp, (arg_count + 1) * kPointerSize), eax);
3127 // Record source position for debugger. 3114
3128 SetSourcePosition(expr->position()); 3115 PrepareForBailoutForId(expr->EvalId(), NO_REGISTERS);
3116
3117 SetExpressionPosition(expr);
3129 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS); 3118 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS);
3130 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize)); 3119 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize));
3131 __ CallStub(&stub); 3120 __ CallStub(&stub);
3132 RecordJSReturnSite(expr); 3121 RecordJSReturnSite(expr);
3133 // Restore context register. 3122 // Restore context register.
3134 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset)); 3123 __ mov(esi, Operand(ebp, StandardFrameConstants::kContextOffset));
3135 context()->DropAndPlug(1, eax); 3124 context()->DropAndPlug(1, eax);
3136 3125
3137 } else if (call_type == Call::GLOBAL_CALL) { 3126 } else if (call_type == Call::GLOBAL_CALL) {
3138 EmitCallWithLoadIC(expr); 3127 EmitCallWithLoadIC(expr);
3139 } else if (call_type == Call::LOOKUP_SLOT_CALL) { 3128 } else if (call_type == Call::LOOKUP_SLOT_CALL) {
3140 // Call to a lookup slot (dynamically introduced variable). 3129 // Call to a lookup slot (dynamically introduced variable).
3141 PushCalleeAndWithBaseObject(expr); 3130 PushCalleeAndWithBaseObject(expr);
3142 EmitCall(expr); 3131 EmitCall(expr);
3143 } else if (call_type == Call::PROPERTY_CALL) { 3132 } else if (call_type == Call::PROPERTY_CALL) {
3144 Property* property = callee->AsProperty(); 3133 Property* property = callee->AsProperty();
3145 bool is_named_call = property->key()->IsPropertyName(); 3134 bool is_named_call = property->key()->IsPropertyName();
3146 if (property->IsSuperAccess()) { 3135 if (property->IsSuperAccess()) {
3147 if (is_named_call) { 3136 if (is_named_call) {
3148 EmitSuperCallWithLoadIC(expr); 3137 EmitSuperCallWithLoadIC(expr);
3149 } else { 3138 } else {
3150 EmitKeyedSuperCallWithLoadIC(expr); 3139 EmitKeyedSuperCallWithLoadIC(expr);
3151 } 3140 }
3152 } else { 3141 } else {
3153 { 3142 VisitForStackValue(property->obj());
3154 PreservePositionScope scope(masm()->positions_recorder());
3155 VisitForStackValue(property->obj());
3156 }
3157 if (is_named_call) { 3143 if (is_named_call) {
3158 EmitCallWithLoadIC(expr); 3144 EmitCallWithLoadIC(expr);
3159 } else { 3145 } else {
3160 EmitKeyedCallWithLoadIC(expr, property->key()); 3146 EmitKeyedCallWithLoadIC(expr, property->key());
3161 } 3147 }
3162 } 3148 }
3163 } else if (call_type == Call::SUPER_CALL) { 3149 } else if (call_type == Call::SUPER_CALL) {
3164 EmitSuperConstructorCall(expr); 3150 EmitSuperConstructorCall(expr);
3165 } else { 3151 } else {
3166 DCHECK(call_type == Call::OTHER_CALL); 3152 DCHECK(call_type == Call::OTHER_CALL);
3167 // Call to an arbitrary expression not handled specially above. 3153 // Call to an arbitrary expression not handled specially above.
3168 { PreservePositionScope scope(masm()->positions_recorder()); 3154 VisitForStackValue(callee);
3169 VisitForStackValue(callee);
3170 }
3171 __ push(Immediate(isolate()->factory()->undefined_value())); 3155 __ push(Immediate(isolate()->factory()->undefined_value()));
3172 // Emit function call. 3156 // Emit function call.
3173 EmitCall(expr); 3157 EmitCall(expr);
3174 } 3158 }
3175 3159
3176 #ifdef DEBUG 3160 #ifdef DEBUG
3177 // RecordJSReturnSite should have been called. 3161 // RecordJSReturnSite should have been called.
3178 DCHECK(expr->return_is_recorded_); 3162 DCHECK(expr->return_is_recorded_);
3179 #endif 3163 #endif
3180 } 3164 }
(...skipping 13 matching lines...) Expand all
3194 3178
3195 // Push the arguments ("left-to-right") on the stack. 3179 // Push the arguments ("left-to-right") on the stack.
3196 ZoneList<Expression*>* args = expr->arguments(); 3180 ZoneList<Expression*>* args = expr->arguments();
3197 int arg_count = args->length(); 3181 int arg_count = args->length();
3198 for (int i = 0; i < arg_count; i++) { 3182 for (int i = 0; i < arg_count; i++) {
3199 VisitForStackValue(args->at(i)); 3183 VisitForStackValue(args->at(i));
3200 } 3184 }
3201 3185
3202 // Call the construct call builtin that handles allocation and 3186 // Call the construct call builtin that handles allocation and
3203 // constructor invocation. 3187 // constructor invocation.
3204 SetSourcePosition(expr->position()); 3188 SetExpressionPosition(expr);
3205 3189
3206 // Load function and argument count into edi and eax. 3190 // Load function and argument count into edi and eax.
3207 __ Move(eax, Immediate(arg_count)); 3191 __ Move(eax, Immediate(arg_count));
3208 __ mov(edi, Operand(esp, arg_count * kPointerSize)); 3192 __ mov(edi, Operand(esp, arg_count * kPointerSize));
3209 3193
3210 // Record call targets in unoptimized code. 3194 // Record call targets in unoptimized code.
3211 if (FLAG_pretenuring_call_new) { 3195 if (FLAG_pretenuring_call_new) {
3212 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot()); 3196 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot());
3213 DCHECK(expr->AllocationSiteFeedbackSlot().ToInt() == 3197 DCHECK(expr->AllocationSiteFeedbackSlot().ToInt() ==
3214 expr->CallNewFeedbackSlot().ToInt() + 1); 3198 expr->CallNewFeedbackSlot().ToInt() + 1);
(...skipping 22 matching lines...) Expand all
3237 3221
3238 // Push the arguments ("left-to-right") on the stack. 3222 // Push the arguments ("left-to-right") on the stack.
3239 ZoneList<Expression*>* args = expr->arguments(); 3223 ZoneList<Expression*>* args = expr->arguments();
3240 int arg_count = args->length(); 3224 int arg_count = args->length();
3241 for (int i = 0; i < arg_count; i++) { 3225 for (int i = 0; i < arg_count; i++) {
3242 VisitForStackValue(args->at(i)); 3226 VisitForStackValue(args->at(i));
3243 } 3227 }
3244 3228
3245 // Call the construct call builtin that handles allocation and 3229 // Call the construct call builtin that handles allocation and
3246 // constructor invocation. 3230 // constructor invocation.
3247 SetSourcePosition(expr->position()); 3231 SetExpressionPosition(expr);
3248 3232
3249 // Load function and argument count into edi and eax. 3233 // Load function and argument count into edi and eax.
3250 __ Move(eax, Immediate(arg_count)); 3234 __ Move(eax, Immediate(arg_count));
3251 __ mov(edi, Operand(esp, arg_count * kPointerSize)); 3235 __ mov(edi, Operand(esp, arg_count * kPointerSize));
3252 3236
3253 // Record call targets in unoptimized code. 3237 // Record call targets in unoptimized code.
3254 if (FLAG_pretenuring_call_new) { 3238 if (FLAG_pretenuring_call_new) {
3255 UNREACHABLE(); 3239 UNREACHABLE();
3256 /* TODO(dslomov): support pretenuring. 3240 /* TODO(dslomov): support pretenuring.
3257 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot()); 3241 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot());
(...skipping 1402 matching lines...) Expand 10 before | Expand all | Expand 10 after
4660 __ mov(LoadDescriptor::SlotRegister(), 4644 __ mov(LoadDescriptor::SlotRegister(),
4661 Immediate(SmiFromSlot(expr->CallRuntimeFeedbackSlot()))); 4645 Immediate(SmiFromSlot(expr->CallRuntimeFeedbackSlot())));
4662 CallLoadIC(NOT_CONTEXTUAL); 4646 CallLoadIC(NOT_CONTEXTUAL);
4663 } 4647 }
4664 4648
4665 4649
4666 void FullCodeGenerator::EmitCallJSRuntimeFunction(CallRuntime* expr) { 4650 void FullCodeGenerator::EmitCallJSRuntimeFunction(CallRuntime* expr) {
4667 ZoneList<Expression*>* args = expr->arguments(); 4651 ZoneList<Expression*>* args = expr->arguments();
4668 int arg_count = args->length(); 4652 int arg_count = args->length();
4669 4653
4670 // Record source position of the IC call. 4654 SetExpressionPosition(expr);
4671 SetSourcePosition(expr->position());
4672 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS); 4655 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS);
4673 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize)); 4656 __ mov(edi, Operand(esp, (arg_count + 1) * kPointerSize));
4674 __ CallStub(&stub); 4657 __ CallStub(&stub);
4675 } 4658 }
4676 4659
4677 4660
4678 void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { 4661 void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) {
4679 ZoneList<Expression*>* args = expr->arguments(); 4662 ZoneList<Expression*>* args = expr->arguments();
4680 int arg_count = args->length(); 4663 int arg_count = args->length();
4681 4664
(...skipping 159 matching lines...) Expand 10 before | Expand all | Expand 10 after
4841 default: 4824 default:
4842 UNREACHABLE(); 4825 UNREACHABLE();
4843 } 4826 }
4844 } 4827 }
4845 4828
4846 4829
4847 void FullCodeGenerator::VisitCountOperation(CountOperation* expr) { 4830 void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
4848 DCHECK(expr->expression()->IsValidReferenceExpression()); 4831 DCHECK(expr->expression()->IsValidReferenceExpression());
4849 4832
4850 Comment cmnt(masm_, "[ CountOperation"); 4833 Comment cmnt(masm_, "[ CountOperation");
4851 SetSourcePosition(expr->position());
4852 4834
4853 Property* prop = expr->expression()->AsProperty(); 4835 Property* prop = expr->expression()->AsProperty();
4854 LhsKind assign_type = Property::GetAssignType(prop); 4836 LhsKind assign_type = Property::GetAssignType(prop);
4855 4837
4856 // Evaluate expression and get value. 4838 // Evaluate expression and get value.
4857 if (assign_type == VARIABLE) { 4839 if (assign_type == VARIABLE) {
4858 DCHECK(expr->expression()->AsVariableProxy()->var() != NULL); 4840 DCHECK(expr->expression()->AsVariableProxy()->var() != NULL);
4859 AccumulatorValueContext context(this); 4841 AccumulatorValueContext context(this);
4860 EmitVariableLoad(expr->expression()->AsVariableProxy()); 4842 EmitVariableLoad(expr->expression()->AsVariableProxy());
4861 } else { 4843 } else {
(...skipping 130 matching lines...) Expand 10 before | Expand all | Expand 10 after
4992 case KEYED_PROPERTY: 4974 case KEYED_PROPERTY:
4993 __ mov(Operand(esp, 2 * kPointerSize), eax); 4975 __ mov(Operand(esp, 2 * kPointerSize), eax);
4994 break; 4976 break;
4995 case KEYED_SUPER_PROPERTY: 4977 case KEYED_SUPER_PROPERTY:
4996 __ mov(Operand(esp, 3 * kPointerSize), eax); 4978 __ mov(Operand(esp, 3 * kPointerSize), eax);
4997 break; 4979 break;
4998 } 4980 }
4999 } 4981 }
5000 } 4982 }
5001 4983
5002 // Record position before stub call. 4984 SetExpressionPosition(expr);
5003 SetSourcePosition(expr->position());
5004 4985
5005 // Call stub for +1/-1. 4986 // Call stub for +1/-1.
5006 __ bind(&stub_call); 4987 __ bind(&stub_call);
5007 __ mov(edx, eax); 4988 __ mov(edx, eax);
5008 __ mov(eax, Immediate(Smi::FromInt(1))); 4989 __ mov(eax, Immediate(Smi::FromInt(1)));
5009 Handle<Code> code = CodeFactory::BinaryOpIC(isolate(), expr->binary_op(), 4990 Handle<Code> code = CodeFactory::BinaryOpIC(isolate(), expr->binary_op(),
5010 strength(language_mode())).code(); 4991 strength(language_mode())).code();
5011 CallIC(code, expr->CountBinOpFeedbackId()); 4992 CallIC(code, expr->CountBinOpFeedbackId());
5012 patch_site.EmitPatchInfo(); 4993 patch_site.EmitPatchInfo();
5013 __ bind(&done); 4994 __ bind(&done);
(...skipping 200 matching lines...) Expand 10 before | Expand all | Expand 10 after
5214 Split(zero, if_true, if_false, fall_through); 5195 Split(zero, if_true, if_false, fall_through);
5215 } else { 5196 } else {
5216 if (if_false != fall_through) __ jmp(if_false); 5197 if (if_false != fall_through) __ jmp(if_false);
5217 } 5198 }
5218 context()->Plug(if_true, if_false); 5199 context()->Plug(if_true, if_false);
5219 } 5200 }
5220 5201
5221 5202
5222 void FullCodeGenerator::VisitCompareOperation(CompareOperation* expr) { 5203 void FullCodeGenerator::VisitCompareOperation(CompareOperation* expr) {
5223 Comment cmnt(masm_, "[ CompareOperation"); 5204 Comment cmnt(masm_, "[ CompareOperation");
5224 SetSourcePosition(expr->position()); 5205 SetExpressionPosition(expr);
5225 5206
5226 // First we try a fast inlined version of the compare when one of 5207 // First we try a fast inlined version of the compare when one of
5227 // the operands is a literal. 5208 // the operands is a literal.
5228 if (TryLiteralCompare(expr)) return; 5209 if (TryLiteralCompare(expr)) return;
5229 5210
5230 // Always perform the comparison for its control flow. Pack the result 5211 // Always perform the comparison for its control flow. Pack the result
5231 // into the expression's context after the comparison is performed. 5212 // into the expression's context after the comparison is performed.
5232 Label materialize_true, materialize_false; 5213 Label materialize_true, materialize_false;
5233 Label* if_true = NULL; 5214 Label* if_true = NULL;
5234 Label* if_false = NULL; 5215 Label* if_false = NULL;
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
5268 if (inline_smi_code) { 5249 if (inline_smi_code) {
5269 Label slow_case; 5250 Label slow_case;
5270 __ mov(ecx, edx); 5251 __ mov(ecx, edx);
5271 __ or_(ecx, eax); 5252 __ or_(ecx, eax);
5272 patch_site.EmitJumpIfNotSmi(ecx, &slow_case, Label::kNear); 5253 patch_site.EmitJumpIfNotSmi(ecx, &slow_case, Label::kNear);
5273 __ cmp(edx, eax); 5254 __ cmp(edx, eax);
5274 Split(cc, if_true, if_false, NULL); 5255 Split(cc, if_true, if_false, NULL);
5275 __ bind(&slow_case); 5256 __ bind(&slow_case);
5276 } 5257 }
5277 5258
5278 // Record position and call the compare IC.
5279 SetSourcePosition(expr->position());
5280 Handle<Code> ic = CodeFactory::CompareIC( 5259 Handle<Code> ic = CodeFactory::CompareIC(
5281 isolate(), op, strength(language_mode())).code(); 5260 isolate(), op, strength(language_mode())).code();
5282 CallIC(ic, expr->CompareOperationFeedbackId()); 5261 CallIC(ic, expr->CompareOperationFeedbackId());
5283 patch_site.EmitPatchInfo(); 5262 patch_site.EmitPatchInfo();
5284 5263
5285 PrepareForBailoutBeforeSplit(expr, true, if_true, if_false); 5264 PrepareForBailoutBeforeSplit(expr, true, if_true, if_false);
5286 __ test(eax, eax); 5265 __ test(eax, eax);
5287 Split(cc, if_true, if_false, fall_through); 5266 Split(cc, if_true, if_false, fall_through);
5288 } 5267 }
5289 } 5268 }
(...skipping 219 matching lines...) Expand 10 before | Expand all | Expand 10 after
5509 Assembler::target_address_at(call_target_address, 5488 Assembler::target_address_at(call_target_address,
5510 unoptimized_code)); 5489 unoptimized_code));
5511 return OSR_AFTER_STACK_CHECK; 5490 return OSR_AFTER_STACK_CHECK;
5512 } 5491 }
5513 5492
5514 5493
5515 } // namespace internal 5494 } // namespace internal
5516 } // namespace v8 5495 } // namespace v8
5517 5496
5518 #endif // V8_TARGET_ARCH_IA32 5497 #endif // V8_TARGET_ARCH_IA32
OLDNEW
« no previous file with comments | « src/ia32/debug-ia32.cc ('k') | src/mips/debug-mips.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698