Index: runtime/vm/instructions_mips.cc |
diff --git a/runtime/vm/instructions_mips.cc b/runtime/vm/instructions_mips.cc |
index 34a5c3a460970d7bb805e91314a6d6fd98c195cb..8625d8a828aab972ca9250f898c11716e9f1f2fe 100644 |
--- a/runtime/vm/instructions_mips.cc |
+++ b/runtime/vm/instructions_mips.cc |
@@ -164,6 +164,51 @@ void CallPattern::SetTargetAddress(uword target_address) const { |
} |
+NativeCallPattern::NativeCallPattern(uword pc, const Code& code) |
+ : object_pool_(ObjectPool::Handle(code.GetObjectPool())), |
+ end_(pc), |
+ native_function_pool_index_(-1), |
+ target_address_pool_index_(-1) { |
+ ASSERT(code.ContainsInstructionAt(pc)); |
+ // Last instruction: jalr RA, T9(=R25). |
+ ASSERT(*(reinterpret_cast<uword*>(end_) - 2) == 0x0320f809); |
+ |
+ Register reg; |
+ uword native_function_load_end = |
+ InstructionPattern::DecodeLoadWordFromPool(end_ - 2 * Instr::kInstrSize, |
+ ®, |
+ &target_address_pool_index_); |
+ ASSERT(reg == T9); |
+ InstructionPattern::DecodeLoadWordFromPool(native_function_load_end, |
+ ®, |
+ &native_function_pool_index_); |
+ ASSERT(reg == T5); |
+} |
+ |
+ |
+uword NativeCallPattern::target() const { |
+ return object_pool_.RawValueAt(target_address_pool_index_); |
+} |
+ |
+ |
+void NativeCallPattern::set_target(uword target_address) const { |
+ object_pool_.SetRawValueAt(target_address_pool_index_, target_address); |
+ // No need to flush the instruction cache, since the code is not modified. |
+} |
+ |
+ |
+NativeFunction NativeCallPattern::native_function() const { |
+ return reinterpret_cast<NativeFunction>( |
+ object_pool_.RawValueAt(native_function_pool_index_)); |
+} |
+ |
+ |
+void NativeCallPattern::set_native_function(NativeFunction func) const { |
+ object_pool_.SetRawValueAt(native_function_pool_index_, |
+ reinterpret_cast<uword>(func)); |
+} |
+ |
+ |
void CallPattern::InsertAt(uword pc, uword target_address) { |
Instr* lui = Instr::At(pc + (0 * Instr::kInstrSize)); |
Instr* ori = Instr::At(pc + (1 * Instr::kInstrSize)); |