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

Side by Side Diff: runtime/vm/stub_code_x64.cc

Issue 842953002: x64 port of r42717. (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 5 years, 11 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
« runtime/vm/assembler_x64.cc ('K') | « runtime/vm/intrinsifier_x64.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) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, 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/assembler.h" 8 #include "vm/assembler.h"
9 #include "vm/compiler.h" 9 #include "vm/compiler.h"
10 #include "vm/dart_entry.h" 10 #include "vm/dart_entry.h"
(...skipping 350 matching lines...) Expand 10 before | Expand all | Expand 10 after
361 __ pushq(RAX); // Array is in RAX and on top of stack. 361 __ pushq(RAX); // Array is in RAX and on top of stack.
362 __ leaq(R12, Address(RBP, R10, TIMES_8, kParamEndSlotFromFp * kWordSize)); 362 __ leaq(R12, Address(RBP, R10, TIMES_8, kParamEndSlotFromFp * kWordSize));
363 __ leaq(RBX, FieldAddress(RAX, Array::data_offset())); 363 __ leaq(RBX, FieldAddress(RAX, Array::data_offset()));
364 // R12: address of first argument on stack. 364 // R12: address of first argument on stack.
365 // RBX: address of first argument in array. 365 // RBX: address of first argument in array.
366 Label loop, loop_condition; 366 Label loop, loop_condition;
367 __ jmp(&loop_condition, Assembler::kNearJump); 367 __ jmp(&loop_condition, Assembler::kNearJump);
368 __ Bind(&loop); 368 __ Bind(&loop);
369 __ movq(RDI, Address(R12, 0)); 369 __ movq(RDI, Address(R12, 0));
370 // No generational barrier needed, since array is in new space. 370 // No generational barrier needed, since array is in new space.
371 __ StoreIntoObjectNoBarrier(RAX, Address(RBX, 0), RDI); 371 __ InitializeFieldNoBarrier(RAX, Address(RBX, 0), RDI);
372 __ addq(RBX, Immediate(kWordSize)); 372 __ addq(RBX, Immediate(kWordSize));
373 __ subq(R12, Immediate(kWordSize)); 373 __ subq(R12, Immediate(kWordSize));
374 __ Bind(&loop_condition); 374 __ Bind(&loop_condition);
375 __ decq(R10); 375 __ decq(R10);
376 __ j(POSITIVE, &loop, Assembler::kNearJump); 376 __ j(POSITIVE, &loop, Assembler::kNearJump);
377 } 377 }
378 378
379 379
380 DECLARE_LEAF_RUNTIME_ENTRY(intptr_t, DeoptimizeCopyFrame, 380 DECLARE_LEAF_RUNTIME_ENTRY(intptr_t, DeoptimizeCopyFrame,
381 intptr_t deopt_reason, 381 intptr_t deopt_reason,
(...skipping 243 matching lines...) Expand 10 before | Expand all | Expand 10 after
625 __ movq(RDI, Immediate(0)); 625 __ movq(RDI, Immediate(0));
626 __ Bind(&done); 626 __ Bind(&done);
627 627
628 // Get the class index and insert it into the tags. 628 // Get the class index and insert it into the tags.
629 __ orq(RDI, Immediate(RawObject::ClassIdTag::encode(cid))); 629 __ orq(RDI, Immediate(RawObject::ClassIdTag::encode(cid)));
630 __ movq(FieldAddress(RAX, Array::tags_offset()), RDI); // Tags. 630 __ movq(FieldAddress(RAX, Array::tags_offset()), RDI); // Tags.
631 } 631 }
632 632
633 // RAX: new object start as a tagged pointer. 633 // RAX: new object start as a tagged pointer.
634 // Store the type argument field. 634 // Store the type argument field.
635 __ StoreIntoObjectNoBarrier(RAX, 635 __ InitializeFieldNoBarrier(RAX,
636 FieldAddress(RAX, Array::type_arguments_offset()), 636 FieldAddress(RAX, Array::type_arguments_offset()),
637 RBX); 637 RBX);
638 638
639 // Set the length field. 639 // Set the length field.
640 __ StoreIntoObjectNoBarrier(RAX, 640 __ InitializeFieldNoBarrier(RAX,
641 FieldAddress(RAX, Array::length_offset()), 641 FieldAddress(RAX, Array::length_offset()),
642 R10); 642 R10);
643 643
644 // Initialize all array elements to raw_null. 644 // Initialize all array elements to raw_null.
645 // RAX: new object start as a tagged pointer. 645 // RAX: new object start as a tagged pointer.
646 // RCX: new object end address. 646 // RCX: new object end address.
647 // RDI: iterator which initially points to the start of the variable 647 // RDI: iterator which initially points to the start of the variable
648 // data area to be initialized. 648 // data area to be initialized.
649 __ LoadObject(R12, Object::null_object(), PP); 649 __ LoadObject(R12, Object::null_object(), PP);
650 __ leaq(RDI, FieldAddress(RAX, sizeof(RawArray))); 650 __ leaq(RDI, FieldAddress(RAX, sizeof(RawArray)));
651 Label done; 651 Label done;
652 Label init_loop; 652 Label init_loop;
653 __ Bind(&init_loop); 653 __ Bind(&init_loop);
654 __ cmpq(RDI, RCX); 654 __ cmpq(RDI, RCX);
655 __ j(ABOVE_EQUAL, &done, Assembler::kNearJump); 655 __ j(ABOVE_EQUAL, &done, Assembler::kNearJump);
656 // No generational barrier needed, since we are storing null. 656 // No generational barrier needed, since we are storing null.
657 __ StoreIntoObjectNoBarrier(RAX, Address(RDI, 0), R12); 657 __ InitializeFieldNoBarrier(RAX, Address(RDI, 0), R12);
658 __ addq(RDI, Immediate(kWordSize)); 658 __ addq(RDI, Immediate(kWordSize));
659 __ jmp(&init_loop, Assembler::kNearJump); 659 __ jmp(&init_loop, Assembler::kNearJump);
660 __ Bind(&done); 660 __ Bind(&done);
661 __ ret(); // returns the newly allocated object in RAX. 661 __ ret(); // returns the newly allocated object in RAX.
662 662
663 // Unable to allocate the array using the fast inline code, just call 663 // Unable to allocate the array using the fast inline code, just call
664 // into the runtime. 664 // into the runtime.
665 __ Bind(&slow_case); 665 __ Bind(&slow_case);
666 // Create a stub frame as we are pushing some objects on the stack before 666 // Create a stub frame as we are pushing some objects on the stack before
667 // calling into the runtime. 667 // calling into the runtime.
(...skipping 213 matching lines...) Expand 10 before | Expand all | Expand 10 after
881 881
882 // Setup up number of context variables field. 882 // Setup up number of context variables field.
883 // RAX: new object. 883 // RAX: new object.
884 // R10: number of context variables as integer value (not object). 884 // R10: number of context variables as integer value (not object).
885 __ movq(FieldAddress(RAX, Context::num_variables_offset()), R10); 885 __ movq(FieldAddress(RAX, Context::num_variables_offset()), R10);
886 886
887 // Setup the parent field. 887 // Setup the parent field.
888 // RAX: new object. 888 // RAX: new object.
889 // R10: number of context variables. 889 // R10: number of context variables.
890 // No generational barrier needed, since we are storing null. 890 // No generational barrier needed, since we are storing null.
891 __ StoreIntoObjectNoBarrier(RAX, 891 __ InitializeFieldNoBarrier(RAX,
892 FieldAddress(RAX, Context::parent_offset()), 892 FieldAddress(RAX, Context::parent_offset()),
893 R12); 893 R12);
894 894
895 // Initialize the context variables. 895 // Initialize the context variables.
896 // RAX: new object. 896 // RAX: new object.
897 // R10: number of context variables. 897 // R10: number of context variables.
898 { 898 {
899 Label loop, entry; 899 Label loop, entry;
900 __ leaq(R13, FieldAddress(RAX, Context::variable_offset(0))); 900 __ leaq(R13, FieldAddress(RAX, Context::variable_offset(0)));
901 901 #if defined(DEBUG)
902 __ jmp(&entry, Assembler::kNearJump); 902 static const bool kJumpLength = Assembler::kFarJump;
903 #else
904 static const bool kJumpLength = Assembler::kNearJump;
905 #endif // DEBUG
906 __ jmp(&entry, kJumpLength);
903 __ Bind(&loop); 907 __ Bind(&loop);
904 __ decq(R10); 908 __ decq(R10);
905 // No generational barrier needed, since we are storing null. 909 // No generational barrier needed, since we are storing null.
906 __ StoreIntoObjectNoBarrier(RAX, 910 __ InitializeFieldNoBarrier(RAX,
907 Address(R13, R10, TIMES_8, 0), 911 Address(R13, R10, TIMES_8, 0),
908 R12); 912 R12);
909 __ Bind(&entry); 913 __ Bind(&entry);
910 __ cmpq(R10, Immediate(0)); 914 __ cmpq(R10, Immediate(0));
911 __ j(NOT_EQUAL, &loop, Assembler::kNearJump); 915 __ j(NOT_EQUAL, &loop, Assembler::kNearJump);
912 } 916 }
913 917
914 // Done allocating and initializing the context. 918 // Done allocating and initializing the context.
915 // RAX: new object. 919 // RAX: new object.
916 __ ret(); 920 __ ret();
(...skipping 153 matching lines...) Expand 10 before | Expand all | Expand 10 after
1070 // RBX: next object start. 1074 // RBX: next object start.
1071 // RDX: new object type arguments (if is_cls_parameterized). 1075 // RDX: new object type arguments (if is_cls_parameterized).
1072 // R12: raw null. 1076 // R12: raw null.
1073 // First try inlining the initialization without a loop. 1077 // First try inlining the initialization without a loop.
1074 if (instance_size < (kInlineInstanceSize * kWordSize)) { 1078 if (instance_size < (kInlineInstanceSize * kWordSize)) {
1075 // Check if the object contains any non-header fields. 1079 // Check if the object contains any non-header fields.
1076 // Small objects are initialized using a consecutive set of writes. 1080 // Small objects are initialized using a consecutive set of writes.
1077 for (intptr_t current_offset = Instance::NextFieldOffset(); 1081 for (intptr_t current_offset = Instance::NextFieldOffset();
1078 current_offset < instance_size; 1082 current_offset < instance_size;
1079 current_offset += kWordSize) { 1083 current_offset += kWordSize) {
1080 __ StoreIntoObjectNoBarrier(RAX, 1084 __ InitializeFieldNoBarrier(RAX,
1081 FieldAddress(RAX, current_offset), 1085 FieldAddress(RAX, current_offset),
1082 R12); 1086 R12);
1083 } 1087 }
1084 } else { 1088 } else {
1085 __ leaq(RCX, FieldAddress(RAX, Instance::NextFieldOffset())); 1089 __ leaq(RCX, FieldAddress(RAX, Instance::NextFieldOffset()));
1086 // Loop until the whole object is initialized. 1090 // Loop until the whole object is initialized.
1087 // RAX: new object (tagged). 1091 // RAX: new object (tagged).
1088 // RBX: next object start. 1092 // RBX: next object start.
1089 // RCX: next word to be initialized. 1093 // RCX: next word to be initialized.
1090 // RDX: new object type arguments (if is_cls_parameterized). 1094 // RDX: new object type arguments (if is_cls_parameterized).
1091 Label init_loop; 1095 Label init_loop;
1092 Label done; 1096 Label done;
1093 __ Bind(&init_loop); 1097 __ Bind(&init_loop);
1094 __ cmpq(RCX, RBX); 1098 __ cmpq(RCX, RBX);
1095 __ j(ABOVE_EQUAL, &done, Assembler::kNearJump); 1099 __ j(ABOVE_EQUAL, &done, Assembler::kNearJump);
1096 __ StoreIntoObjectNoBarrier(RAX, Address(RCX, 0), R12); 1100 __ InitializeFieldNoBarrier(RAX, Address(RCX, 0), R12);
1097 __ addq(RCX, Immediate(kWordSize)); 1101 __ addq(RCX, Immediate(kWordSize));
1098 __ jmp(&init_loop, Assembler::kNearJump); 1102 __ jmp(&init_loop, Assembler::kNearJump);
1099 __ Bind(&done); 1103 __ Bind(&done);
1100 } 1104 }
1101 if (is_cls_parameterized) { 1105 if (is_cls_parameterized) {
1102 // RDX: new object type arguments. 1106 // RDX: new object type arguments.
1103 // Set the type arguments in the new object. 1107 // Set the type arguments in the new object.
1104 intptr_t offset = cls.type_arguments_field_offset(); 1108 intptr_t offset = cls.type_arguments_field_offset();
1105 __ StoreIntoObjectNoBarrier(RAX, FieldAddress(RAX, offset), RDX); 1109 __ InitializeFieldNoBarrier(RAX, FieldAddress(RAX, offset), RDX);
1106 } 1110 }
1107 // Done allocating and initializing the instance. 1111 // Done allocating and initializing the instance.
1108 // RAX: new object (tagged). 1112 // RAX: new object (tagged).
1109 __ ret(); 1113 __ ret();
1110 1114
1111 __ Bind(&slow_case); 1115 __ Bind(&slow_case);
1112 } 1116 }
1113 // If is_cls_parameterized: 1117 // If is_cls_parameterized:
1114 // RDX: new object type arguments. 1118 // RDX: new object type arguments.
1115 // Create a stub frame. 1119 // Create a stub frame.
(...skipping 507 matching lines...) Expand 10 before | Expand all | Expand 10 after
1623 __ Stop("Incorrect IC data for unoptimized static call"); 1627 __ Stop("Incorrect IC data for unoptimized static call");
1624 __ Bind(&ok); 1628 __ Bind(&ok);
1625 } 1629 }
1626 #endif // DEBUG 1630 #endif // DEBUG
1627 1631
1628 // Check single stepping. 1632 // Check single stepping.
1629 Label stepping, done_stepping; 1633 Label stepping, done_stepping;
1630 __ LoadIsolate(RAX); 1634 __ LoadIsolate(RAX);
1631 __ movzxb(RAX, Address(RAX, Isolate::single_step_offset())); 1635 __ movzxb(RAX, Address(RAX, Isolate::single_step_offset()));
1632 __ cmpq(RAX, Immediate(0)); 1636 __ cmpq(RAX, Immediate(0));
1633 __ j(NOT_EQUAL, &stepping, Assembler::kNearJump); 1637 #if defined(DEBUG)
1638 static const bool kJumpLength = Assembler::kFarJump;
1639 #else
1640 static const bool kJumpLength = Assembler::kNearJump;
1641 #endif // DEBUG
1642 __ j(NOT_EQUAL, &stepping, kJumpLength);
1634 __ Bind(&done_stepping); 1643 __ Bind(&done_stepping);
1635 1644
1636 // RBX: IC data object (preserved). 1645 // RBX: IC data object (preserved).
1637 __ movq(R12, FieldAddress(RBX, ICData::ic_data_offset())); 1646 __ movq(R12, FieldAddress(RBX, ICData::ic_data_offset()));
1638 // R12: ic_data_array with entries: target functions and count. 1647 // R12: ic_data_array with entries: target functions and count.
1639 __ leaq(R12, FieldAddress(R12, Array::data_offset())); 1648 __ leaq(R12, FieldAddress(R12, Array::data_offset()));
1640 // R12: points directly to the first ic data array element. 1649 // R12: points directly to the first ic data array element.
1641 const intptr_t target_offset = ICData::TargetIndexFor(0) * kWordSize; 1650 const intptr_t target_offset = ICData::TargetIndexFor(0) * kWordSize;
1642 const intptr_t count_offset = ICData::CountIndexFor(0) * kWordSize; 1651 const intptr_t count_offset = ICData::CountIndexFor(0) * kWordSize;
1643 1652
(...skipping 425 matching lines...) Expand 10 before | Expand all | Expand 10 after
2069 2078
2070 __ movq(left, Address(RSP, 2 * kWordSize)); 2079 __ movq(left, Address(RSP, 2 * kWordSize));
2071 __ movq(right, Address(RSP, 1 * kWordSize)); 2080 __ movq(right, Address(RSP, 1 * kWordSize));
2072 GenerateIdenticalWithNumberCheckStub(assembler, left, right); 2081 GenerateIdenticalWithNumberCheckStub(assembler, left, right);
2073 __ ret(); 2082 __ ret();
2074 } 2083 }
2075 2084
2076 } // namespace dart 2085 } // namespace dart
2077 2086
2078 #endif // defined TARGET_ARCH_X64 2087 #endif // defined TARGET_ARCH_X64
OLDNEW
« runtime/vm/assembler_x64.cc ('K') | « runtime/vm/intrinsifier_x64.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698