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

Side by Side Diff: src/x64/full-codegen-x64.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/x64/debug-x64.cc ('k') | test/cctest/test-debug.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-factory.h" 9 #include "src/code-factory.h"
10 #include "src/code-stubs.h" 10 #include "src/code-stubs.h"
(...skipping 454 matching lines...) Expand 10 before | Expand all | Expand 10 after
465 __ call(isolate()->builtins()->InterruptCheck(), 465 __ call(isolate()->builtins()->InterruptCheck(),
466 RelocInfo::CODE_TARGET); 466 RelocInfo::CODE_TARGET);
467 __ Pop(rax); 467 __ Pop(rax);
468 EmitProfilingCounterReset(); 468 EmitProfilingCounterReset();
469 __ bind(&ok); 469 __ bind(&ok);
470 #ifdef DEBUG 470 #ifdef DEBUG
471 // Add a label for checking the size of the code used for returning. 471 // Add a label for checking the size of the code used for returning.
472 Label check_exit_codesize; 472 Label check_exit_codesize;
473 masm_->bind(&check_exit_codesize); 473 masm_->bind(&check_exit_codesize);
474 #endif 474 #endif
475 CodeGenerator::RecordPositions(masm_, function()->end_position() - 1); 475 SetReturnPosition(function());
476 __ RecordJSReturn(); 476 __ RecordJSReturn();
477 // Do not use the leave instruction here because it is too short to 477 // Do not use the leave instruction here because it is too short to
478 // patch with the code required by the debugger. 478 // patch with the code required by the debugger.
479 __ movp(rsp, rbp); 479 __ movp(rsp, rbp);
480 __ popq(rbp); 480 __ popq(rbp);
481 int no_frame_start = masm_->pc_offset(); 481 int no_frame_start = masm_->pc_offset();
482 482
483 int arg_count = info_->scope()->num_parameters() + 1; 483 int arg_count = info_->scope()->num_parameters() + 1;
484 int arguments_bytes = arg_count * kPointerSize; 484 int arguments_bytes = arg_count * kPointerSize;
485 __ Ret(arguments_bytes, rcx); 485 __ Ret(arguments_bytes, rcx);
(...skipping 553 matching lines...) Expand 10 before | Expand all | Expand 10 after
1039 patch_site.EmitJumpIfNotSmi(rcx, &slow_case, Label::kNear); 1039 patch_site.EmitJumpIfNotSmi(rcx, &slow_case, Label::kNear);
1040 1040
1041 __ cmpp(rdx, rax); 1041 __ cmpp(rdx, rax);
1042 __ j(not_equal, &next_test); 1042 __ j(not_equal, &next_test);
1043 __ Drop(1); // Switch value is no longer needed. 1043 __ Drop(1); // Switch value is no longer needed.
1044 __ jmp(clause->body_target()); 1044 __ jmp(clause->body_target());
1045 __ bind(&slow_case); 1045 __ bind(&slow_case);
1046 } 1046 }
1047 1047
1048 // Record position before stub call for type feedback. 1048 // Record position before stub call for type feedback.
1049 SetSourcePosition(clause->position()); 1049 SetExpressionPosition(clause);
1050 Handle<Code> ic = CodeFactory::CompareIC(isolate(), Token::EQ_STRICT, 1050 Handle<Code> ic = CodeFactory::CompareIC(isolate(), Token::EQ_STRICT,
1051 strength(language_mode())).code(); 1051 strength(language_mode())).code();
1052 CallIC(ic, clause->CompareId()); 1052 CallIC(ic, clause->CompareId());
1053 patch_site.EmitPatchInfo(); 1053 patch_site.EmitPatchInfo();
1054 1054
1055 Label skip; 1055 Label skip;
1056 __ jmp(&skip, Label::kNear); 1056 __ jmp(&skip, Label::kNear);
1057 PrepareForBailout(clause, TOS_REG); 1057 PrepareForBailout(clause, TOS_REG);
1058 __ CompareRoot(rax, Heap::kTrueValueRootIndex); 1058 __ CompareRoot(rax, Heap::kTrueValueRootIndex);
1059 __ j(not_equal, &next_test); 1059 __ j(not_equal, &next_test);
(...skipping 26 matching lines...) Expand all
1086 VisitStatements(clause->statements()); 1086 VisitStatements(clause->statements());
1087 } 1087 }
1088 1088
1089 __ bind(nested_statement.break_label()); 1089 __ bind(nested_statement.break_label());
1090 PrepareForBailoutForId(stmt->ExitId(), NO_REGISTERS); 1090 PrepareForBailoutForId(stmt->ExitId(), NO_REGISTERS);
1091 } 1091 }
1092 1092
1093 1093
1094 void FullCodeGenerator::VisitForInStatement(ForInStatement* stmt) { 1094 void FullCodeGenerator::VisitForInStatement(ForInStatement* stmt) {
1095 Comment cmnt(masm_, "[ ForInStatement"); 1095 Comment cmnt(masm_, "[ ForInStatement");
1096 SetStatementPosition(stmt, SKIP_BREAK);
1097
1096 FeedbackVectorSlot slot = stmt->ForInFeedbackSlot(); 1098 FeedbackVectorSlot slot = stmt->ForInFeedbackSlot();
1097 SetStatementPosition(stmt);
1098 1099
1099 Label loop, exit; 1100 Label loop, exit;
1100 ForIn loop_statement(this, stmt); 1101 ForIn loop_statement(this, stmt);
1101 increment_loop_depth(); 1102 increment_loop_depth();
1102 1103
1103 // Get the object to enumerate over. If the object is null or undefined, skip 1104 // Get the object to enumerate over. If the object is null or undefined, skip
1104 // over the loop. See ECMA-262 version 5, section 12.6.4. 1105 // over the loop. See ECMA-262 version 5, section 12.6.4.
1105 SetExpressionPosition(stmt->enumerable()); 1106 SetExpressionAsStatementPosition(stmt->enumerable());
1106 VisitForAccumulatorValue(stmt->enumerable()); 1107 VisitForAccumulatorValue(stmt->enumerable());
1107 __ CompareRoot(rax, Heap::kUndefinedValueRootIndex); 1108 __ CompareRoot(rax, Heap::kUndefinedValueRootIndex);
1108 __ j(equal, &exit); 1109 __ j(equal, &exit);
1109 Register null_value = rdi; 1110 Register null_value = rdi;
1110 __ LoadRoot(null_value, Heap::kNullValueRootIndex); 1111 __ LoadRoot(null_value, Heap::kNullValueRootIndex);
1111 __ cmpp(rax, null_value); 1112 __ cmpp(rax, null_value);
1112 __ j(equal, &exit); 1113 __ j(equal, &exit);
1113 1114
1114 PrepareForBailoutForId(stmt->PrepareId(), TOS_REG); 1115 PrepareForBailoutForId(stmt->PrepareId(), TOS_REG);
1115 1116
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
1199 __ bind(&non_proxy); 1200 __ bind(&non_proxy);
1200 __ Push(rbx); // Smi 1201 __ Push(rbx); // Smi
1201 __ Push(rax); // Array 1202 __ Push(rax); // Array
1202 __ movp(rax, FieldOperand(rax, FixedArray::kLengthOffset)); 1203 __ movp(rax, FieldOperand(rax, FixedArray::kLengthOffset));
1203 __ Push(rax); // Fixed array length (as smi). 1204 __ Push(rax); // Fixed array length (as smi).
1204 __ Push(Smi::FromInt(0)); // Initial index. 1205 __ Push(Smi::FromInt(0)); // Initial index.
1205 1206
1206 // Generate code for doing the condition check. 1207 // Generate code for doing the condition check.
1207 PrepareForBailoutForId(stmt->BodyId(), NO_REGISTERS); 1208 PrepareForBailoutForId(stmt->BodyId(), NO_REGISTERS);
1208 __ bind(&loop); 1209 __ bind(&loop);
1209 SetExpressionPosition(stmt->each()); 1210 SetExpressionAsStatementPosition(stmt->each());
1210 1211
1211 __ movp(rax, Operand(rsp, 0 * kPointerSize)); // Get the current index. 1212 __ movp(rax, Operand(rsp, 0 * kPointerSize)); // Get the current index.
1212 __ cmpp(rax, Operand(rsp, 1 * kPointerSize)); // Compare to the array length. 1213 __ cmpp(rax, Operand(rsp, 1 * kPointerSize)); // Compare to the array length.
1213 __ j(above_equal, loop_statement.break_label()); 1214 __ j(above_equal, loop_statement.break_label());
1214 1215
1215 // Get the current entry of the array into register rbx. 1216 // Get the current entry of the array into register rbx.
1216 __ movp(rbx, Operand(rsp, 2 * kPointerSize)); 1217 __ movp(rbx, Operand(rsp, 2 * kPointerSize));
1217 SmiIndex index = masm()->SmiToIndex(rax, rax, kPointerSizeLog2); 1218 SmiIndex index = masm()->SmiToIndex(rax, rax, kPointerSizeLog2);
1218 __ movp(rbx, FieldOperand(rbx, 1219 __ movp(rbx, FieldOperand(rbx,
1219 index.reg, 1220 index.reg,
(...skipping 228 matching lines...) Expand 10 before | Expand all | Expand 10 after
1448 __ CallRuntime(Runtime::kThrowReferenceError, 1); 1449 __ CallRuntime(Runtime::kThrowReferenceError, 1);
1449 } 1450 }
1450 } 1451 }
1451 __ jmp(done); 1452 __ jmp(done);
1452 } 1453 }
1453 } 1454 }
1454 1455
1455 1456
1456 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) { 1457 void FullCodeGenerator::EmitVariableLoad(VariableProxy* proxy) {
1457 // Record position before possible IC call. 1458 // Record position before possible IC call.
1458 SetSourcePosition(proxy->position()); 1459 SetExpressionPosition(proxy);
1459 PrepareForBailoutForId(proxy->BeforeId(), NO_REGISTERS); 1460 PrepareForBailoutForId(proxy->BeforeId(), NO_REGISTERS);
1460 Variable* var = proxy->var(); 1461 Variable* var = proxy->var();
1461 1462
1462 // Three cases: global variables, lookup variables, and all other types of 1463 // Three cases: global variables, lookup variables, and all other types of
1463 // variables. 1464 // variables.
1464 switch (var->location()) { 1465 switch (var->location()) {
1465 case Variable::UNALLOCATED: { 1466 case Variable::UNALLOCATED: {
1466 Comment cmnt(masm_, "[ Global variable"); 1467 Comment cmnt(masm_, "[ Global variable");
1467 __ Move(LoadDescriptor::NameRegister(), var->name()); 1468 __ Move(LoadDescriptor::NameRegister(), var->name());
1468 __ movp(LoadDescriptor::ReceiverRegister(), GlobalObjectOperand()); 1469 __ movp(LoadDescriptor::ReceiverRegister(), GlobalObjectOperand());
(...skipping 473 matching lines...) Expand 10 before | Expand all | Expand 10 after
1942 } else { 1943 } else {
1943 context()->Plug(rax); 1944 context()->Plug(rax);
1944 } 1945 }
1945 } 1946 }
1946 1947
1947 1948
1948 void FullCodeGenerator::VisitAssignment(Assignment* expr) { 1949 void FullCodeGenerator::VisitAssignment(Assignment* expr) {
1949 DCHECK(expr->target()->IsValidReferenceExpression()); 1950 DCHECK(expr->target()->IsValidReferenceExpression());
1950 1951
1951 Comment cmnt(masm_, "[ Assignment"); 1952 Comment cmnt(masm_, "[ Assignment");
1953 SetExpressionPosition(expr, INSERT_BREAK);
1952 1954
1953 Property* property = expr->target()->AsProperty(); 1955 Property* property = expr->target()->AsProperty();
1954 LhsKind assign_type = Property::GetAssignType(property); 1956 LhsKind assign_type = Property::GetAssignType(property);
1955 1957
1956 // Evaluate LHS expression. 1958 // Evaluate LHS expression.
1957 switch (assign_type) { 1959 switch (assign_type) {
1958 case VARIABLE: 1960 case VARIABLE:
1959 // Nothing to do here. 1961 // Nothing to do here.
1960 break; 1962 break;
1961 case NAMED_PROPERTY: 1963 case NAMED_PROPERTY:
(...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after
2030 EmitKeyedPropertyLoad(property); 2032 EmitKeyedPropertyLoad(property);
2031 PrepareForBailoutForId(property->LoadId(), TOS_REG); 2033 PrepareForBailoutForId(property->LoadId(), TOS_REG);
2032 break; 2034 break;
2033 } 2035 }
2034 } 2036 }
2035 2037
2036 Token::Value op = expr->binary_op(); 2038 Token::Value op = expr->binary_op();
2037 __ Push(rax); // Left operand goes on the stack. 2039 __ Push(rax); // Left operand goes on the stack.
2038 VisitForAccumulatorValue(expr->value()); 2040 VisitForAccumulatorValue(expr->value());
2039 2041
2040 SetSourcePosition(expr->position() + 1);
2041 AccumulatorValueContext context(this); 2042 AccumulatorValueContext context(this);
2042 if (ShouldInlineSmiCase(op)) { 2043 if (ShouldInlineSmiCase(op)) {
2043 EmitInlineSmiBinaryOp(expr->binary_operation(), 2044 EmitInlineSmiBinaryOp(expr->binary_operation(),
2044 op, 2045 op,
2045 expr->target(), 2046 expr->target(),
2046 expr->value()); 2047 expr->value());
2047 } else { 2048 } else {
2048 EmitBinaryOp(expr->binary_operation(), op); 2049 EmitBinaryOp(expr->binary_operation(), op);
2049 } 2050 }
2050 // Deoptimization point in case the binary operation may have side effects. 2051 // Deoptimization point in case the binary operation may have side effects.
2051 PrepareForBailout(expr->binary_operation(), TOS_REG); 2052 PrepareForBailout(expr->binary_operation(), TOS_REG);
2052 } else { 2053 } else {
2053 VisitForAccumulatorValue(expr->value()); 2054 VisitForAccumulatorValue(expr->value());
2054 } 2055 }
2055 2056
2056 // Record source position before possible IC call. 2057 SetExpressionPosition(expr);
2057 SetSourcePosition(expr->position());
2058 2058
2059 // Store the value. 2059 // Store the value.
2060 switch (assign_type) { 2060 switch (assign_type) {
2061 case VARIABLE: 2061 case VARIABLE:
2062 EmitVariableAssignment(expr->target()->AsVariableProxy()->var(), 2062 EmitVariableAssignment(expr->target()->AsVariableProxy()->var(),
2063 expr->op(), expr->AssignmentSlot()); 2063 expr->op(), expr->AssignmentSlot());
2064 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2064 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2065 context()->Plug(rax); 2065 context()->Plug(rax);
2066 break; 2066 break;
2067 case NAMED_PROPERTY: 2067 case NAMED_PROPERTY:
2068 EmitNamedPropertyAssignment(expr); 2068 EmitNamedPropertyAssignment(expr);
2069 break; 2069 break;
2070 case NAMED_SUPER_PROPERTY: 2070 case NAMED_SUPER_PROPERTY:
2071 EmitNamedSuperPropertyStore(property); 2071 EmitNamedSuperPropertyStore(property);
2072 context()->Plug(rax); 2072 context()->Plug(rax);
2073 break; 2073 break;
2074 case KEYED_SUPER_PROPERTY: 2074 case KEYED_SUPER_PROPERTY:
2075 EmitKeyedSuperPropertyStore(property); 2075 EmitKeyedSuperPropertyStore(property);
2076 context()->Plug(rax); 2076 context()->Plug(rax);
2077 break; 2077 break;
2078 case KEYED_PROPERTY: 2078 case KEYED_PROPERTY:
2079 EmitKeyedPropertyAssignment(expr); 2079 EmitKeyedPropertyAssignment(expr);
2080 break; 2080 break;
2081 } 2081 }
2082 } 2082 }
2083 2083
2084 2084
2085 void FullCodeGenerator::VisitYield(Yield* expr) { 2085 void FullCodeGenerator::VisitYield(Yield* expr) {
2086 Comment cmnt(masm_, "[ Yield"); 2086 Comment cmnt(masm_, "[ Yield");
2087 SetExpressionPosition(expr);
2088
2087 // Evaluate yielded value first; the initial iterator definition depends on 2089 // Evaluate yielded value first; the initial iterator definition depends on
2088 // this. It stays on the stack while we update the iterator. 2090 // this. It stays on the stack while we update the iterator.
2089 VisitForStackValue(expr->expression()); 2091 VisitForStackValue(expr->expression());
2090 2092
2091 switch (expr->yield_kind()) { 2093 switch (expr->yield_kind()) {
2092 case Yield::kSuspend: 2094 case Yield::kSuspend:
2093 // Pop value from top-of-stack slot; box result into result register. 2095 // Pop value from top-of-stack slot; box result into result register.
2094 EmitCreateIteratorResult(false); 2096 EmitCreateIteratorResult(false);
2095 __ Push(result_register()); 2097 __ Push(result_register());
2096 // Fall through. 2098 // Fall through.
(...skipping 266 matching lines...) Expand 10 before | Expand all | Expand 10 after
2363 rdx); 2365 rdx);
2364 2366
2365 // Only the value field needs a write barrier, as the other values are in the 2367 // Only the value field needs a write barrier, as the other values are in the
2366 // root set. 2368 // root set.
2367 __ RecordWriteField(rax, JSGeneratorObject::kResultValuePropertyOffset, 2369 __ RecordWriteField(rax, JSGeneratorObject::kResultValuePropertyOffset,
2368 rcx, rdx, kDontSaveFPRegs); 2370 rcx, rdx, kDontSaveFPRegs);
2369 } 2371 }
2370 2372
2371 2373
2372 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) { 2374 void FullCodeGenerator::EmitNamedPropertyLoad(Property* prop) {
2373 SetSourcePosition(prop->position()); 2375 SetExpressionPosition(prop);
2374 Literal* key = prop->key()->AsLiteral(); 2376 Literal* key = prop->key()->AsLiteral();
2375 DCHECK(!prop->IsSuperAccess()); 2377 DCHECK(!prop->IsSuperAccess());
2376 2378
2377 __ Move(LoadDescriptor::NameRegister(), key->value()); 2379 __ Move(LoadDescriptor::NameRegister(), key->value());
2378 __ Move(LoadDescriptor::SlotRegister(), 2380 __ Move(LoadDescriptor::SlotRegister(),
2379 SmiFromSlot(prop->PropertyFeedbackSlot())); 2381 SmiFromSlot(prop->PropertyFeedbackSlot()));
2380 CallLoadIC(NOT_CONTEXTUAL, language_mode()); 2382 CallLoadIC(NOT_CONTEXTUAL, language_mode());
2381 } 2383 }
2382 2384
2383 2385
2384 void FullCodeGenerator::EmitNamedSuperPropertyLoad(Property* prop) { 2386 void FullCodeGenerator::EmitNamedSuperPropertyLoad(Property* prop) {
2385 // Stack: receiver, home_object 2387 // Stack: receiver, home_object
2386 SetSourcePosition(prop->position()); 2388 SetExpressionPosition(prop);
2387 Literal* key = prop->key()->AsLiteral(); 2389 Literal* key = prop->key()->AsLiteral();
2388 DCHECK(!key->value()->IsSmi()); 2390 DCHECK(!key->value()->IsSmi());
2389 DCHECK(prop->IsSuperAccess()); 2391 DCHECK(prop->IsSuperAccess());
2390 2392
2391 __ Push(key->value()); 2393 __ Push(key->value());
2392 __ Push(Smi::FromInt(language_mode())); 2394 __ Push(Smi::FromInt(language_mode()));
2393 __ CallRuntime(Runtime::kLoadFromSuper, 4); 2395 __ CallRuntime(Runtime::kLoadFromSuper, 4);
2394 } 2396 }
2395 2397
2396 2398
2397 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) { 2399 void FullCodeGenerator::EmitKeyedPropertyLoad(Property* prop) {
2398 SetSourcePosition(prop->position()); 2400 SetExpressionPosition(prop);
2399 Handle<Code> ic = CodeFactory::KeyedLoadIC(isolate(), language_mode()).code(); 2401 Handle<Code> ic = CodeFactory::KeyedLoadIC(isolate(), language_mode()).code();
2400 __ Move(LoadDescriptor::SlotRegister(), 2402 __ Move(LoadDescriptor::SlotRegister(),
2401 SmiFromSlot(prop->PropertyFeedbackSlot())); 2403 SmiFromSlot(prop->PropertyFeedbackSlot()));
2402 CallIC(ic); 2404 CallIC(ic);
2403 } 2405 }
2404 2406
2405 2407
2406 void FullCodeGenerator::EmitKeyedSuperPropertyLoad(Property* prop) { 2408 void FullCodeGenerator::EmitKeyedSuperPropertyLoad(Property* prop) {
2407 // Stack: receiver, home_object, key. 2409 // Stack: receiver, home_object, key.
2410 SetExpressionPosition(prop);
2408 __ Push(Smi::FromInt(language_mode())); 2411 __ Push(Smi::FromInt(language_mode()));
2409 SetSourcePosition(prop->position());
2410
2411 __ CallRuntime(Runtime::kLoadKeyedFromSuper, 4); 2412 __ CallRuntime(Runtime::kLoadKeyedFromSuper, 4);
2412 } 2413 }
2413 2414
2414 2415
2415 void FullCodeGenerator::EmitInlineSmiBinaryOp(BinaryOperation* expr, 2416 void FullCodeGenerator::EmitInlineSmiBinaryOp(BinaryOperation* expr,
2416 Token::Value op, 2417 Token::Value op,
2417 Expression* left, 2418 Expression* left,
2418 Expression* right) { 2419 Expression* right) {
2419 // Do combined smi check of the operands. Left operand is on the 2420 // Do combined smi check of the operands. Left operand is on the
2420 // stack (popped into rdx). Right operand is in rax but moved into 2421 // stack (popped into rdx). Right operand is in rax but moved into
(...skipping 310 matching lines...) Expand 10 before | Expand all | Expand 10 after
2731 } 2732 }
2732 } 2733 }
2733 2734
2734 2735
2735 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) { 2736 void FullCodeGenerator::EmitNamedPropertyAssignment(Assignment* expr) {
2736 // Assignment to a property, using a named store IC. 2737 // Assignment to a property, using a named store IC.
2737 Property* prop = expr->target()->AsProperty(); 2738 Property* prop = expr->target()->AsProperty();
2738 DCHECK(prop != NULL); 2739 DCHECK(prop != NULL);
2739 DCHECK(prop->key()->IsLiteral()); 2740 DCHECK(prop->key()->IsLiteral());
2740 2741
2741 // Record source code position before IC call.
2742 SetSourcePosition(expr->position());
2743 __ Move(StoreDescriptor::NameRegister(), prop->key()->AsLiteral()->value()); 2742 __ Move(StoreDescriptor::NameRegister(), prop->key()->AsLiteral()->value());
2744 __ Pop(StoreDescriptor::ReceiverRegister()); 2743 __ Pop(StoreDescriptor::ReceiverRegister());
2745 if (FLAG_vector_stores) { 2744 if (FLAG_vector_stores) {
2746 EmitLoadStoreICSlot(expr->AssignmentSlot()); 2745 EmitLoadStoreICSlot(expr->AssignmentSlot());
2747 CallStoreIC(); 2746 CallStoreIC();
2748 } else { 2747 } else {
2749 CallStoreIC(expr->AssignmentFeedbackId()); 2748 CallStoreIC(expr->AssignmentFeedbackId());
2750 } 2749 }
2751 2750
2752 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2751 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
(...skipping 26 matching lines...) Expand all
2779 __ Push(rax); 2778 __ Push(rax);
2780 __ CallRuntime( 2779 __ CallRuntime(
2781 (is_strict(language_mode()) ? Runtime::kStoreKeyedToSuper_Strict 2780 (is_strict(language_mode()) ? Runtime::kStoreKeyedToSuper_Strict
2782 : Runtime::kStoreKeyedToSuper_Sloppy), 2781 : Runtime::kStoreKeyedToSuper_Sloppy),
2783 4); 2782 4);
2784 } 2783 }
2785 2784
2786 2785
2787 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) { 2786 void FullCodeGenerator::EmitKeyedPropertyAssignment(Assignment* expr) {
2788 // Assignment to a property, using a keyed store IC. 2787 // Assignment to a property, using a keyed store IC.
2789
2790 __ Pop(StoreDescriptor::NameRegister()); // Key. 2788 __ Pop(StoreDescriptor::NameRegister()); // Key.
2791 __ Pop(StoreDescriptor::ReceiverRegister()); 2789 __ Pop(StoreDescriptor::ReceiverRegister());
2792 DCHECK(StoreDescriptor::ValueRegister().is(rax)); 2790 DCHECK(StoreDescriptor::ValueRegister().is(rax));
2793 // Record source code position before IC call.
2794 SetSourcePosition(expr->position());
2795 Handle<Code> ic = 2791 Handle<Code> ic =
2796 CodeFactory::KeyedStoreIC(isolate(), language_mode()).code(); 2792 CodeFactory::KeyedStoreIC(isolate(), language_mode()).code();
2797 if (FLAG_vector_stores) { 2793 if (FLAG_vector_stores) {
2798 EmitLoadStoreICSlot(expr->AssignmentSlot()); 2794 EmitLoadStoreICSlot(expr->AssignmentSlot());
2799 CallIC(ic); 2795 CallIC(ic);
2800 } else { 2796 } else {
2801 CallIC(ic, expr->AssignmentFeedbackId()); 2797 CallIC(ic, expr->AssignmentFeedbackId());
2802 } 2798 }
2803 2799
2804 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG); 2800 PrepareForBailoutForId(expr->AssignmentId(), TOS_REG);
2805 context()->Plug(rax); 2801 context()->Plug(rax);
2806 } 2802 }
2807 2803
2808 2804
2809 void FullCodeGenerator::VisitProperty(Property* expr) { 2805 void FullCodeGenerator::VisitProperty(Property* expr) {
2810 Comment cmnt(masm_, "[ Property"); 2806 Comment cmnt(masm_, "[ Property");
2807 SetExpressionPosition(expr);
2808
2811 Expression* key = expr->key(); 2809 Expression* key = expr->key();
2812 2810
2813 if (key->IsPropertyName()) { 2811 if (key->IsPropertyName()) {
2814 if (!expr->IsSuperAccess()) { 2812 if (!expr->IsSuperAccess()) {
2815 VisitForAccumulatorValue(expr->obj()); 2813 VisitForAccumulatorValue(expr->obj());
2816 DCHECK(!rax.is(LoadDescriptor::ReceiverRegister())); 2814 DCHECK(!rax.is(LoadDescriptor::ReceiverRegister()));
2817 __ movp(LoadDescriptor::ReceiverRegister(), rax); 2815 __ movp(LoadDescriptor::ReceiverRegister(), rax);
2818 EmitNamedPropertyLoad(expr); 2816 EmitNamedPropertyLoad(expr);
2819 } else { 2817 } else {
2820 VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var()); 2818 VisitForStackValue(expr->obj()->AsSuperPropertyReference()->this_var());
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
2878 2876
2879 EmitCall(expr, call_type); 2877 EmitCall(expr, call_type);
2880 } 2878 }
2881 2879
2882 2880
2883 void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) { 2881 void FullCodeGenerator::EmitSuperCallWithLoadIC(Call* expr) {
2884 Expression* callee = expr->expression(); 2882 Expression* callee = expr->expression();
2885 DCHECK(callee->IsProperty()); 2883 DCHECK(callee->IsProperty());
2886 Property* prop = callee->AsProperty(); 2884 Property* prop = callee->AsProperty();
2887 DCHECK(prop->IsSuperAccess()); 2885 DCHECK(prop->IsSuperAccess());
2886 SetExpressionPosition(prop);
2888 2887
2889 SetSourcePosition(prop->position());
2890 Literal* key = prop->key()->AsLiteral(); 2888 Literal* key = prop->key()->AsLiteral();
2891 DCHECK(!key->value()->IsSmi()); 2889 DCHECK(!key->value()->IsSmi());
2892 // Load the function from the receiver. 2890 // Load the function from the receiver.
2893 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference(); 2891 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
2894 VisitForStackValue(super_ref->home_object()); 2892 VisitForStackValue(super_ref->home_object());
2895 VisitForAccumulatorValue(super_ref->this_var()); 2893 VisitForAccumulatorValue(super_ref->this_var());
2896 __ Push(rax); 2894 __ Push(rax);
2897 __ Push(rax); 2895 __ Push(rax);
2898 __ Push(Operand(rsp, kPointerSize * 2)); 2896 __ Push(Operand(rsp, kPointerSize * 2));
2899 __ Push(key->value()); 2897 __ Push(key->value());
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
2940 EmitCall(expr, CallICState::METHOD); 2938 EmitCall(expr, CallICState::METHOD);
2941 } 2939 }
2942 2940
2943 2941
2944 void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) { 2942 void FullCodeGenerator::EmitKeyedSuperCallWithLoadIC(Call* expr) {
2945 Expression* callee = expr->expression(); 2943 Expression* callee = expr->expression();
2946 DCHECK(callee->IsProperty()); 2944 DCHECK(callee->IsProperty());
2947 Property* prop = callee->AsProperty(); 2945 Property* prop = callee->AsProperty();
2948 DCHECK(prop->IsSuperAccess()); 2946 DCHECK(prop->IsSuperAccess());
2949 2947
2950 SetSourcePosition(prop->position()); 2948 SetExpressionPosition(prop);
2951 // Load the function from the receiver. 2949 // Load the function from the receiver.
2952 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference(); 2950 SuperPropertyReference* super_ref = prop->obj()->AsSuperPropertyReference();
2953 VisitForStackValue(super_ref->home_object()); 2951 VisitForStackValue(super_ref->home_object());
2954 VisitForAccumulatorValue(super_ref->this_var()); 2952 VisitForAccumulatorValue(super_ref->this_var());
2955 __ Push(rax); 2953 __ Push(rax);
2956 __ Push(rax); 2954 __ Push(rax);
2957 __ Push(Operand(rsp, kPointerSize * 2)); 2955 __ Push(Operand(rsp, kPointerSize * 2));
2958 VisitForStackValue(prop->key()); 2956 VisitForStackValue(prop->key());
2959 __ Push(Smi::FromInt(language_mode())); 2957 __ Push(Smi::FromInt(language_mode()));
2960 2958
(...skipping 13 matching lines...) Expand all
2974 // - target function 2972 // - target function
2975 // - this (receiver) 2973 // - this (receiver)
2976 EmitCall(expr, CallICState::METHOD); 2974 EmitCall(expr, CallICState::METHOD);
2977 } 2975 }
2978 2976
2979 2977
2980 void FullCodeGenerator::EmitCall(Call* expr, CallICState::CallType call_type) { 2978 void FullCodeGenerator::EmitCall(Call* expr, CallICState::CallType call_type) {
2981 // Load the arguments. 2979 // Load the arguments.
2982 ZoneList<Expression*>* args = expr->arguments(); 2980 ZoneList<Expression*>* args = expr->arguments();
2983 int arg_count = args->length(); 2981 int arg_count = args->length();
2984 { PreservePositionScope scope(masm()->positions_recorder()); 2982 for (int i = 0; i < arg_count; i++) {
2985 for (int i = 0; i < arg_count; i++) { 2983 VisitForStackValue(args->at(i));
2986 VisitForStackValue(args->at(i));
2987 }
2988 } 2984 }
2989 2985
2990 // Record source position of the IC call. 2986 SetExpressionPosition(expr);
2991 SetSourcePosition(expr->position());
2992 Handle<Code> ic = CodeFactory::CallIC(isolate(), arg_count, call_type).code(); 2987 Handle<Code> ic = CodeFactory::CallIC(isolate(), arg_count, call_type).code();
2993 __ Move(rdx, SmiFromSlot(expr->CallFeedbackICSlot())); 2988 __ Move(rdx, SmiFromSlot(expr->CallFeedbackICSlot()));
2994 __ movp(rdi, Operand(rsp, (arg_count + 1) * kPointerSize)); 2989 __ movp(rdi, Operand(rsp, (arg_count + 1) * kPointerSize));
2995 // 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
2996 // by the vector above. 2991 // by the vector above.
2997 CallIC(ic); 2992 CallIC(ic);
2998 2993
2999 RecordJSReturnSite(expr); 2994 RecordJSReturnSite(expr);
3000 2995
3001 // Restore context register. 2996 // Restore context register.
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
3040 3035
3041 EmitVariableAssignment(this_var, Token::INIT_CONST, slot); 3036 EmitVariableAssignment(this_var, Token::INIT_CONST, slot);
3042 } 3037 }
3043 3038
3044 3039
3045 // See http://www.ecma-international.org/ecma-262/6.0/#sec-function-calls. 3040 // See http://www.ecma-international.org/ecma-262/6.0/#sec-function-calls.
3046 void FullCodeGenerator::PushCalleeAndWithBaseObject(Call* expr) { 3041 void FullCodeGenerator::PushCalleeAndWithBaseObject(Call* expr) {
3047 VariableProxy* callee = expr->expression()->AsVariableProxy(); 3042 VariableProxy* callee = expr->expression()->AsVariableProxy();
3048 if (callee->var()->IsLookupSlot()) { 3043 if (callee->var()->IsLookupSlot()) {
3049 Label slow, done; 3044 Label slow, done;
3050 SetSourcePosition(callee->position()); 3045 SetExpressionPosition(callee);
3051 { 3046 // Generate code for loading from variables potentially shadowed by
3052 PreservePositionScope scope(masm()->positions_recorder()); 3047 // eval-introduced variables.
3053 // Generate code for loading from variables potentially shadowed by 3048 EmitDynamicLookupFastCase(callee, NOT_INSIDE_TYPEOF, &slow, &done);
3054 // eval-introduced variables.
3055 EmitDynamicLookupFastCase(callee, NOT_INSIDE_TYPEOF, &slow, &done);
3056 }
3057 __ bind(&slow); 3049 __ bind(&slow);
3058 // Call the runtime to find the function to call (returned in rax) and 3050 // Call the runtime to find the function to call (returned in rax) and
3059 // the object holding it (returned in rdx). 3051 // the object holding it (returned in rdx).
3060 __ Push(context_register()); 3052 __ Push(context_register());
3061 __ Push(callee->name()); 3053 __ Push(callee->name());
3062 __ CallRuntime(Runtime::kLoadLookupSlot, 2); 3054 __ CallRuntime(Runtime::kLoadLookupSlot, 2);
3063 __ Push(rax); // Function. 3055 __ Push(rax); // Function.
3064 __ Push(rdx); // Receiver. 3056 __ Push(rdx); // Receiver.
3065 PrepareForBailoutForId(expr->LookupId(), NO_REGISTERS); 3057 PrepareForBailoutForId(expr->LookupId(), NO_REGISTERS);
3066 3058
(...skipping 29 matching lines...) Expand all
3096 Comment cmnt(masm_, "[ Call"); 3088 Comment cmnt(masm_, "[ Call");
3097 Expression* callee = expr->expression(); 3089 Expression* callee = expr->expression();
3098 Call::CallType call_type = expr->GetCallType(isolate()); 3090 Call::CallType call_type = expr->GetCallType(isolate());
3099 3091
3100 if (call_type == Call::POSSIBLY_EVAL_CALL) { 3092 if (call_type == Call::POSSIBLY_EVAL_CALL) {
3101 // In a call to eval, we first call RuntimeHidden_ResolvePossiblyDirectEval 3093 // In a call to eval, we first call RuntimeHidden_ResolvePossiblyDirectEval
3102 // to resolve the function we need to call. Then we call the resolved 3094 // to resolve the function we need to call. Then we call the resolved
3103 // function using the given arguments. 3095 // function using the given arguments.
3104 ZoneList<Expression*>* args = expr->arguments(); 3096 ZoneList<Expression*>* args = expr->arguments();
3105 int arg_count = args->length(); 3097 int arg_count = args->length();
3106 { PreservePositionScope pos_scope(masm()->positions_recorder());
3107 PushCalleeAndWithBaseObject(expr); 3098 PushCalleeAndWithBaseObject(expr);
3108 3099
3109 // Push the arguments. 3100 // Push the arguments.
3110 for (int i = 0; i < arg_count; i++) { 3101 for (int i = 0; i < arg_count; i++) {
3111 VisitForStackValue(args->at(i)); 3102 VisitForStackValue(args->at(i));
3112 } 3103 }
3113 3104
3114 // Push a copy of the function (found below the arguments) and resolve 3105 // Push a copy of the function (found below the arguments) and resolve
3115 // eval. 3106 // eval.
3116 __ Push(Operand(rsp, (arg_count + 1) * kPointerSize)); 3107 __ Push(Operand(rsp, (arg_count + 1) * kPointerSize));
3117 EmitResolvePossiblyDirectEval(arg_count); 3108 EmitResolvePossiblyDirectEval(arg_count);
3118 3109
3119 // Touch up the callee. 3110 // Touch up the callee.
3120 __ movp(Operand(rsp, (arg_count + 1) * kPointerSize), rax); 3111 __ movp(Operand(rsp, (arg_count + 1) * kPointerSize), rax);
3121 3112
3122 PrepareForBailoutForId(expr->EvalId(), NO_REGISTERS); 3113 PrepareForBailoutForId(expr->EvalId(), NO_REGISTERS);
3123 }
3124 // Record source position for debugger. 3114 // Record source position for debugger.
3125 SetSourcePosition(expr->position()); 3115 SetExpressionPosition(expr);
3126 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS); 3116 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS);
3127 __ movp(rdi, Operand(rsp, (arg_count + 1) * kPointerSize)); 3117 __ movp(rdi, Operand(rsp, (arg_count + 1) * kPointerSize));
3128 __ CallStub(&stub); 3118 __ CallStub(&stub);
3129 RecordJSReturnSite(expr); 3119 RecordJSReturnSite(expr);
3130 // Restore context register. 3120 // Restore context register.
3131 __ movp(rsi, Operand(rbp, StandardFrameConstants::kContextOffset)); 3121 __ movp(rsi, Operand(rbp, StandardFrameConstants::kContextOffset));
3132 context()->DropAndPlug(1, rax); 3122 context()->DropAndPlug(1, rax);
3133 } else if (call_type == Call::GLOBAL_CALL) { 3123 } else if (call_type == Call::GLOBAL_CALL) {
3134 EmitCallWithLoadIC(expr); 3124 EmitCallWithLoadIC(expr);
3135 3125
3136 } else if (call_type == Call::LOOKUP_SLOT_CALL) { 3126 } else if (call_type == Call::LOOKUP_SLOT_CALL) {
3137 // Call to a lookup slot (dynamically introduced variable). 3127 // Call to a lookup slot (dynamically introduced variable).
3138 PushCalleeAndWithBaseObject(expr); 3128 PushCalleeAndWithBaseObject(expr);
3139 EmitCall(expr); 3129 EmitCall(expr);
3140 } else if (call_type == Call::PROPERTY_CALL) { 3130 } else if (call_type == Call::PROPERTY_CALL) {
3141 Property* property = callee->AsProperty(); 3131 Property* property = callee->AsProperty();
3142 bool is_named_call = property->key()->IsPropertyName(); 3132 bool is_named_call = property->key()->IsPropertyName();
3143 if (property->IsSuperAccess()) { 3133 if (property->IsSuperAccess()) {
3144 if (is_named_call) { 3134 if (is_named_call) {
3145 EmitSuperCallWithLoadIC(expr); 3135 EmitSuperCallWithLoadIC(expr);
3146 } else { 3136 } else {
3147 EmitKeyedSuperCallWithLoadIC(expr); 3137 EmitKeyedSuperCallWithLoadIC(expr);
3148 } 3138 }
3149 } else { 3139 } else {
3150 {
3151 PreservePositionScope scope(masm()->positions_recorder());
3152 VisitForStackValue(property->obj()); 3140 VisitForStackValue(property->obj());
3153 }
3154 if (is_named_call) { 3141 if (is_named_call) {
3155 EmitCallWithLoadIC(expr); 3142 EmitCallWithLoadIC(expr);
3156 } else { 3143 } else {
3157 EmitKeyedCallWithLoadIC(expr, property->key()); 3144 EmitKeyedCallWithLoadIC(expr, property->key());
3158 } 3145 }
3159 } 3146 }
3160 } else if (call_type == Call::SUPER_CALL) { 3147 } else if (call_type == Call::SUPER_CALL) {
3161 EmitSuperConstructorCall(expr); 3148 EmitSuperConstructorCall(expr);
3162 } else { 3149 } else {
3163 DCHECK(call_type == Call::OTHER_CALL); 3150 DCHECK(call_type == Call::OTHER_CALL);
3164 // Call to an arbitrary expression not handled specially above. 3151 // Call to an arbitrary expression not handled specially above.
3165 { PreservePositionScope scope(masm()->positions_recorder());
3166 VisitForStackValue(callee); 3152 VisitForStackValue(callee);
3167 }
3168 __ PushRoot(Heap::kUndefinedValueRootIndex); 3153 __ PushRoot(Heap::kUndefinedValueRootIndex);
3169 // Emit function call. 3154 // Emit function call.
3170 EmitCall(expr); 3155 EmitCall(expr);
3171 } 3156 }
3172 3157
3173 #ifdef DEBUG 3158 #ifdef DEBUG
3174 // RecordJSReturnSite should have been called. 3159 // RecordJSReturnSite should have been called.
3175 DCHECK(expr->return_is_recorded_); 3160 DCHECK(expr->return_is_recorded_);
3176 #endif 3161 #endif
3177 } 3162 }
(...skipping 13 matching lines...) Expand all
3191 3176
3192 // Push the arguments ("left-to-right") on the stack. 3177 // Push the arguments ("left-to-right") on the stack.
3193 ZoneList<Expression*>* args = expr->arguments(); 3178 ZoneList<Expression*>* args = expr->arguments();
3194 int arg_count = args->length(); 3179 int arg_count = args->length();
3195 for (int i = 0; i < arg_count; i++) { 3180 for (int i = 0; i < arg_count; i++) {
3196 VisitForStackValue(args->at(i)); 3181 VisitForStackValue(args->at(i));
3197 } 3182 }
3198 3183
3199 // Call the construct call builtin that handles allocation and 3184 // Call the construct call builtin that handles allocation and
3200 // constructor invocation. 3185 // constructor invocation.
3201 SetSourcePosition(expr->position()); 3186 SetExpressionPosition(expr);
3202 3187
3203 // Load function and argument count into rdi and rax. 3188 // Load function and argument count into rdi and rax.
3204 __ Set(rax, arg_count); 3189 __ Set(rax, arg_count);
3205 __ movp(rdi, Operand(rsp, arg_count * kPointerSize)); 3190 __ movp(rdi, Operand(rsp, arg_count * kPointerSize));
3206 3191
3207 // Record call targets in unoptimized code, but not in the snapshot. 3192 // Record call targets in unoptimized code, but not in the snapshot.
3208 if (FLAG_pretenuring_call_new) { 3193 if (FLAG_pretenuring_call_new) {
3209 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot()); 3194 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot());
3210 DCHECK(expr->AllocationSiteFeedbackSlot().ToInt() == 3195 DCHECK(expr->AllocationSiteFeedbackSlot().ToInt() ==
3211 expr->CallNewFeedbackSlot().ToInt() + 1); 3196 expr->CallNewFeedbackSlot().ToInt() + 1);
(...skipping 22 matching lines...) Expand all
3234 3219
3235 // Push the arguments ("left-to-right") on the stack. 3220 // Push the arguments ("left-to-right") on the stack.
3236 ZoneList<Expression*>* args = expr->arguments(); 3221 ZoneList<Expression*>* args = expr->arguments();
3237 int arg_count = args->length(); 3222 int arg_count = args->length();
3238 for (int i = 0; i < arg_count; i++) { 3223 for (int i = 0; i < arg_count; i++) {
3239 VisitForStackValue(args->at(i)); 3224 VisitForStackValue(args->at(i));
3240 } 3225 }
3241 3226
3242 // Call the construct call builtin that handles allocation and 3227 // Call the construct call builtin that handles allocation and
3243 // constructor invocation. 3228 // constructor invocation.
3244 SetSourcePosition(expr->position()); 3229 SetExpressionPosition(expr);
3245 3230
3246 // Load function and argument count into edi and eax. 3231 // Load function and argument count into edi and eax.
3247 __ Set(rax, arg_count); 3232 __ Set(rax, arg_count);
3248 __ movp(rdi, Operand(rsp, arg_count * kPointerSize)); 3233 __ movp(rdi, Operand(rsp, arg_count * kPointerSize));
3249 3234
3250 // Record call targets in unoptimized code. 3235 // Record call targets in unoptimized code.
3251 if (FLAG_pretenuring_call_new) { 3236 if (FLAG_pretenuring_call_new) {
3252 UNREACHABLE(); 3237 UNREACHABLE();
3253 /* TODO(dslomov): support pretenuring. 3238 /* TODO(dslomov): support pretenuring.
3254 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot()); 3239 EnsureSlotContainsAllocationSite(expr->AllocationSiteFeedbackSlot());
(...skipping 1428 matching lines...) Expand 10 before | Expand all | Expand 10 after
4683 __ Move(LoadDescriptor::SlotRegister(), 4668 __ Move(LoadDescriptor::SlotRegister(),
4684 SmiFromSlot(expr->CallRuntimeFeedbackSlot())); 4669 SmiFromSlot(expr->CallRuntimeFeedbackSlot()));
4685 CallLoadIC(NOT_CONTEXTUAL); 4670 CallLoadIC(NOT_CONTEXTUAL);
4686 } 4671 }
4687 4672
4688 4673
4689 void FullCodeGenerator::EmitCallJSRuntimeFunction(CallRuntime* expr) { 4674 void FullCodeGenerator::EmitCallJSRuntimeFunction(CallRuntime* expr) {
4690 ZoneList<Expression*>* args = expr->arguments(); 4675 ZoneList<Expression*>* args = expr->arguments();
4691 int arg_count = args->length(); 4676 int arg_count = args->length();
4692 4677
4693 // Record source position of the IC call. 4678 SetExpressionPosition(expr);
4694 SetSourcePosition(expr->position());
4695 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS); 4679 CallFunctionStub stub(isolate(), arg_count, NO_CALL_FUNCTION_FLAGS);
4696 __ movp(rdi, Operand(rsp, (arg_count + 1) * kPointerSize)); 4680 __ movp(rdi, Operand(rsp, (arg_count + 1) * kPointerSize));
4697 __ CallStub(&stub); 4681 __ CallStub(&stub);
4698 } 4682 }
4699 4683
4700 4684
4701 void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) { 4685 void FullCodeGenerator::VisitCallRuntime(CallRuntime* expr) {
4702 ZoneList<Expression*>* args = expr->arguments(); 4686 ZoneList<Expression*>* args = expr->arguments();
4703 int arg_count = args->length(); 4687 int arg_count = args->length();
4704 4688
(...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after
4865 default: 4849 default:
4866 UNREACHABLE(); 4850 UNREACHABLE();
4867 } 4851 }
4868 } 4852 }
4869 4853
4870 4854
4871 void FullCodeGenerator::VisitCountOperation(CountOperation* expr) { 4855 void FullCodeGenerator::VisitCountOperation(CountOperation* expr) {
4872 DCHECK(expr->expression()->IsValidReferenceExpression()); 4856 DCHECK(expr->expression()->IsValidReferenceExpression());
4873 4857
4874 Comment cmnt(masm_, "[ CountOperation"); 4858 Comment cmnt(masm_, "[ CountOperation");
4875 SetSourcePosition(expr->position());
4876 4859
4877 Property* prop = expr->expression()->AsProperty(); 4860 Property* prop = expr->expression()->AsProperty();
4878 LhsKind assign_type = Property::GetAssignType(prop); 4861 LhsKind assign_type = Property::GetAssignType(prop);
4879 4862
4880 // Evaluate expression and get value. 4863 // Evaluate expression and get value.
4881 if (assign_type == VARIABLE) { 4864 if (assign_type == VARIABLE) {
4882 DCHECK(expr->expression()->AsVariableProxy()->var() != NULL); 4865 DCHECK(expr->expression()->AsVariableProxy()->var() != NULL);
4883 AccumulatorValueContext context(this); 4866 AccumulatorValueContext context(this);
4884 EmitVariableLoad(expr->expression()->AsVariableProxy()); 4867 EmitVariableLoad(expr->expression()->AsVariableProxy());
4885 } else { 4868 } else {
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after
5012 case KEYED_PROPERTY: 4995 case KEYED_PROPERTY:
5013 __ movp(Operand(rsp, 2 * kPointerSize), rax); 4996 __ movp(Operand(rsp, 2 * kPointerSize), rax);
5014 break; 4997 break;
5015 case KEYED_SUPER_PROPERTY: 4998 case KEYED_SUPER_PROPERTY:
5016 __ movp(Operand(rsp, 3 * kPointerSize), rax); 4999 __ movp(Operand(rsp, 3 * kPointerSize), rax);
5017 break; 5000 break;
5018 } 5001 }
5019 } 5002 }
5020 } 5003 }
5021 5004
5022 // Record position before stub call. 5005 SetExpressionPosition(expr);
5023 SetSourcePosition(expr->position());
5024 5006
5025 // Call stub for +1/-1. 5007 // Call stub for +1/-1.
5026 __ bind(&stub_call); 5008 __ bind(&stub_call);
5027 __ movp(rdx, rax); 5009 __ movp(rdx, rax);
5028 __ Move(rax, Smi::FromInt(1)); 5010 __ Move(rax, Smi::FromInt(1));
5029 Handle<Code> code = CodeFactory::BinaryOpIC(isolate(), expr->binary_op(), 5011 Handle<Code> code = CodeFactory::BinaryOpIC(isolate(), expr->binary_op(),
5030 strength(language_mode())).code(); 5012 strength(language_mode())).code();
5031 CallIC(code, expr->CountBinOpFeedbackId()); 5013 CallIC(code, expr->CountBinOpFeedbackId());
5032 patch_site.EmitPatchInfo(); 5014 patch_site.EmitPatchInfo();
5033 __ bind(&done); 5015 __ bind(&done);
(...skipping 199 matching lines...) Expand 10 before | Expand all | Expand 10 after
5233 Split(zero, if_true, if_false, fall_through); 5215 Split(zero, if_true, if_false, fall_through);
5234 } else { 5216 } else {
5235 if (if_false != fall_through) __ jmp(if_false); 5217 if (if_false != fall_through) __ jmp(if_false);
5236 } 5218 }
5237 context()->Plug(if_true, if_false); 5219 context()->Plug(if_true, if_false);
5238 } 5220 }
5239 5221
5240 5222
5241 void FullCodeGenerator::VisitCompareOperation(CompareOperation* expr) { 5223 void FullCodeGenerator::VisitCompareOperation(CompareOperation* expr) {
5242 Comment cmnt(masm_, "[ CompareOperation"); 5224 Comment cmnt(masm_, "[ CompareOperation");
5243 SetSourcePosition(expr->position()); 5225 SetExpressionPosition(expr);
5244 5226
5245 // First we try a fast inlined version of the compare when one of 5227 // First we try a fast inlined version of the compare when one of
5246 // the operands is a literal. 5228 // the operands is a literal.
5247 if (TryLiteralCompare(expr)) return; 5229 if (TryLiteralCompare(expr)) return;
5248 5230
5249 // Always perform the comparison for its control flow. Pack the result 5231 // Always perform the comparison for its control flow. Pack the result
5250 // into the expression's context after the comparison is performed. 5232 // into the expression's context after the comparison is performed.
5251 Label materialize_true, materialize_false; 5233 Label materialize_true, materialize_false;
5252 Label* if_true = NULL; 5234 Label* if_true = NULL;
5253 Label* if_false = NULL; 5235 Label* if_false = NULL;
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
5287 if (inline_smi_code) { 5269 if (inline_smi_code) {
5288 Label slow_case; 5270 Label slow_case;
5289 __ movp(rcx, rdx); 5271 __ movp(rcx, rdx);
5290 __ orp(rcx, rax); 5272 __ orp(rcx, rax);
5291 patch_site.EmitJumpIfNotSmi(rcx, &slow_case, Label::kNear); 5273 patch_site.EmitJumpIfNotSmi(rcx, &slow_case, Label::kNear);
5292 __ cmpp(rdx, rax); 5274 __ cmpp(rdx, rax);
5293 Split(cc, if_true, if_false, NULL); 5275 Split(cc, if_true, if_false, NULL);
5294 __ bind(&slow_case); 5276 __ bind(&slow_case);
5295 } 5277 }
5296 5278
5297 // Record position and call the compare IC.
5298 SetSourcePosition(expr->position());
5299 Handle<Code> ic = CodeFactory::CompareIC( 5279 Handle<Code> ic = CodeFactory::CompareIC(
5300 isolate(), op, strength(language_mode())).code(); 5280 isolate(), op, strength(language_mode())).code();
5301 CallIC(ic, expr->CompareOperationFeedbackId()); 5281 CallIC(ic, expr->CompareOperationFeedbackId());
5302 patch_site.EmitPatchInfo(); 5282 patch_site.EmitPatchInfo();
5303 5283
5304 PrepareForBailoutBeforeSplit(expr, true, if_true, if_false); 5284 PrepareForBailoutBeforeSplit(expr, true, if_true, if_false);
5305 __ testp(rax, rax); 5285 __ testp(rax, rax);
5306 Split(cc, if_true, if_false, fall_through); 5286 Split(cc, if_true, if_false, fall_through);
5307 } 5287 }
5308 } 5288 }
(...skipping 220 matching lines...) Expand 10 before | Expand all | Expand 10 after
5529 Assembler::target_address_at(call_target_address, 5509 Assembler::target_address_at(call_target_address,
5530 unoptimized_code)); 5510 unoptimized_code));
5531 return OSR_AFTER_STACK_CHECK; 5511 return OSR_AFTER_STACK_CHECK;
5532 } 5512 }
5533 5513
5534 5514
5535 } // namespace internal 5515 } // namespace internal
5536 } // namespace v8 5516 } // namespace v8
5537 5517
5538 #endif // V8_TARGET_ARCH_X64 5518 #endif // V8_TARGET_ARCH_X64
OLDNEW
« no previous file with comments | « src/x64/debug-x64.cc ('k') | test/cctest/test-debug.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698