Index: runtime/vm/instructions_x64.cc |
=================================================================== |
--- runtime/vm/instructions_x64.cc (revision 26726) |
+++ runtime/vm/instructions_x64.cc (working copy) |
@@ -11,6 +11,21 @@ |
namespace dart { |
+int InstructionPattern::IndexFromPPLoad(uword start) { |
+ uint8_t which = *reinterpret_cast<uint8_t*>(start); |
+ if ((which & 0xF0) == 0x90) { |
+ int32_t offset = *reinterpret_cast<int32_t*>(start + 1); |
+ offset += kHeapObjectTag; |
+ return (offset - Array::data_offset())/kWordSize; |
+ } else { |
+ ASSERT((which & 0xF0) == 0x50); |
+ int32_t offset = *reinterpret_cast<int8_t*>(start + 1); |
+ offset += kHeapObjectTag; |
+ return (offset - Array::data_offset())/kWordSize; |
+ } |
+} |
+ |
+ |
bool InstructionPattern::TestBytesWith(const int* data, int num_bytes) const { |
ASSERT(data != NULL); |
const uint8_t* byte_array = reinterpret_cast<const uint8_t*>(start_); |
@@ -24,13 +39,13 @@ |
} |
-uword CallOrJumpPattern::TargetAddress() const { |
+uword CallPattern::TargetAddress() const { |
ASSERT(IsValid()); |
return *reinterpret_cast<uword*>(start() + 2); |
} |
-void CallOrJumpPattern::SetTargetAddress(uword target) const { |
+void CallPattern::SetTargetAddress(uword target) const { |
ASSERT(IsValid()); |
*reinterpret_cast<uword*>(start() + 2) = target; |
CPU::FlushICache(start() + 2, kWordSize); |
@@ -46,11 +61,30 @@ |
} |
+uword JumpPattern::TargetAddress() const { |
+ ASSERT(IsValid()); |
+ int index = InstructionPattern::IndexFromPPLoad(start() + 2); |
+ return reinterpret_cast<uword>(object_pool_.At(index)); |
+} |
+ |
+ |
+void JumpPattern::SetTargetAddress(uword target) const { |
+ ASSERT(IsValid()); |
+ int index = InstructionPattern::IndexFromPPLoad(start() + 2); |
+ const Smi& smi = Smi::Handle(reinterpret_cast<RawSmi*>(target)); |
+ object_pool_.SetAt(index, smi); |
+ // No need to flush the instruction cache, since the code is not modified. |
+} |
+ |
+ |
const int* JumpPattern::pattern() const { |
- // movq $target, TMP |
- // jmpq TMP |
+ // 00: 4d 8b 9d imm32 mov R11, [R13 + off] |
+ // OR: |
+ // 00: 4d 8b 5d imm8 mov R11, [R13 + off] |
+ // 04: 0f 1f 00 nop |
+ // 07: 41 ff e3 jmpq R11 |
static const int kJumpPattern[kLengthInBytes] = |
- {0x49, 0xBB, -1, -1, -1, -1, -1, -1, -1, -1, 0x41, 0xFF, 0xE3}; |
+ {0x4D, 0x8B, -1, -1, -1, -1, -1, 0x41, 0xFF, 0xE3}; |
return kJumpPattern; |
} |