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

Side by Side Diff: src/arm64/assembler-arm64.cc

Issue 222433002: ARM64: Introduce a version of ADR handling distant targets. (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Fix loop offset Created 6 years, 8 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
OLDNEW
1 // Copyright 2013 the V8 project authors. All rights reserved. 1 // Copyright 2013 the V8 project authors. All rights reserved.
2 // 2 //
3 // Redistribution and use in source and binary forms, with or without 3 // Redistribution and use in source and binary forms, with or without
4 // modification, are permitted provided that the following conditions are 4 // modification, are permitted provided that the following conditions are
5 // met: 5 // met:
6 // 6 //
7 // * Redistributions of source code must retain the above copyright 7 // * Redistributions of source code must retain the above copyright
8 // notice, this list of conditions and the following disclaimer. 8 // notice, this list of conditions and the following disclaimer.
9 // * Redistributions in binary form must reproduce the above 9 // * Redistributions in binary form must reproduce the above
10 // copyright notice, this list of conditions and the following 10 // copyright notice, this list of conditions and the following
(...skipping 2790 matching lines...) Expand 10 before | Expand all | Expand 10 after
2801 return NULL; 2801 return NULL;
2802 } 2802 }
2803 2803
2804 2804
2805 void Assembler::PopulateConstantPool(ConstantPoolArray* constant_pool) { 2805 void Assembler::PopulateConstantPool(ConstantPoolArray* constant_pool) {
2806 // No out-of-line constant pool support. 2806 // No out-of-line constant pool support.
2807 UNREACHABLE(); 2807 UNREACHABLE();
2808 } 2808 }
2809 2809
2810 2810
2811 void PatchingAssembler::MovInt64(const Register& rd, int64_t imm) {
2812 Label start;
2813 bind(&start);
2814
2815 ASSERT(rd.Is64Bits());
2816 ASSERT(!rd.IsSP());
2817
2818 for (unsigned i = 0; i < (rd.SizeInBits() / 16); i++) {
2819 uint64_t imm16 = (imm >> (16 * i)) & 0xffffL;
2820 movk(rd, imm16, 16 * i);
2821 }
2822
2823 ASSERT(SizeOfCodeGeneratedSince(&start) ==
2824 kMovInt64NInstrs * kInstructionSize);
2825 }
2826
2827
2828 void PatchingAssembler::PatchAdrFar(Instruction* target) {
2829 // The code at the current instruction should be:
2830 // adr rd, 0
2831 // nop (adr_far)
2832 // nop (adr_far)
2833 // nop (adr_far)
2834 // movz scratch, 0
2835 // add rd, rd, scratch
2836
2837 // Verify the expected code.
2838 Instruction* expected_adr = InstructionAt(0);
2839 CHECK(expected_adr->IsAdr() && (expected_adr->ImmPCRel() == 0));
2840 int rd_code = expected_adr->Rd();
2841 for (int i = 0; i < kAdrFarPatchableNNops; ++i) {
2842 CHECK(InstructionAt((i + 1) * kInstructionSize)->IsNop(ADR_FAR_NOP));
2843 }
2844 Instruction* expected_movz =
2845 InstructionAt((kAdrFarPatchableNInstrs - 2) * kInstructionSize);
2846 CHECK(expected_movz->IsMovz() &&
2847 (expected_movz->ImmMoveWide() == 0) &&
2848 (expected_movz->ShiftMoveWide() == 0));
2849 int scratch_code = expected_movz->Rd();
2850 Instruction* expected_add =
2851 InstructionAt((kAdrFarPatchableNInstrs - 1) * kInstructionSize);
2852 CHECK(expected_add->IsAddSubShifted() &&
2853 (expected_add->Mask(AddSubOpMask) == ADD) &&
2854 expected_add->SixtyFourBits() &&
2855 (expected_add->Rd() == rd_code) && (expected_add->Rn() == rd_code) &&
2856 (expected_add->Rm() == scratch_code) &&
2857 (static_cast<Shift>(expected_add->ShiftDP()) == LSL) &&
2858 (expected_add->ImmDPShift() == 0));
2859
2860 // Patch to load the correct address.
2861 Label start;
2862 bind(&start);
2863 Register rd = Register::XRegFromCode(rd_code);
2864 // If the target is in range, we only patch the adr. Otherwise we patch the
2865 // nops with fixup instructions.
2866 int target_offset = expected_adr->DistanceTo(target);
2867 if (Instruction::IsValidPCRelOffset(target_offset)) {
2868 adr(rd, target_offset);
2869 for (int i = 0; i < kAdrFarPatchableNInstrs - 2; ++i) {
2870 nop(ADR_FAR_NOP);
2871 }
2872 } else {
2873 Register scratch = Register::XRegFromCode(scratch_code);
2874 adr(rd, 0);
2875 MovInt64(scratch, target_offset);
2876 add(rd, rd, scratch);
2877 }
2878 }
2879
2880
2811 } } // namespace v8::internal 2881 } } // namespace v8::internal
2812 2882
2813 #endif // V8_TARGET_ARCH_ARM64 2883 #endif // V8_TARGET_ARCH_ARM64
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698