OLD | NEW |
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" // Needed here to get TARGET_ARCH_MIPS. | 5 #include "vm/globals.h" // Needed here to get TARGET_ARCH_MIPS. |
6 #if defined(TARGET_ARCH_MIPS) | 6 #if defined(TARGET_ARCH_MIPS) |
7 | 7 |
8 #include "vm/constants_mips.h" | 8 #include "vm/constants_mips.h" |
9 #include "vm/cpu.h" | 9 #include "vm/cpu.h" |
10 #include "vm/instructions.h" | 10 #include "vm/instructions.h" |
11 #include "vm/object.h" | 11 #include "vm/object.h" |
12 | 12 |
13 namespace dart { | 13 namespace dart { |
14 | 14 |
15 CallPattern::CallPattern(uword pc, const Code& code) | 15 CallPattern::CallPattern(uword pc, const Code& code) |
16 : object_pool_(ObjectPool::Handle(code.GetObjectPool())), | 16 : object_pool_(ObjectPool::Handle(code.GetObjectPool())), |
17 end_(pc), | 17 end_(pc), |
18 args_desc_load_end_(0), | |
19 ic_data_load_end_(0), | 18 ic_data_load_end_(0), |
20 target_address_pool_index_(-1), | 19 target_address_pool_index_(-1), |
21 args_desc_(Array::Handle()), | |
22 ic_data_(ICData::Handle()) { | 20 ic_data_(ICData::Handle()) { |
23 ASSERT(code.ContainsInstructionAt(pc)); | 21 ASSERT(code.ContainsInstructionAt(pc)); |
24 // Last instruction: jalr RA, T9(=R25). | 22 // Last instruction: jalr RA, T9(=R25). |
25 ASSERT(*(reinterpret_cast<uword*>(end_) - 2) == 0x0320f809); | 23 ASSERT(*(reinterpret_cast<uword*>(end_) - 2) == 0x0320f809); |
26 Register reg; | 24 Register reg; |
27 // The end of the pattern is the instruction after the delay slot of the jalr. | 25 // The end of the pattern is the instruction after the delay slot of the jalr. |
28 ic_data_load_end_ = | 26 ic_data_load_end_ = |
29 InstructionPattern::DecodeLoadWordFromPool(end_ - (2 * Instr::kInstrSize), | 27 InstructionPattern::DecodeLoadWordFromPool(end_ - (2 * Instr::kInstrSize), |
30 ®, | 28 ®, |
31 &target_address_pool_index_); | 29 &target_address_pool_index_); |
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
119 offset += (instr->UImmField() << 16); | 117 offset += (instr->UImmField() << 16); |
120 } | 118 } |
121 *index = ObjectPool::IndexFromOffset(offset); | 119 *index = ObjectPool::IndexFromOffset(offset); |
122 return start; | 120 return start; |
123 } | 121 } |
124 | 122 |
125 | 123 |
126 RawICData* CallPattern::IcData() { | 124 RawICData* CallPattern::IcData() { |
127 if (ic_data_.IsNull()) { | 125 if (ic_data_.IsNull()) { |
128 Register reg; | 126 Register reg; |
129 args_desc_load_end_ = | 127 InstructionPattern::DecodeLoadObject(ic_data_load_end_, |
130 InstructionPattern::DecodeLoadObject(ic_data_load_end_, | 128 object_pool_, |
131 object_pool_, | 129 ®, |
132 ®, | 130 &ic_data_); |
133 &ic_data_); | |
134 ASSERT(reg == S5); | 131 ASSERT(reg == S5); |
135 } | 132 } |
136 return ic_data_.raw(); | 133 return ic_data_.raw(); |
137 } | 134 } |
138 | 135 |
139 | 136 |
140 RawArray* CallPattern::ClosureArgumentsDescriptor() { | |
141 if (args_desc_.IsNull()) { | |
142 IcData(); // Loading of the ic_data must be decoded first, if not already. | |
143 Register reg; | |
144 InstructionPattern::DecodeLoadObject(args_desc_load_end_, | |
145 object_pool_, | |
146 ®, | |
147 &args_desc_); | |
148 ASSERT(reg == S4); | |
149 } | |
150 return args_desc_.raw(); | |
151 } | |
152 | |
153 | |
154 uword CallPattern::TargetAddress() const { | 137 uword CallPattern::TargetAddress() const { |
155 return object_pool_.RawValueAt(target_address_pool_index_); | 138 return object_pool_.RawValueAt(target_address_pool_index_); |
156 } | 139 } |
157 | 140 |
158 | 141 |
159 void CallPattern::SetTargetAddress(uword target_address) const { | 142 void CallPattern::SetTargetAddress(uword target_address) const { |
160 object_pool_.SetRawValueAt(target_address_pool_index_, target_address); | 143 object_pool_.SetRawValueAt(target_address_pool_index_, target_address); |
161 // No need to flush the instruction cache, since the code is not modified. | 144 // No need to flush the instruction cache, since the code is not modified. |
162 } | 145 } |
163 | 146 |
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
226 bool ReturnPattern::IsValid() const { | 209 bool ReturnPattern::IsValid() const { |
227 Instr* jr = Instr::At(pc_); | 210 Instr* jr = Instr::At(pc_); |
228 return (jr->OpcodeField() == SPECIAL) && | 211 return (jr->OpcodeField() == SPECIAL) && |
229 (jr->FunctionField() == JR) && | 212 (jr->FunctionField() == JR) && |
230 (jr->RsField() == RA); | 213 (jr->RsField() == RA); |
231 } | 214 } |
232 | 215 |
233 } // namespace dart | 216 } // namespace dart |
234 | 217 |
235 #endif // defined TARGET_ARCH_MIPS | 218 #endif // defined TARGET_ARCH_MIPS |
OLD | NEW |