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

Side by Side Diff: vm/stub_code_x64.cc

Issue 8965071: Push raw_null instead of smi 0 in all places were we setup the return value location before calli... (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/runtime/
Patch Set: '' Created 8 years, 12 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « vm/stub_code_ia32.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
2 // for details. All rights reserved. Use of this source code is governed by a 2 // for details. All rights reserved. Use of this source code is governed by a
3 // BSD-style license that can be found in the LICENSE file. 3 // BSD-style license that can be found in the LICENSE file.
4 4
5 #include "vm/globals.h" 5 #include "vm/globals.h"
6 #if defined(TARGET_ARCH_X64) 6 #if defined(TARGET_ARCH_X64)
7 7
8 #include "vm/code_generator.h" 8 #include "vm/code_generator.h"
9 #include "vm/compiler.h" 9 #include "vm/compiler.h"
10 #include "vm/ic_data.h" 10 #include "vm/ic_data.h"
(...skipping 368 matching lines...) Expand 10 before | Expand all | Expand 10 after
379 // TOS + 2: Last argument of caller. 379 // TOS + 2: Last argument of caller.
380 // .... 380 // ....
381 // Total number of args is the first Smi in args descriptor array (R10). 381 // Total number of args is the first Smi in args descriptor array (R10).
382 __ movq(RAX, FieldAddress(R10, Array::data_offset())); 382 __ movq(RAX, FieldAddress(R10, Array::data_offset()));
383 __ movq(RAX, Address(RSP, RAX, TIMES_4, kWordSize)); // Get receiver. 383 __ movq(RAX, Address(RSP, RAX, TIMES_4, kWordSize)); // Get receiver.
384 __ pushq(R10); // Preserve arguments descriptor array. 384 __ pushq(R10); // Preserve arguments descriptor array.
385 __ pushq(RAX); // Preserve receiver. 385 __ pushq(RAX); // Preserve receiver.
386 __ pushq(RBX); // Preserve ic-data array. 386 __ pushq(RBX); // Preserve ic-data array.
387 // First resolve the function to get the function object. 387 // First resolve the function to get the function object.
388 388
389 // Setup space for return value on stack by pushing smi 0. 389 __ pushq(raw_null); // Setup space on stack for return value.
390 __ pushq(Immediate(0));
391 __ pushq(RAX); // Push receiver. 390 __ pushq(RAX); // Push receiver.
392 __ CallRuntimeFromStub(kResolveCompileInstanceFunctionRuntimeEntry); 391 __ CallRuntimeFromStub(kResolveCompileInstanceFunctionRuntimeEntry);
393 __ popq(RAX); // Remove receiver pushed earlier. 392 __ popq(RAX); // Remove receiver pushed earlier.
394 __ popq(RBX); // Pop returned code object into RBX. 393 __ popq(RBX); // Pop returned code object into RBX.
395 // Pop preserved values 394 // Pop preserved values
396 __ popq(R10); // Restore ic-data array. 395 __ popq(R10); // Restore ic-data array.
397 __ popq(RAX); // Restore receiver. 396 __ popq(RAX); // Restore receiver.
398 __ popq(R13); // Restore arguments descriptor array. 397 __ popq(R13); // Restore arguments descriptor array.
399 398
400 __ cmpq(RBX, raw_null); 399 __ cmpq(RBX, raw_null);
(...skipping 14 matching lines...) Expand all
415 // RBX: raw_null. 414 // RBX: raw_null.
416 // R13: arguments descriptor array. 415 // R13: arguments descriptor array.
417 // The target function was not found. 416 // The target function was not found.
418 // First check to see if this is a getter function and we are 417 // First check to see if this is a getter function and we are
419 // trying to create a closure of an instance function. 418 // trying to create a closure of an instance function.
420 // Push values that need to be preserved across runtime call. 419 // Push values that need to be preserved across runtime call.
421 __ pushq(RAX); // Preserve receiver. 420 __ pushq(RAX); // Preserve receiver.
422 __ pushq(R10); // Preserve ic-data array. 421 __ pushq(R10); // Preserve ic-data array.
423 __ pushq(R13); // Preserve arguments descriptor array. 422 __ pushq(R13); // Preserve arguments descriptor array.
424 423
425 __ pushq(Immediate(0)); 424 __ pushq(raw_null); // Setup space on stack for return value.
426 __ pushq(RAX); // Push receiver. 425 __ pushq(RAX); // Push receiver.
427 __ pushq(R10); // Ic-data array. 426 __ pushq(R10); // Ic-data array.
428 __ CallRuntimeFromStub(kResolveImplicitClosureFunctionRuntimeEntry); 427 __ CallRuntimeFromStub(kResolveImplicitClosureFunctionRuntimeEntry);
429 __ popq(RAX); 428 __ popq(RAX);
430 __ popq(RAX); 429 __ popq(RAX);
431 __ popq(RBX); // Get return value into RBX, might be Closure object. 430 __ popq(RBX); // Get return value into RBX, might be Closure object.
432 431
433 // Pop preserved values. 432 // Pop preserved values.
434 __ popq(R13); // Restore arguments descriptor array. 433 __ popq(R13); // Restore arguments descriptor array.
435 __ popq(R10); // Restore ic-data array. 434 __ popq(R10); // Restore ic-data array.
(...skipping 14 matching lines...) Expand all
450 // RBX: raw_null. 449 // RBX: raw_null.
451 // R13: arguments descriptor array. 450 // R13: arguments descriptor array.
452 // This is not the case of an instance so invoke the getter of the 451 // This is not the case of an instance so invoke the getter of the
453 // same name and see if we get a closure back which we are then 452 // same name and see if we get a closure back which we are then
454 // supposed to invoke. 453 // supposed to invoke.
455 // Push values that need to be preserved across runtime call. 454 // Push values that need to be preserved across runtime call.
456 __ pushq(RAX); // Preserve receiver. 455 __ pushq(RAX); // Preserve receiver.
457 __ pushq(R10); // Preserve ic-data array. 456 __ pushq(R10); // Preserve ic-data array.
458 __ pushq(R13); // Preserve arguments descriptor array. 457 __ pushq(R13); // Preserve arguments descriptor array.
459 458
460 __ pushq(Immediate(0)); 459 __ pushq(raw_null); // Setup space on stack for return value.
461 __ pushq(RAX); // Push receiver. 460 __ pushq(RAX); // Push receiver.
462 __ pushq(R10); // Ic-data array. 461 __ pushq(R10); // Ic-data array.
463 __ CallRuntimeFromStub(kResolveImplicitClosureThroughGetterRuntimeEntry); 462 __ CallRuntimeFromStub(kResolveImplicitClosureThroughGetterRuntimeEntry);
464 __ popq(R10); // Pop argument. 463 __ popq(R10); // Pop argument.
465 __ popq(RAX); // Pop argument. 464 __ popq(RAX); // Pop argument.
466 __ popq(RBX); // get return value into RBX, might be Closure object. 465 __ popq(RBX); // get return value into RBX, might be Closure object.
467 466
468 // Pop preserved values. 467 // Pop preserved values.
469 __ popq(R13); // Restore arguments descriptor array. 468 __ popq(R13); // Restore arguments descriptor array.
470 __ popq(R10); // Restore ic-data array. 469 __ popq(R10); // Restore ic-data array.
471 __ popq(RAX); // Restore receiver. 470 __ popq(RAX); // Restore receiver.
472 471
473 __ cmpq(RBX, raw_null); 472 __ cmpq(RBX, raw_null);
474 Label function_not_found; 473 Label function_not_found;
475 __ j(EQUAL, &function_not_found, Assembler::kNearJump); 474 __ j(EQUAL, &function_not_found);
476 475
477 // RBX: Closure object. 476 // RBX: Closure object.
478 // R13: Arguments descriptor array. 477 // R13: Arguments descriptor array.
479 __ pushq(Immediate(0)); // Result from invoking Closure. 478 __ pushq(raw_null); // Setup space on stack for result from invoking Closure.
480 __ pushq(RBX); // Closure object. 479 __ pushq(RBX); // Closure object.
481 __ pushq(R13); // Arguments descriptor. 480 __ pushq(R13); // Arguments descriptor.
482 __ movq(R13, FieldAddress(R13, Array::data_offset())); 481 __ movq(R13, FieldAddress(R13, Array::data_offset()));
483 __ SmiUntag(R13); 482 __ SmiUntag(R13);
484 __ subq(R13, Immediate(1)); // Arguments array length, minus the receiver. 483 __ subq(R13, Immediate(1)); // Arguments array length, minus the receiver.
485 PushArgumentsArray(assembler, (kWordSize * 5)); 484 PushArgumentsArray(assembler, (kWordSize * 5));
486 // Stack layout explaining "(kWordSize * 5)" offset. 485 // Stack layout explaining "(kWordSize * 5)" offset.
487 // TOS + 0: Argument array. 486 // TOS + 0: Argument array.
488 // TOS + 1: Arguments descriptor array. 487 // TOS + 1: Arguments descriptor array.
489 // TOS + 2: Closure object. 488 // TOS + 2: Closure object.
(...skipping 15 matching lines...) Expand all
505 __ ret(); 504 __ ret();
506 505
507 __ Bind(&function_not_found); 506 __ Bind(&function_not_found);
508 // The target function was not found, so invoke method 507 // The target function was not found, so invoke method
509 // "void noSuchMethod(function_name, args_array)". 508 // "void noSuchMethod(function_name, args_array)".
510 // RAX: receiver. 509 // RAX: receiver.
511 // R10: ic-data array. 510 // R10: ic-data array.
512 // RBX: raw_null. 511 // RBX: raw_null.
513 // R13: argument descriptor array. 512 // R13: argument descriptor array.
514 513
515 // Setup space for return value on stack by pushing smi 0. 514 __ pushq(raw_null); // Setup space on stack for result from noSuchMethod.
516 __ pushq(Immediate(0)); // Result from noSuchMethod.
517 __ pushq(RAX); // Receiver. 515 __ pushq(RAX); // Receiver.
518 __ pushq(R10); // IC-data array. 516 __ pushq(R10); // IC-data array.
519 __ pushq(R13); // Argument descriptor array. 517 __ pushq(R13); // Argument descriptor array.
520 __ movq(R13, FieldAddress(R13, Array::data_offset())); 518 __ movq(R13, FieldAddress(R13, Array::data_offset()));
521 __ SmiUntag(R13); 519 __ SmiUntag(R13);
522 __ subq(R13, Immediate(1)); // Arguments array length, minus the receiver. 520 __ subq(R13, Immediate(1)); // Arguments array length, minus the receiver.
523 // See stack layout below explaining "wordSize * 6" offset. 521 // See stack layout below explaining "wordSize * 6" offset.
524 PushArgumentsArray(assembler, (kWordSize * 6)); 522 PushArgumentsArray(assembler, (kWordSize * 6));
525 523
526 // Stack: 524 // Stack:
(...skipping 119 matching lines...) Expand 10 before | Expand all | Expand 10 after
646 644
647 // Done allocating and initializing the array. 645 // Done allocating and initializing the array.
648 // RAX: new object. 646 // RAX: new object.
649 __ ret(); 647 __ ret();
650 } 648 }
651 649
652 // Unable to allocate the array using the fast inline code, just call 650 // Unable to allocate the array using the fast inline code, just call
653 // into the runtime. 651 // into the runtime.
654 __ Bind(&slow_case); 652 __ Bind(&slow_case);
655 __ EnterFrame(0); 653 __ EnterFrame(0);
656 __ pushq(raw_null); // Push Null object for return value. 654 __ pushq(raw_null); // Setup space on stack for return value.
657 __ pushq(R10); // Array length as Smi. 655 __ pushq(R10); // Array length as Smi.
658 __ pushq(RBX); // Element type. 656 __ pushq(RBX); // Element type.
659 __ pushq(raw_null); // Null instantiator. 657 __ pushq(raw_null); // Null instantiator.
660 __ CallRuntimeFromStub(kAllocateArrayRuntimeEntry); 658 __ CallRuntimeFromStub(kAllocateArrayRuntimeEntry);
661 __ popq(RAX); // Pop instantiator. 659 __ popq(RAX); // Pop instantiator.
662 __ popq(RAX); // Pop element type argument. 660 __ popq(RAX); // Pop element type argument.
663 __ popq(R10); // Pop array length argument. 661 __ popq(R10); // Pop array length argument.
664 __ popq(RAX); // Pop return value from return slot. 662 __ popq(RAX); // Pop return value from return slot.
665 __ LeaveFrame(); 663 __ LeaveFrame();
666 __ ret(); 664 __ ret();
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after
796 // RBX and RDX are destroyed. 794 // RBX and RDX are destroyed.
797 void StubCode::GenerateAllocateContextStub(Assembler* assembler) { 795 void StubCode::GenerateAllocateContextStub(Assembler* assembler) {
798 const Immediate raw_null = 796 const Immediate raw_null =
799 Immediate(reinterpret_cast<intptr_t>(Object::null())); 797 Immediate(reinterpret_cast<intptr_t>(Object::null()));
800 if (false) { 798 if (false) {
801 // TODO(regis): Implement fast inline allocation of contexts. 799 // TODO(regis): Implement fast inline allocation of contexts.
802 __ Unimplemented("AllocateContext stub - inline allocation"); 800 __ Unimplemented("AllocateContext stub - inline allocation");
803 } 801 }
804 // Create the stub frame. 802 // Create the stub frame.
805 __ EnterFrame(0); 803 __ EnterFrame(0);
806 __ pushq(raw_null); // Make space for the return value. 804 __ pushq(raw_null); // Setup space on stack for the return value.
807 __ SmiTag(RDX); 805 __ SmiTag(RDX);
808 __ pushq(RDX); // Push number of context variables. 806 __ pushq(RDX); // Push number of context variables.
809 __ CallRuntimeFromStub(kAllocateContextRuntimeEntry); // Allocate context. 807 __ CallRuntimeFromStub(kAllocateContextRuntimeEntry); // Allocate context.
810 __ popq(RAX); // Pop number of context variables argument. 808 __ popq(RAX); // Pop number of context variables argument.
811 __ popq(RAX); // Pop the new context object. 809 __ popq(RAX); // Pop the new context object.
812 // RAX: new object 810 // RAX: new object
813 // Restore the frame pointer. 811 // Restore the frame pointer.
814 __ LeaveFrame(); 812 __ LeaveFrame();
815 __ ret(); 813 __ ret();
816 } 814 }
(...skipping 164 matching lines...) Expand 10 before | Expand all | Expand 10 after
981 __ ret(); 979 __ ret();
982 980
983 __ Bind(&slow_case); 981 __ Bind(&slow_case);
984 } 982 }
985 if (is_cls_parameterized) { 983 if (is_cls_parameterized) {
986 __ movq(RAX, Address(RSP, kObjectTypeArgumentsOffset)); 984 __ movq(RAX, Address(RSP, kObjectTypeArgumentsOffset));
987 __ movq(RDX, Address(RSP, kInstantiatorTypeArgumentsOffset)); 985 __ movq(RDX, Address(RSP, kInstantiatorTypeArgumentsOffset));
988 } 986 }
989 // Create a stub frame. 987 // Create a stub frame.
990 __ EnterFrame(0); 988 __ EnterFrame(0);
991 const Object& new_object = Object::ZoneHandle(); 989 __ pushq(raw_null); // Setup space on stack for return value.
992 __ PushObject(new_object); // Push Null object for return value.
993 __ PushObject(cls); // Push class of object to be allocated. 990 __ PushObject(cls); // Push class of object to be allocated.
994 if (is_cls_parameterized) { 991 if (is_cls_parameterized) {
995 __ pushq(RAX); // Push type arguments of object to be allocated. 992 __ pushq(RAX); // Push type arguments of object to be allocated.
996 __ pushq(RDX); // Push type arguments of instantiator. 993 __ pushq(RDX); // Push type arguments of instantiator.
997 } else { 994 } else {
998 __ pushq(raw_null); // Push null type arguments. 995 __ pushq(raw_null); // Push null type arguments.
999 __ pushq(raw_null); // Push null instantiator. 996 __ pushq(raw_null); // Push null instantiator.
1000 } 997 }
1001 __ CallRuntimeFromStub(kAllocateObjectRuntimeEntry); // Allocate object. 998 __ CallRuntimeFromStub(kAllocateObjectRuntimeEntry); // Allocate object.
1002 __ popq(RAX); // Pop argument (instantiator). 999 __ popq(RAX); // Pop argument (instantiator).
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
1036 __ Unimplemented("AllocateClosure stub - inline allocation"); 1033 __ Unimplemented("AllocateClosure stub - inline allocation");
1037 } 1034 }
1038 if (has_type_arguments) { 1035 if (has_type_arguments) {
1039 __ movq(RCX, Address(RSP, kTypeArgumentsOffset)); 1036 __ movq(RCX, Address(RSP, kTypeArgumentsOffset));
1040 } 1037 }
1041 if (is_implicit_instance_closure) { 1038 if (is_implicit_instance_closure) {
1042 __ movq(RAX, Address(RSP, kReceiverOffset)); 1039 __ movq(RAX, Address(RSP, kReceiverOffset));
1043 } 1040 }
1044 // Create the stub frame. 1041 // Create the stub frame.
1045 __ EnterFrame(0); 1042 __ EnterFrame(0);
1046 __ pushq(raw_null); // Make space for the return value. 1043 __ pushq(raw_null); // Setup space on stack for the return value.
1047 __ PushObject(func); 1044 __ PushObject(func);
1048 if (is_implicit_static_closure) { 1045 if (is_implicit_static_closure) {
1049 __ CallRuntimeFromStub(kAllocateImplicitStaticClosureRuntimeEntry); 1046 __ CallRuntimeFromStub(kAllocateImplicitStaticClosureRuntimeEntry);
1050 } else { 1047 } else {
1051 if (is_implicit_instance_closure) { 1048 if (is_implicit_instance_closure) {
1052 __ pushq(RAX); // Receiver. 1049 __ pushq(RAX); // Receiver.
1053 } 1050 }
1054 if (has_type_arguments) { 1051 if (has_type_arguments) {
1055 __ pushq(RCX); // Push type arguments of closure to be allocated. 1052 __ pushq(RCX); // Push type arguments of closure to be allocated.
1056 } else { 1053 } else {
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after
1144 __ call(&get_class); 1141 __ call(&get_class);
1145 __ cmpq(RAX, R13); // Match? 1142 __ cmpq(RAX, R13); // Match?
1146 __ j(NOT_EQUAL, &no_match, Assembler::kNearJump); 1143 __ j(NOT_EQUAL, &no_match, Assembler::kNearJump);
1147 // Check second. 1144 // Check second.
1148 __ movq(R13, Address(R12, kWordSize)); // Get class from IC data to check. 1145 __ movq(R13, Address(R12, kWordSize)); // Get class from IC data to check.
1149 // Get next argument. 1146 // Get next argument.
1150 __ movq(RAX, FieldAddress(R10, Array::data_offset())); 1147 __ movq(RAX, FieldAddress(R10, Array::data_offset()));
1151 __ movq(RAX, Address(RSP, RAX, TIMES_4, -kWordSize)); // RAX is Smi. 1148 __ movq(RAX, Address(RSP, RAX, TIMES_4, -kWordSize)); // RAX is Smi.
1152 __ call(&get_class); 1149 __ call(&get_class);
1153 __ cmpq(RAX, R13); // Match? 1150 __ cmpq(RAX, R13); // Match?
1154 __ j(EQUAL, &found, Assembler::kNearJump); 1151 __ j(EQUAL, &found);
1155 __ Bind(&no_match); 1152 __ Bind(&no_match);
1156 __ addq(R12, Immediate(kWordSize * (1 + num_args))); // Next element. 1153 __ addq(R12, Immediate(kWordSize * (1 + num_args))); // Next element.
1157 __ cmpq(R13, raw_null); // Done? 1154 __ cmpq(R13, raw_null); // Done?
1158 __ j(NOT_EQUAL, &loop, Assembler::kNearJump); 1155 __ j(NOT_EQUAL, &loop, Assembler::kNearJump);
1159 } 1156 }
1160 1157
1161 __ Bind(&ic_miss); 1158 __ Bind(&ic_miss);
1162 // Get receiver, again. 1159 // Get receiver, again.
1163 __ movq(RAX, FieldAddress(R10, Array::data_offset())); 1160 __ movq(RAX, FieldAddress(R10, Array::data_offset()));
1164 __ leaq(RAX, Address(RSP, RAX, TIMES_4, 0)); // RAX is Smi. 1161 __ leaq(RAX, Address(RSP, RAX, TIMES_4, 0)); // RAX is Smi.
1165 __ EnterFrame(0); 1162 __ EnterFrame(0);
1166 // Setup space for return value on stack by pushing smi 0.
1167 __ pushq(R10); // Preserve arguments array. 1163 __ pushq(R10); // Preserve arguments array.
1168 __ pushq(RBX); // Preserve IC data array 1164 __ pushq(RBX); // Preserve IC data array
1169 __ pushq(Immediate(0)); // Space for result (target code object). 1165 __ pushq(raw_null); // Setup space on stack for result (target code object).
1170 __ movq(R10, FieldAddress(R10, Array::data_offset())); 1166 __ movq(R10, FieldAddress(R10, Array::data_offset()));
1171 // Push call arguments. 1167 // Push call arguments.
1172 for (intptr_t i = 0; i < num_args; i++) { 1168 for (intptr_t i = 0; i < num_args; i++) {
1173 __ movq(R10, Address(RAX, -kWordSize * i)); 1169 __ movq(R10, Address(RAX, -kWordSize * i));
1174 __ pushq(R10); 1170 __ pushq(R10);
1175 } 1171 }
1176 if (num_args == 1) { 1172 if (num_args == 1) {
1177 __ CallRuntimeFromStub(kInlineCacheMissHandlerOneArgRuntimeEntry); 1173 __ CallRuntimeFromStub(kInlineCacheMissHandlerOneArgRuntimeEntry);
1178 } else if (num_args == 2) { 1174 } else if (num_args == 2) {
1179 __ CallRuntimeFromStub(kInlineCacheMissHandlerTwoArgsRuntimeEntry); 1175 __ CallRuntimeFromStub(kInlineCacheMissHandlerTwoArgsRuntimeEntry);
(...skipping 67 matching lines...) Expand 10 before | Expand all | Expand 10 after
1247 } 1243 }
1248 1244
1249 1245
1250 void StubCode::GenerateBreakpointDynamicStub(Assembler* assembler) { 1246 void StubCode::GenerateBreakpointDynamicStub(Assembler* assembler) {
1251 __ Unimplemented("BreakpointDynamic stub"); 1247 __ Unimplemented("BreakpointDynamic stub");
1252 } 1248 }
1253 1249
1254 } // namespace dart 1250 } // namespace dart
1255 1251
1256 #endif // defined TARGET_ARCH_X64 1252 #endif // defined TARGET_ARCH_X64
OLDNEW
« no previous file with comments | « vm/stub_code_ia32.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698