OLD | NEW |
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 646 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
657 | 657 |
658 const intptr_t fixed_size_plus_alignment_padding = | 658 const intptr_t fixed_size_plus_alignment_padding = |
659 sizeof(RawArray) + kObjectAlignment - 1; | 659 sizeof(RawArray) + kObjectAlignment - 1; |
660 // RDI is a Smi. | 660 // RDI is a Smi. |
661 __ leaq(RDI, Address(RDI, TIMES_4, fixed_size_plus_alignment_padding)); | 661 __ leaq(RDI, Address(RDI, TIMES_4, fixed_size_plus_alignment_padding)); |
662 ASSERT(kSmiTagShift == 1); | 662 ASSERT(kSmiTagShift == 1); |
663 __ andq(RDI, Immediate(-kObjectAlignment)); | 663 __ andq(RDI, Immediate(-kObjectAlignment)); |
664 | 664 |
665 const intptr_t cid = kArrayCid; | 665 const intptr_t cid = kArrayCid; |
666 Heap::Space space = Heap::kNew; | 666 Heap::Space space = Heap::kNew; |
667 __ movq(R13, Address(THR, Thread::heap_offset())); | 667 __ movq(RAX, Address(THR, Thread::top_offset())); |
668 __ movq(RAX, Address(R13, Heap::TopOffset(space))); | |
669 | 668 |
670 // RDI: allocation size. | 669 // RDI: allocation size. |
671 __ movq(RCX, RAX); | 670 __ movq(RCX, RAX); |
672 __ addq(RCX, RDI); | 671 __ addq(RCX, RDI); |
673 __ j(CARRY, &slow_case); | 672 __ j(CARRY, &slow_case); |
674 | 673 |
675 // Check if the allocation fits into the remaining space. | 674 // Check if the allocation fits into the remaining space. |
676 // RAX: potential new object start. | 675 // RAX: potential new object start. |
677 // RCX: potential next object start. | 676 // RCX: potential next object start. |
678 // RDI: allocation size. | 677 // RDI: allocation size. |
679 // R13: heap. | 678 // R13: heap. |
680 __ cmpq(RCX, Address(R13, Heap::EndOffset(space))); | 679 __ cmpq(RCX, Address(THR, Thread::end_offset())); |
681 __ j(ABOVE_EQUAL, &slow_case); | 680 __ j(ABOVE_EQUAL, &slow_case); |
682 | 681 |
683 // Successfully allocated the object(s), now update top to point to | 682 // Successfully allocated the object(s), now update top to point to |
684 // next object start and initialize the object. | 683 // next object start and initialize the object. |
685 __ movq(Address(R13, Heap::TopOffset(space)), RCX); | 684 __ movq(Address(THR, Thread::top_offset()), RCX); |
686 __ addq(RAX, Immediate(kHeapObjectTag)); | 685 __ addq(RAX, Immediate(kHeapObjectTag)); |
687 NOT_IN_PRODUCT(__ UpdateAllocationStatsWithSize(cid, RDI, space)); | 686 NOT_IN_PRODUCT(__ UpdateAllocationStatsWithSize(cid, RDI, space)); |
688 // Initialize the tags. | 687 // Initialize the tags. |
689 // RAX: new object start as a tagged pointer. | 688 // RAX: new object start as a tagged pointer. |
690 // RDI: allocation size. | 689 // RDI: allocation size. |
691 { | 690 { |
692 Label size_tag_overflow, done; | 691 Label size_tag_overflow, done; |
693 __ cmpq(RDI, Immediate(RawObject::SizeTag::kMaxSizeTag)); | 692 __ cmpq(RDI, Immediate(RawObject::SizeTag::kMaxSizeTag)); |
694 __ j(ABOVE, &size_tag_overflow, Assembler::kNearJump); | 693 __ j(ABOVE, &size_tag_overflow, Assembler::kNearJump); |
695 __ shlq(RDI, Immediate(RawObject::kSizeTagPos - kObjectAlignmentLog2)); | 694 __ shlq(RDI, Immediate(RawObject::kSizeTagPos - kObjectAlignmentLog2)); |
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
906 __ andq(R13, Immediate(-kObjectAlignment)); | 905 __ andq(R13, Immediate(-kObjectAlignment)); |
907 | 906 |
908 // Check for allocation tracing. | 907 // Check for allocation tracing. |
909 NOT_IN_PRODUCT( | 908 NOT_IN_PRODUCT( |
910 __ MaybeTraceAllocation(kContextCid, &slow_case, Assembler::kFarJump)); | 909 __ MaybeTraceAllocation(kContextCid, &slow_case, Assembler::kFarJump)); |
911 | 910 |
912 // Now allocate the object. | 911 // Now allocate the object. |
913 // R10: number of context variables. | 912 // R10: number of context variables. |
914 const intptr_t cid = kContextCid; | 913 const intptr_t cid = kContextCid; |
915 Heap::Space space = Heap::kNew; | 914 Heap::Space space = Heap::kNew; |
916 __ movq(RCX, Address(THR, Thread::heap_offset())); | 915 __ movq(RAX, Address(THR, Thread::top_offset())); |
917 __ movq(RAX, Address(RCX, Heap::TopOffset(space))); | |
918 __ addq(R13, RAX); | 916 __ addq(R13, RAX); |
919 // Check if the allocation fits into the remaining space. | 917 // Check if the allocation fits into the remaining space. |
920 // RAX: potential new object. | 918 // RAX: potential new object. |
921 // R13: potential next object start. | 919 // R13: potential next object start. |
922 // R10: number of context variables. | 920 // R10: number of context variables. |
923 // RCX: heap. | 921 // RCX: heap. |
924 __ cmpq(R13, Address(RCX, Heap::EndOffset(space))); | 922 __ cmpq(R13, Address(THR, Thread::end_offset())); |
925 if (FLAG_use_slow_path) { | 923 if (FLAG_use_slow_path) { |
926 __ jmp(&slow_case); | 924 __ jmp(&slow_case); |
927 } else { | 925 } else { |
928 __ j(ABOVE_EQUAL, &slow_case); | 926 __ j(ABOVE_EQUAL, &slow_case); |
929 } | 927 } |
930 | 928 |
931 // Successfully allocated the object, now update top to point to | 929 // Successfully allocated the object, now update top to point to |
932 // next object start and initialize the object. | 930 // next object start and initialize the object. |
933 // RAX: new object. | 931 // RAX: new object. |
934 // R13: next object start. | 932 // R13: next object start. |
935 // R10: number of context variables. | 933 // R10: number of context variables. |
936 // RCX: heap. | 934 // RCX: heap. |
937 __ movq(Address(RCX, Heap::TopOffset(space)), R13); | 935 __ movq(Address(THR, Thread::top_offset()), R13); |
938 // R13: Size of allocation in bytes. | 936 // R13: Size of allocation in bytes. |
939 __ subq(R13, RAX); | 937 __ subq(R13, RAX); |
940 __ addq(RAX, Immediate(kHeapObjectTag)); | 938 __ addq(RAX, Immediate(kHeapObjectTag)); |
941 // Generate isolate-independent code to allow sharing between isolates. | 939 // Generate isolate-independent code to allow sharing between isolates. |
942 NOT_IN_PRODUCT(__ UpdateAllocationStatsWithSize(cid, R13, space)); | 940 NOT_IN_PRODUCT(__ UpdateAllocationStatsWithSize(cid, R13, space)); |
943 | 941 |
944 // Calculate the size tag. | 942 // Calculate the size tag. |
945 // RAX: new object. | 943 // RAX: new object. |
946 // R10: number of context variables. | 944 // R10: number of context variables. |
947 { | 945 { |
(...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1105 // RDX: instantiated type arguments. | 1103 // RDX: instantiated type arguments. |
1106 } | 1104 } |
1107 Isolate* isolate = Isolate::Current(); | 1105 Isolate* isolate = Isolate::Current(); |
1108 if (FLAG_inline_alloc && Heap::IsAllocatableInNewSpace(instance_size) && | 1106 if (FLAG_inline_alloc && Heap::IsAllocatableInNewSpace(instance_size) && |
1109 !cls.TraceAllocation(isolate)) { | 1107 !cls.TraceAllocation(isolate)) { |
1110 Label slow_case; | 1108 Label slow_case; |
1111 // Allocate the object and update top to point to | 1109 // Allocate the object and update top to point to |
1112 // next object start and initialize the allocated object. | 1110 // next object start and initialize the allocated object. |
1113 // RDX: instantiated type arguments (if is_cls_parameterized). | 1111 // RDX: instantiated type arguments (if is_cls_parameterized). |
1114 Heap::Space space = Heap::kNew; | 1112 Heap::Space space = Heap::kNew; |
1115 __ movq(RCX, Address(THR, Thread::heap_offset())); | 1113 __ movq(RAX, Address(THR, Thread::top_offset())); |
1116 __ movq(RAX, Address(RCX, Heap::TopOffset(space))); | |
1117 __ leaq(RBX, Address(RAX, instance_size)); | 1114 __ leaq(RBX, Address(RAX, instance_size)); |
1118 // Check if the allocation fits into the remaining space. | 1115 // Check if the allocation fits into the remaining space. |
1119 // RAX: potential new object start. | 1116 // RAX: potential new object start. |
1120 // RBX: potential next object start. | 1117 // RBX: potential next object start. |
1121 // RCX: heap. | 1118 // RCX: heap. |
1122 __ cmpq(RBX, Address(RCX, Heap::EndOffset(space))); | 1119 __ cmpq(RBX, Address(THR, Thread::end_offset())); |
1123 if (FLAG_use_slow_path) { | 1120 if (FLAG_use_slow_path) { |
1124 __ jmp(&slow_case); | 1121 __ jmp(&slow_case); |
1125 } else { | 1122 } else { |
1126 __ j(ABOVE_EQUAL, &slow_case); | 1123 __ j(ABOVE_EQUAL, &slow_case); |
1127 } | 1124 } |
1128 __ movq(Address(RCX, Heap::TopOffset(space)), RBX); | 1125 __ movq(Address(THR, Thread::top_offset()), RBX); |
1129 NOT_IN_PRODUCT(__ UpdateAllocationStats(cls.id(), space)); | 1126 NOT_IN_PRODUCT(__ UpdateAllocationStats(cls.id(), space)); |
1130 | 1127 |
1131 // RAX: new object start (untagged). | 1128 // RAX: new object start (untagged). |
1132 // RBX: next object start. | 1129 // RBX: next object start. |
1133 // RDX: new object type arguments (if is_cls_parameterized). | 1130 // RDX: new object type arguments (if is_cls_parameterized). |
1134 // Set the tags. | 1131 // Set the tags. |
1135 uword tags = 0; | 1132 uword tags = 0; |
1136 tags = RawObject::SizeTag::update(instance_size, tags); | 1133 tags = RawObject::SizeTag::update(instance_size, tags); |
1137 ASSERT(cls.id() != kIllegalCid); | 1134 ASSERT(cls.id() != kIllegalCid); |
1138 tags = RawObject::ClassIdTag::update(cls.id(), tags); | 1135 tags = RawObject::ClassIdTag::update(cls.id(), tags); |
(...skipping 1181 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2320 } | 2317 } |
2321 | 2318 |
2322 | 2319 |
2323 void StubCode::GenerateAsynchronousGapMarkerStub(Assembler* assembler) { | 2320 void StubCode::GenerateAsynchronousGapMarkerStub(Assembler* assembler) { |
2324 __ int3(); | 2321 __ int3(); |
2325 } | 2322 } |
2326 | 2323 |
2327 } // namespace dart | 2324 } // namespace dart |
2328 | 2325 |
2329 #endif // defined TARGET_ARCH_X64 | 2326 #endif // defined TARGET_ARCH_X64 |
OLD | NEW |