OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 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 #ifndef V8_ARM64_ASSEMBLER_ARM64_INL_H_ | 5 #ifndef V8_ARM64_ASSEMBLER_ARM64_INL_H_ |
6 #define V8_ARM64_ASSEMBLER_ARM64_INL_H_ | 6 #define V8_ARM64_ASSEMBLER_ARM64_INL_H_ |
7 | 7 |
8 #include "src/arm64/assembler-arm64.h" | 8 #include "src/arm64/assembler-arm64.h" |
9 #include "src/assembler.h" | 9 #include "src/assembler.h" |
10 #include "src/debug/debug.h" | 10 #include "src/debug/debug.h" |
(...skipping 13 matching lines...) Expand all Loading... |
24 // Absolute code pointer inside code object moves with the code object. | 24 // Absolute code pointer inside code object moves with the code object. |
25 intptr_t* p = reinterpret_cast<intptr_t*>(pc_); | 25 intptr_t* p = reinterpret_cast<intptr_t*>(pc_); |
26 *p += delta; // Relocate entry. | 26 *p += delta; // Relocate entry. |
27 } | 27 } |
28 | 28 |
29 | 29 |
30 void RelocInfo::set_target_address(Address target, | 30 void RelocInfo::set_target_address(Address target, |
31 WriteBarrierMode write_barrier_mode, | 31 WriteBarrierMode write_barrier_mode, |
32 ICacheFlushMode icache_flush_mode) { | 32 ICacheFlushMode icache_flush_mode) { |
33 DCHECK(IsCodeTarget(rmode_) || IsRuntimeEntry(rmode_)); | 33 DCHECK(IsCodeTarget(rmode_) || IsRuntimeEntry(rmode_)); |
34 Assembler::set_target_address_at(pc_, host_, target, icache_flush_mode); | 34 Assembler::set_target_address_at(isolate_, pc_, host_, target, |
| 35 icache_flush_mode); |
35 if (write_barrier_mode == UPDATE_WRITE_BARRIER && host() != NULL && | 36 if (write_barrier_mode == UPDATE_WRITE_BARRIER && host() != NULL && |
36 IsCodeTarget(rmode_)) { | 37 IsCodeTarget(rmode_)) { |
37 Object* target_code = Code::GetCodeFromTargetAddress(target); | 38 Object* target_code = Code::GetCodeFromTargetAddress(target); |
38 host()->GetHeap()->incremental_marking()->RecordWriteIntoCode( | 39 host()->GetHeap()->incremental_marking()->RecordWriteIntoCode( |
39 host(), this, HeapObject::cast(target_code)); | 40 host(), this, HeapObject::cast(target_code)); |
40 } | 41 } |
41 } | 42 } |
42 | 43 |
43 | 44 |
44 inline int CPURegister::code() const { | 45 inline int CPURegister::code() const { |
(...skipping 596 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
641 } else { | 642 } else { |
642 // Verify the instruction sequence. | 643 // Verify the instruction sequence. |
643 DCHECK(instr->IsLdrLiteralX()); | 644 DCHECK(instr->IsLdrLiteralX()); |
644 DCHECK(instr->following(1)->IsBranchAndLinkToRegister()); | 645 DCHECK(instr->following(1)->IsBranchAndLinkToRegister()); |
645 return pc + Assembler::kCallSizeWithRelocation; | 646 return pc + Assembler::kCallSizeWithRelocation; |
646 } | 647 } |
647 } | 648 } |
648 | 649 |
649 | 650 |
650 void Assembler::deserialization_set_special_target_at( | 651 void Assembler::deserialization_set_special_target_at( |
651 Address constant_pool_entry, Code* code, Address target) { | 652 Isolate* isolate, Address constant_pool_entry, Code* code, Address target) { |
652 Memory::Address_at(constant_pool_entry) = target; | 653 Memory::Address_at(constant_pool_entry) = target; |
653 } | 654 } |
654 | 655 |
655 | 656 |
656 void Assembler::deserialization_set_target_internal_reference_at( | 657 void Assembler::deserialization_set_target_internal_reference_at( |
657 Address pc, Address target, RelocInfo::Mode mode) { | 658 Isolate* isolate, Address pc, Address target, RelocInfo::Mode mode) { |
658 Memory::Address_at(pc) = target; | 659 Memory::Address_at(pc) = target; |
659 } | 660 } |
660 | 661 |
661 | 662 |
662 void Assembler::set_target_address_at(Address pc, Address constant_pool, | 663 void Assembler::set_target_address_at(Isolate* isolate, Address pc, |
663 Address target, | 664 Address constant_pool, Address target, |
664 ICacheFlushMode icache_flush_mode) { | 665 ICacheFlushMode icache_flush_mode) { |
665 Memory::Address_at(target_pointer_address_at(pc)) = target; | 666 Memory::Address_at(target_pointer_address_at(pc)) = target; |
666 // Intuitively, we would think it is necessary to always flush the | 667 // Intuitively, we would think it is necessary to always flush the |
667 // instruction cache after patching a target address in the code as follows: | 668 // instruction cache after patching a target address in the code as follows: |
668 // Assembler::FlushICache(isolate(), pc, sizeof(target)); | 669 // Assembler::FlushICache(isolate(), pc, sizeof(target)); |
669 // However, on ARM, an instruction is actually patched in the case of | 670 // However, on ARM, an instruction is actually patched in the case of |
670 // embedded constants of the form: | 671 // embedded constants of the form: |
671 // ldr ip, [pc, #...] | 672 // ldr ip, [pc, #...] |
672 // since the instruction accessing this address in the constant pool remains | 673 // since the instruction accessing this address in the constant pool remains |
673 // unchanged, a flush is not required. | 674 // unchanged, a flush is not required. |
674 } | 675 } |
675 | 676 |
676 | 677 |
677 void Assembler::set_target_address_at(Address pc, | 678 void Assembler::set_target_address_at(Isolate* isolate, Address pc, Code* code, |
678 Code* code, | |
679 Address target, | 679 Address target, |
680 ICacheFlushMode icache_flush_mode) { | 680 ICacheFlushMode icache_flush_mode) { |
681 Address constant_pool = code ? code->constant_pool() : NULL; | 681 Address constant_pool = code ? code->constant_pool() : NULL; |
682 set_target_address_at(pc, constant_pool, target, icache_flush_mode); | 682 set_target_address_at(isolate, pc, constant_pool, target, icache_flush_mode); |
683 } | 683 } |
684 | 684 |
685 | 685 |
686 int RelocInfo::target_address_size() { | 686 int RelocInfo::target_address_size() { |
687 return kPointerSize; | 687 return kPointerSize; |
688 } | 688 } |
689 | 689 |
690 | 690 |
691 Address RelocInfo::target_address() { | 691 Address RelocInfo::target_address() { |
692 DCHECK(IsCodeTarget(rmode_) || IsRuntimeEntry(rmode_)); | 692 DCHECK(IsCodeTarget(rmode_) || IsRuntimeEntry(rmode_)); |
(...skipping 25 matching lines...) Expand all Loading... |
718 DCHECK(IsCodeTarget(rmode_) || rmode_ == EMBEDDED_OBJECT); | 718 DCHECK(IsCodeTarget(rmode_) || rmode_ == EMBEDDED_OBJECT); |
719 return Handle<Object>(reinterpret_cast<Object**>( | 719 return Handle<Object>(reinterpret_cast<Object**>( |
720 Assembler::target_address_at(pc_, host_))); | 720 Assembler::target_address_at(pc_, host_))); |
721 } | 721 } |
722 | 722 |
723 | 723 |
724 void RelocInfo::set_target_object(Object* target, | 724 void RelocInfo::set_target_object(Object* target, |
725 WriteBarrierMode write_barrier_mode, | 725 WriteBarrierMode write_barrier_mode, |
726 ICacheFlushMode icache_flush_mode) { | 726 ICacheFlushMode icache_flush_mode) { |
727 DCHECK(IsCodeTarget(rmode_) || rmode_ == EMBEDDED_OBJECT); | 727 DCHECK(IsCodeTarget(rmode_) || rmode_ == EMBEDDED_OBJECT); |
728 Assembler::set_target_address_at(pc_, host_, | 728 Assembler::set_target_address_at(isolate_, pc_, host_, |
729 reinterpret_cast<Address>(target), | 729 reinterpret_cast<Address>(target), |
730 icache_flush_mode); | 730 icache_flush_mode); |
731 if (write_barrier_mode == UPDATE_WRITE_BARRIER && | 731 if (write_barrier_mode == UPDATE_WRITE_BARRIER && |
732 host() != NULL && | 732 host() != NULL && |
733 target->IsHeapObject()) { | 733 target->IsHeapObject()) { |
734 host()->GetHeap()->incremental_marking()->RecordWrite( | 734 host()->GetHeap()->incremental_marking()->RecordWrite( |
735 host(), &Memory::Object_at(pc_), HeapObject::cast(target)); | 735 host(), &Memory::Object_at(pc_), HeapObject::cast(target)); |
736 } | 736 } |
737 } | 737 } |
738 | 738 |
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
825 // For the above sequences the Relocinfo points to the load literal loading | 825 // For the above sequences the Relocinfo points to the load literal loading |
826 // the call address. | 826 // the call address. |
827 STATIC_ASSERT(Assembler::kPatchDebugBreakSlotAddressOffset == 0); | 827 STATIC_ASSERT(Assembler::kPatchDebugBreakSlotAddressOffset == 0); |
828 return Assembler::target_address_at(pc_, host_); | 828 return Assembler::target_address_at(pc_, host_); |
829 } | 829 } |
830 | 830 |
831 | 831 |
832 void RelocInfo::set_debug_call_address(Address target) { | 832 void RelocInfo::set_debug_call_address(Address target) { |
833 DCHECK(IsDebugBreakSlot(rmode()) && IsPatchedDebugBreakSlotSequence()); | 833 DCHECK(IsDebugBreakSlot(rmode()) && IsPatchedDebugBreakSlotSequence()); |
834 STATIC_ASSERT(Assembler::kPatchDebugBreakSlotAddressOffset == 0); | 834 STATIC_ASSERT(Assembler::kPatchDebugBreakSlotAddressOffset == 0); |
835 Assembler::set_target_address_at(pc_, host_, target); | 835 Assembler::set_target_address_at(isolate_, pc_, host_, target); |
836 if (host() != NULL) { | 836 if (host() != NULL) { |
837 Object* target_code = Code::GetCodeFromTargetAddress(target); | 837 Object* target_code = Code::GetCodeFromTargetAddress(target); |
838 host()->GetHeap()->incremental_marking()->RecordWriteIntoCode( | 838 host()->GetHeap()->incremental_marking()->RecordWriteIntoCode( |
839 host(), this, HeapObject::cast(target_code)); | 839 host(), this, HeapObject::cast(target_code)); |
840 } | 840 } |
841 } | 841 } |
842 | 842 |
843 | 843 |
844 void RelocInfo::WipeOut() { | 844 void RelocInfo::WipeOut() { |
845 DCHECK(IsEmbeddedObject(rmode_) || IsCodeTarget(rmode_) || | 845 DCHECK(IsEmbeddedObject(rmode_) || IsCodeTarget(rmode_) || |
846 IsRuntimeEntry(rmode_) || IsExternalReference(rmode_) || | 846 IsRuntimeEntry(rmode_) || IsExternalReference(rmode_) || |
847 IsInternalReference(rmode_)); | 847 IsInternalReference(rmode_)); |
848 if (IsInternalReference(rmode_)) { | 848 if (IsInternalReference(rmode_)) { |
849 Memory::Address_at(pc_) = NULL; | 849 Memory::Address_at(pc_) = NULL; |
850 } else { | 850 } else { |
851 Assembler::set_target_address_at(pc_, host_, NULL); | 851 Assembler::set_target_address_at(isolate_, pc_, host_, NULL); |
852 } | 852 } |
853 } | 853 } |
854 | 854 |
855 | 855 |
856 bool RelocInfo::IsPatchedReturnSequence() { | 856 bool RelocInfo::IsPatchedReturnSequence() { |
857 // The sequence must be: | 857 // The sequence must be: |
858 // ldr ip0, [pc, #offset] | 858 // ldr ip0, [pc, #offset] |
859 // blr ip0 | 859 // blr ip0 |
860 // See arm64/debug-arm64.cc DebugCodegen::PatchDebugBreakSlot | 860 // See arm64/debug-arm64.cc DebugCodegen::PatchDebugBreakSlot |
861 Instruction* i1 = reinterpret_cast<Instruction*>(pc_); | 861 Instruction* i1 = reinterpret_cast<Instruction*>(pc_); |
(...skipping 394 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1256 | 1256 |
1257 void Assembler::ClearRecordedAstId() { | 1257 void Assembler::ClearRecordedAstId() { |
1258 recorded_ast_id_ = TypeFeedbackId::None(); | 1258 recorded_ast_id_ = TypeFeedbackId::None(); |
1259 } | 1259 } |
1260 | 1260 |
1261 | 1261 |
1262 } // namespace internal | 1262 } // namespace internal |
1263 } // namespace v8 | 1263 } // namespace v8 |
1264 | 1264 |
1265 #endif // V8_ARM64_ASSEMBLER_ARM64_INL_H_ | 1265 #endif // V8_ARM64_ASSEMBLER_ARM64_INL_H_ |
OLD | NEW |