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

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

Issue 1156593002: Cache current thread in a reserved register and use it in LoadIsolate (Closed) Base URL: https://github.com/dart-lang/sdk.git@master
Patch Set: Added more comments. Created 5 years, 7 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
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 683 matching lines...) Expand 10 before | Expand all | Expand 10 after
694 __ JmpPatchable(&stub_code->FixAllocateArrayStubTargetLabel(), new_pp); 694 __ JmpPatchable(&stub_code->FixAllocateArrayStubTargetLabel(), new_pp);
695 } 695 }
696 696
697 697
698 // Called when invoking Dart code from C++ (VM code). 698 // Called when invoking Dart code from C++ (VM code).
699 // Input parameters: 699 // Input parameters:
700 // RSP : points to return address. 700 // RSP : points to return address.
701 // RDI : entrypoint of the Dart function to call. 701 // RDI : entrypoint of the Dart function to call.
702 // RSI : arguments descriptor array. 702 // RSI : arguments descriptor array.
703 // RDX : arguments array. 703 // RDX : arguments array.
704 // RCX : new context containing the current isolate pointer. 704 // RCX : current thread.
705 void StubCode::GenerateInvokeDartCodeStub(Assembler* assembler) { 705 void StubCode::GenerateInvokeDartCodeStub(Assembler* assembler) {
706 // Save frame pointer coming in. 706 // Save frame pointer coming in.
707 __ EnterFrame(0); 707 __ EnterFrame(0);
708 708
709 const Register kEntryPointReg = CallingConventions::kArg1Reg; 709 const Register kEntryPointReg = CallingConventions::kArg1Reg;
710 const Register kArgDescReg = CallingConventions::kArg2Reg; 710 const Register kArgDescReg = CallingConventions::kArg2Reg;
711 const Register kArgsReg = CallingConventions::kArg3Reg; 711 const Register kArgsReg = CallingConventions::kArg3Reg;
712 const Register kThreadReg = CallingConventions::kArg4Reg;
712 713
713 // At this point, the stack looks like: 714 // At this point, the stack looks like:
714 // | saved RBP | <-- RBP 715 // | saved RBP | <-- RBP
715 // | saved PC (return to DartEntry::InvokeFunction) | 716 // | saved PC (return to DartEntry::InvokeFunction) |
716 717
717 const intptr_t kInitialOffset = 1; 718 const intptr_t kInitialOffset = 1;
718 // Save arguments descriptor array. 719 // Save arguments descriptor array.
719 const intptr_t kArgumentsDescOffset = -(kInitialOffset) * kWordSize; 720 const intptr_t kArgumentsDescOffset = -(kInitialOffset) * kWordSize;
720 __ pushq(kArgDescReg); 721 __ pushq(kArgDescReg);
721 722
722 // Save C++ ABI callee-saved registers. 723 // Save C++ ABI callee-saved registers.
723 __ PushRegisters(CallingConventions::kCalleeSaveCpuRegisters, 724 __ PushRegisters(CallingConventions::kCalleeSaveCpuRegisters,
724 CallingConventions::kCalleeSaveXmmRegisters); 725 CallingConventions::kCalleeSaveXmmRegisters);
725 726
726 // We now load the pool pointer(PP) as we are about to invoke dart code and we 727 // We now load the pool pointer(PP) as we are about to invoke dart code and we
727 // could potentially invoke some intrinsic functions which need the PP to be 728 // could potentially invoke some intrinsic functions which need the PP to be
728 // set up. 729 // set up.
729 __ LoadPoolPointer(PP); 730 __ LoadPoolPointer(PP);
730 731
731 // If any additional (or fewer) values are pushed, the offsets in 732 // If any additional (or fewer) values are pushed, the offsets in
732 // kExitLinkSlotFromEntryFp will need to be changed. 733 // kExitLinkSlotFromEntryFp will need to be changed.
733 734
735 // Set up THR, which caches the current thread in Dart code.
736 if (THR != kThreadReg) {
737 __ movq(THR, kThreadReg);
738 }
734 // Load Isolate pointer into kIsolateReg. 739 // Load Isolate pointer into kIsolateReg.
735 const Register kIsolateReg = RBX; 740 const Register kIsolateReg = RBX;
736 __ LoadIsolate(kIsolateReg); 741 __ LoadIsolate(kIsolateReg);
737 742
738 // Save the current VMTag on the stack. 743 // Save the current VMTag on the stack.
739 __ movq(RAX, Address(kIsolateReg, Isolate::vm_tag_offset())); 744 __ movq(RAX, Address(kIsolateReg, Isolate::vm_tag_offset()));
740 __ pushq(RAX); 745 __ pushq(RAX);
741 746
742 // Mark that the isolate is executing Dart code. 747 // Mark that the isolate is executing Dart code.
743 __ movq(Address(kIsolateReg, Isolate::vm_tag_offset()), 748 __ movq(Address(kIsolateReg, Isolate::vm_tag_offset()),
(...skipping 554 matching lines...) Expand 10 before | Expand all | Expand 10 after
1298 __ Bind(&error); 1303 __ Bind(&error);
1299 __ Stop("Incorrect IC data"); 1304 __ Stop("Incorrect IC data");
1300 __ Bind(&ok); 1305 __ Bind(&ok);
1301 #endif 1306 #endif
1302 1307
1303 if (FLAG_optimization_counter_threshold >= 0) { 1308 if (FLAG_optimization_counter_threshold >= 0) {
1304 const intptr_t count_offset = ICData::CountIndexFor(num_args) * kWordSize; 1309 const intptr_t count_offset = ICData::CountIndexFor(num_args) * kWordSize;
1305 // Update counter. 1310 // Update counter.
1306 __ movq(R8, Address(R12, count_offset)); 1311 __ movq(R8, Address(R12, count_offset));
1307 __ addq(R8, Immediate(Smi::RawValue(1))); 1312 __ addq(R8, Immediate(Smi::RawValue(1)));
1308 __ movq(R9, Immediate(Smi::RawValue(Smi::kMaxValue))); 1313 __ movq(R13, Immediate(Smi::RawValue(Smi::kMaxValue)));
1309 __ cmovnoq(R9, R8); 1314 __ cmovnoq(R13, R8);
1310 __ StoreIntoSmiField(Address(R12, count_offset), R9); 1315 __ StoreIntoSmiField(Address(R12, count_offset), R13);
1311 } 1316 }
1312 1317
1313 __ ret(); 1318 __ ret();
1314 } 1319 }
1315 1320
1316 1321
1317 // Generate inline cache check for 'num_args'. 1322 // Generate inline cache check for 'num_args'.
1318 // RBX: Inline cache data object. 1323 // RBX: Inline cache data object.
1319 // TOS(0): return address 1324 // TOS(0): return address
1320 // Control flow: 1325 // Control flow:
(...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after
1464 // R12: Pointer to an IC data check group. 1469 // R12: Pointer to an IC data check group.
1465 const intptr_t target_offset = ICData::TargetIndexFor(num_args) * kWordSize; 1470 const intptr_t target_offset = ICData::TargetIndexFor(num_args) * kWordSize;
1466 const intptr_t count_offset = ICData::CountIndexFor(num_args) * kWordSize; 1471 const intptr_t count_offset = ICData::CountIndexFor(num_args) * kWordSize;
1467 __ movq(RAX, Address(R12, target_offset)); 1472 __ movq(RAX, Address(R12, target_offset));
1468 1473
1469 if (FLAG_optimization_counter_threshold >= 0) { 1474 if (FLAG_optimization_counter_threshold >= 0) {
1470 // Update counter. 1475 // Update counter.
1471 __ Comment("Update caller's counter"); 1476 __ Comment("Update caller's counter");
1472 __ movq(R8, Address(R12, count_offset)); 1477 __ movq(R8, Address(R12, count_offset));
1473 __ addq(R8, Immediate(Smi::RawValue(1))); 1478 __ addq(R8, Immediate(Smi::RawValue(1)));
1474 __ movq(R9, Immediate(Smi::RawValue(Smi::kMaxValue))); 1479 __ movq(R13, Immediate(Smi::RawValue(Smi::kMaxValue)));
1475 __ cmovnoq(R9, R8); 1480 __ cmovnoq(R13, R8);
1476 __ StoreIntoSmiField(Address(R12, count_offset), R9); 1481 __ StoreIntoSmiField(Address(R12, count_offset), R13);
1477 } 1482 }
1478 1483
1479 __ Comment("Call target"); 1484 __ Comment("Call target");
1480 __ Bind(&call_target_function); 1485 __ Bind(&call_target_function);
1481 // RAX: Target function. 1486 // RAX: Target function.
1482 Label is_compiled; 1487 Label is_compiled;
1483 __ movq(RCX, FieldAddress(RAX, Function::instructions_offset())); 1488 __ movq(RCX, FieldAddress(RAX, Function::instructions_offset()));
1484 __ addq(RCX, Immediate(Instructions::HeaderSize() - kHeapObjectTag)); 1489 __ addq(RCX, Immediate(Instructions::HeaderSize() - kHeapObjectTag));
1485 if (range_collection_mode == kCollectRanges) { 1490 if (range_collection_mode == kCollectRanges) {
1486 __ movq(R8, Address(RSP, + 1 * kWordSize)); 1491 __ movq(R8, Address(RSP, + 1 * kWordSize));
1487 if (num_args == 2) { 1492 if (num_args == 2) {
1488 __ movq(R9, Address(RSP, + 2 * kWordSize)); 1493 __ movq(R13, Address(RSP, + 2 * kWordSize));
1489 } 1494 }
1490 __ EnterStubFrame(); 1495 __ EnterStubFrame();
1491 __ pushq(RBX); 1496 __ pushq(RBX);
1492 if (num_args == 2) { 1497 if (num_args == 2) {
1493 __ pushq(R9); 1498 __ pushq(R13);
1494 } 1499 }
1495 __ pushq(R8); 1500 __ pushq(R8);
1496 __ call(RCX); 1501 __ call(RCX);
1497 1502
1498 Label done; 1503 Label done;
1499 __ movq(RDX, RAX); 1504 __ movq(RDX, RAX);
1500 __ movq(RBX, Address(RBP, kFirstLocalSlotFromFp * kWordSize)); 1505 __ movq(RBX, Address(RBP, kFirstLocalSlotFromFp * kWordSize));
1501 __ UpdateRangeFeedback(RDX, 2, RBX, RCX, &done); 1506 __ UpdateRangeFeedback(RDX, 2, RBX, RCX, &done);
1502 __ Bind(&done); 1507 __ Bind(&done);
1503 __ LeaveStubFrame(); 1508 __ LeaveStubFrame();
(...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after
1682 // R12: ic_data_array with entries: target functions and count. 1687 // R12: ic_data_array with entries: target functions and count.
1683 __ leaq(R12, FieldAddress(R12, Array::data_offset())); 1688 __ leaq(R12, FieldAddress(R12, Array::data_offset()));
1684 // R12: points directly to the first ic data array element. 1689 // R12: points directly to the first ic data array element.
1685 const intptr_t target_offset = ICData::TargetIndexFor(0) * kWordSize; 1690 const intptr_t target_offset = ICData::TargetIndexFor(0) * kWordSize;
1686 const intptr_t count_offset = ICData::CountIndexFor(0) * kWordSize; 1691 const intptr_t count_offset = ICData::CountIndexFor(0) * kWordSize;
1687 1692
1688 if (FLAG_optimization_counter_threshold >= 0) { 1693 if (FLAG_optimization_counter_threshold >= 0) {
1689 // Increment count for this call. 1694 // Increment count for this call.
1690 __ movq(R8, Address(R12, count_offset)); 1695 __ movq(R8, Address(R12, count_offset));
1691 __ addq(R8, Immediate(Smi::RawValue(1))); 1696 __ addq(R8, Immediate(Smi::RawValue(1)));
1692 __ movq(R9, Immediate(Smi::RawValue(Smi::kMaxValue))); 1697 __ movq(R13, Immediate(Smi::RawValue(Smi::kMaxValue)));
1693 __ cmovnoq(R9, R8); 1698 __ cmovnoq(R13, R8);
1694 __ StoreIntoSmiField(Address(R12, count_offset), R9); 1699 __ StoreIntoSmiField(Address(R12, count_offset), R13);
1695 } 1700 }
1696 1701
1697 // Load arguments descriptor into R10. 1702 // Load arguments descriptor into R10.
1698 __ movq(R10, FieldAddress(RBX, ICData::arguments_descriptor_offset())); 1703 __ movq(R10, FieldAddress(RBX, ICData::arguments_descriptor_offset()));
1699 1704
1700 // Get function and call it, if possible. 1705 // Get function and call it, if possible.
1701 __ movq(RAX, Address(R12, target_offset)); 1706 __ movq(RAX, Address(R12, target_offset));
1702 __ movq(RCX, FieldAddress(RAX, Function::instructions_offset())); 1707 __ movq(RCX, FieldAddress(RAX, Function::instructions_offset()));
1703 // RCX: Target instructions. 1708 // RCX: Target instructions.
1704 __ addq(RCX, Immediate(Instructions::HeaderSize() - kHeapObjectTag)); 1709 __ addq(RCX, Immediate(Instructions::HeaderSize() - kHeapObjectTag));
(...skipping 261 matching lines...) Expand 10 before | Expand all | Expand 10 after
1966 1971
1967 #if defined(_WIN64) 1972 #if defined(_WIN64)
1968 Register stacktrace_reg = RBX; 1973 Register stacktrace_reg = RBX;
1969 __ movq(stacktrace_reg, Address(RSP, 5 * kWordSize)); 1974 __ movq(stacktrace_reg, Address(RSP, 5 * kWordSize));
1970 Register isolate_reg = RDI; 1975 Register isolate_reg = RDI;
1971 __ movq(isolate_reg, Address(RSP, 6 * kWordSize)); 1976 __ movq(isolate_reg, Address(RSP, 6 * kWordSize));
1972 #else 1977 #else
1973 Register stacktrace_reg = CallingConventions::kArg5Reg; 1978 Register stacktrace_reg = CallingConventions::kArg5Reg;
1974 Register isolate_reg = CallingConventions::kArg6Reg; 1979 Register isolate_reg = CallingConventions::kArg6Reg;
1975 #endif 1980 #endif
1976 1981 // TODO(koda): Pass thread instead of isolate.
1982 __ movq(THR, Address(isolate_reg, Isolate::mutator_thread_offset()));
1977 __ movq(RBP, CallingConventions::kArg3Reg); 1983 __ movq(RBP, CallingConventions::kArg3Reg);
1978 __ movq(RSP, CallingConventions::kArg2Reg); 1984 __ movq(RSP, CallingConventions::kArg2Reg);
1979 __ movq(kStackTraceObjectReg, stacktrace_reg); 1985 __ movq(kStackTraceObjectReg, stacktrace_reg);
1980 __ movq(kExceptionObjectReg, CallingConventions::kArg4Reg); 1986 __ movq(kExceptionObjectReg, CallingConventions::kArg4Reg);
1981 // Set the tag. 1987 // Set the tag.
1982 __ movq(Address(isolate_reg, Isolate::vm_tag_offset()), 1988 __ movq(Address(isolate_reg, Isolate::vm_tag_offset()),
1983 Immediate(VMTag::kDartTagId)); 1989 Immediate(VMTag::kDartTagId));
1984 // Clear top exit frame. 1990 // Clear top exit frame.
1985 __ movq(Address(isolate_reg, Isolate::top_exit_frame_info_offset()), 1991 __ movq(Address(isolate_reg, Isolate::top_exit_frame_info_offset()),
1986 Immediate(0)); 1992 Immediate(0));
(...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after
2174 // Result: 2180 // Result:
2175 // RCX: entry point. 2181 // RCX: entry point.
2176 void StubCode::GenerateMegamorphicLookupStub(Assembler* assembler) { 2182 void StubCode::GenerateMegamorphicLookupStub(Assembler* assembler) {
2177 EmitMegamorphicLookup(assembler, RDI, RBX, RCX); 2183 EmitMegamorphicLookup(assembler, RDI, RBX, RCX);
2178 __ ret(); 2184 __ ret();
2179 } 2185 }
2180 2186
2181 } // namespace dart 2187 } // namespace dart
2182 2188
2183 #endif // defined TARGET_ARCH_X64 2189 #endif // defined TARGET_ARCH_X64
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698