blob: ca03885aaba75845bd49a67b282c9ff2f11fe221 [file] [log] [blame]
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001/*
2 * Copyright (C) 2012 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#include "interpreter_common.h"
18
19namespace art {
20namespace interpreter {
21
22// In the following macros, we expect the following local variables exist:
23// - "self": the current Thread*.
24// - "inst" : the current Instruction*.
Sebastien Hertz3b588e02013-09-11 14:33:18 +020025// - "inst_data" : the current instruction's first 16 bits.
Sebastien Hertz8ece0502013-08-07 11:26:41 +020026// - "dex_pc": the current pc.
27// - "shadow_frame": the current shadow frame.
Sebastien Hertz8ece0502013-08-07 11:26:41 +020028// - "mh": the current MethodHelper.
29// - "currentHandlersTable": the current table of pointer to each instruction handler.
30
31// Advance to the next instruction and updates interpreter state.
Sebastien Hertz8ece0502013-08-07 11:26:41 +020032#define ADVANCE(_offset) \
33 do { \
34 int32_t disp = static_cast<int32_t>(_offset); \
35 inst = inst->RelativeAt(disp); \
36 dex_pc = static_cast<uint32_t>(static_cast<int32_t>(dex_pc) + disp); \
37 shadow_frame.SetDexPC(dex_pc); \
Sebastien Hertz8ece0502013-08-07 11:26:41 +020038 TraceExecution(shadow_frame, inst, dex_pc, mh); \
Sebastien Hertz3b588e02013-09-11 14:33:18 +020039 inst_data = inst->Fetch16(0); \
40 goto *currentHandlersTable[inst->Opcode(inst_data)]; \
Sebastien Hertz8ece0502013-08-07 11:26:41 +020041 } while (false)
42
43#define HANDLE_PENDING_EXCEPTION() goto exception_pending_label
44
45#define POSSIBLY_HANDLE_PENDING_EXCEPTION(_is_exception_pending, _offset) \
46 do { \
47 if (UNLIKELY(_is_exception_pending)) { \
48 HANDLE_PENDING_EXCEPTION(); \
49 } else { \
50 ADVANCE(_offset); \
51 } \
52 } while (false)
53
Sebastien Hertzee1997a2013-09-19 14:47:09 +020054#define UPDATE_HANDLER_TABLE() \
55 currentHandlersTable = handlersTable[Runtime::Current()->GetInstrumentation()->GetInterpreterHandlerTable()]
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +020056
Sebastien Hertz8ece0502013-08-07 11:26:41 +020057#define UNREACHABLE_CODE_CHECK() \
58 do { \
59 if (kIsDebugBuild) { \
60 LOG(FATAL) << "We should not be here !"; \
61 } \
62 } while (false)
63
64#define HANDLE_INSTRUCTION_START(opcode) op_##opcode: // NOLINT(whitespace/labels)
65#define HANDLE_INSTRUCTION_END() UNREACHABLE_CODE_CHECK()
66
Sebastien Hertzee1997a2013-09-19 14:47:09 +020067/**
68 * Interpreter based on computed goto tables.
69 *
70 * Each instruction is associated to a handler. This handler is responsible for executing the
71 * instruction and jump to the next instruction's handler.
72 * In order to limit the cost of instrumentation, we have two handler tables:
73 * - the "main" handler table: it contains handlers for normal execution of each instruction without
74 * handling of instrumentation.
75 * - the "alternative" handler table: it contains alternative handlers which first handle
76 * instrumentation before jumping to the corresponding "normal" instruction's handler.
77 *
78 * When instrumentation is active, the interpreter uses the "alternative" handler table. Otherwise
79 * it uses the "main" handler table.
80 *
81 * The current handler table is the handler table being used by the interpreter. It is updated:
82 * - on backward branch (goto, if and switch instructions)
83 * - after invoke
84 * - when an exception is thrown.
85 * This allows to support an attaching debugger to an already running application for instance.
86 *
87 * For a fast handler table update, handler tables are stored in an array of handler tables. Each
88 * handler table is represented by the InterpreterHandlerTable enum which allows to associate it
89 * to an index in this array of handler tables ((see Instrumentation::GetInterpreterHandlerTable).
90 *
91 * Here's the current layout of this array of handler tables:
92 *
93 * ---------------------+---------------+
94 * | NOP | (handler for NOP instruction)
95 * +---------------+
96 * "main" | MOVE | (handler for MOVE instruction)
97 * handler table +---------------+
98 * | ... |
99 * +---------------+
100 * | UNUSED_FF | (handler for UNUSED_FF instruction)
101 * ---------------------+---------------+
102 * | NOP | (alternative handler for NOP instruction)
103 * +---------------+
104 * "alternative" | MOVE | (alternative handler for MOVE instruction)
105 * handler table +---------------+
106 * | ... |
107 * +---------------+
108 * | UNUSED_FF | (alternative handler for UNUSED_FF instruction)
109 * ---------------------+---------------+
110 *
111 */
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200112template<bool do_access_check>
113JValue ExecuteGotoImpl(Thread* self, MethodHelper& mh, const DexFile::CodeItem* code_item,
114 ShadowFrame& shadow_frame, JValue result_register) {
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200115 // Define handler tables:
116 // - The main handler table contains execution handlers for each instruction.
117 // - The alternative handler table contains prelude handlers which check for thread suspend and
118 // manage instrumentation before jumping to the execution handler.
119 static const void* const handlersTable[instrumentation::kNumHandlerTables][kNumPackedOpcodes] = {
120 {
121 // Main handler table.
122#define INSTRUCTION_HANDLER(o, code, n, f, r, i, a, v) &&op_##code,
123#include "dex_instruction_list.h"
124 DEX_INSTRUCTION_LIST(INSTRUCTION_HANDLER)
125#undef DEX_INSTRUCTION_LIST
126#undef INSTRUCTION_HANDLER
127 }, {
128 // Alternative handler table.
129#define INSTRUCTION_HANDLER(o, code, n, f, r, i, a, v) &&alt_op_##code,
130#include "dex_instruction_list.h"
131 DEX_INSTRUCTION_LIST(INSTRUCTION_HANDLER)
132#undef DEX_INSTRUCTION_LIST
133#undef INSTRUCTION_HANDLER
134 }
135 };
136
137 const bool do_assignability_check = do_access_check;
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200138 if (UNLIKELY(!shadow_frame.HasReferenceArray())) {
139 LOG(FATAL) << "Invalid shadow frame for interpreter use";
140 return JValue();
141 }
142 self->VerifyStack();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200143
144 uint32_t dex_pc = shadow_frame.GetDexPC();
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200145 const Instruction* inst = Instruction::At(code_item->insns_ + dex_pc);
146 uint16_t inst_data;
147 const void* const* currentHandlersTable;
148 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200149 if (LIKELY(dex_pc == 0)) { // We are entering the method as opposed to deoptimizing..
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200150 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200151 if (UNLIKELY(instrumentation->HasMethodEntryListeners())) {
Sebastien Hertz947ff082013-09-17 14:10:13 +0200152 instrumentation->MethodEnterEvent(self, shadow_frame.GetThisObject(code_item->ins_size_),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200153 shadow_frame.GetMethod(), 0);
154 }
155 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200156
157 // Jump to first instruction.
158 ADVANCE(0);
159 UNREACHABLE_CODE_CHECK();
160
161 HANDLE_INSTRUCTION_START(NOP)
162 ADVANCE(1);
163 HANDLE_INSTRUCTION_END();
164
165 HANDLE_INSTRUCTION_START(MOVE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200166 shadow_frame.SetVReg(inst->VRegA_12x(inst_data),
167 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200168 ADVANCE(1);
169 HANDLE_INSTRUCTION_END();
170
171 HANDLE_INSTRUCTION_START(MOVE_FROM16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200172 shadow_frame.SetVReg(inst->VRegA_22x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200173 shadow_frame.GetVReg(inst->VRegB_22x()));
174 ADVANCE(2);
175 HANDLE_INSTRUCTION_END();
176
177 HANDLE_INSTRUCTION_START(MOVE_16)
178 shadow_frame.SetVReg(inst->VRegA_32x(),
179 shadow_frame.GetVReg(inst->VRegB_32x()));
180 ADVANCE(3);
181 HANDLE_INSTRUCTION_END();
182
183 HANDLE_INSTRUCTION_START(MOVE_WIDE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200184 shadow_frame.SetVRegLong(inst->VRegA_12x(inst_data),
185 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200186 ADVANCE(1);
187 HANDLE_INSTRUCTION_END();
188
189 HANDLE_INSTRUCTION_START(MOVE_WIDE_FROM16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200190 shadow_frame.SetVRegLong(inst->VRegA_22x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200191 shadow_frame.GetVRegLong(inst->VRegB_22x()));
192 ADVANCE(2);
193 HANDLE_INSTRUCTION_END();
194
195 HANDLE_INSTRUCTION_START(MOVE_WIDE_16)
196 shadow_frame.SetVRegLong(inst->VRegA_32x(),
197 shadow_frame.GetVRegLong(inst->VRegB_32x()));
198 ADVANCE(3);
199 HANDLE_INSTRUCTION_END();
200
201 HANDLE_INSTRUCTION_START(MOVE_OBJECT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200202 shadow_frame.SetVRegReference(inst->VRegA_12x(inst_data),
203 shadow_frame.GetVRegReference(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200204 ADVANCE(1);
205 HANDLE_INSTRUCTION_END();
206
207 HANDLE_INSTRUCTION_START(MOVE_OBJECT_FROM16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200208 shadow_frame.SetVRegReference(inst->VRegA_22x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200209 shadow_frame.GetVRegReference(inst->VRegB_22x()));
210 ADVANCE(2);
211 HANDLE_INSTRUCTION_END();
212
213 HANDLE_INSTRUCTION_START(MOVE_OBJECT_16)
214 shadow_frame.SetVRegReference(inst->VRegA_32x(),
215 shadow_frame.GetVRegReference(inst->VRegB_32x()));
216 ADVANCE(3);
217 HANDLE_INSTRUCTION_END();
218
219 HANDLE_INSTRUCTION_START(MOVE_RESULT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200220 shadow_frame.SetVReg(inst->VRegA_11x(inst_data), result_register.GetI());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200221 ADVANCE(1);
222 HANDLE_INSTRUCTION_END();
223
224 HANDLE_INSTRUCTION_START(MOVE_RESULT_WIDE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200225 shadow_frame.SetVRegLong(inst->VRegA_11x(inst_data), result_register.GetJ());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200226 ADVANCE(1);
227 HANDLE_INSTRUCTION_END();
228
229 HANDLE_INSTRUCTION_START(MOVE_RESULT_OBJECT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200230 shadow_frame.SetVRegReference(inst->VRegA_11x(inst_data), result_register.GetL());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200231 ADVANCE(1);
232 HANDLE_INSTRUCTION_END();
233
234 HANDLE_INSTRUCTION_START(MOVE_EXCEPTION) {
235 Throwable* exception = self->GetException(NULL);
236 self->ClearException();
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200237 shadow_frame.SetVRegReference(inst->VRegA_11x(inst_data), exception);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200238 ADVANCE(1);
239 }
240 HANDLE_INSTRUCTION_END();
241
242 HANDLE_INSTRUCTION_START(RETURN_VOID) {
243 JValue result;
Sebastien Hertz043036f2013-09-09 18:26:48 +0200244 if (do_access_check) {
245 // If access checks are required then the dex-to-dex compiler and analysis of
246 // whether the class has final fields hasn't been performed. Conservatively
247 // perform the memory barrier now.
Ian Rogersb122a4b2013-11-19 18:00:50 -0800248 QuasiAtomic::MembarStoreLoad();
Sebastien Hertz043036f2013-09-09 18:26:48 +0200249 }
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200250 if (UNLIKELY(self->TestAllFlags())) {
251 CheckSuspend(self);
252 }
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200253 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200254 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
Sebastien Hertz947ff082013-09-17 14:10:13 +0200255 instrumentation->MethodExitEvent(self, shadow_frame.GetThisObject(code_item->ins_size_),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200256 shadow_frame.GetMethod(), dex_pc,
257 result);
258 }
259 return result;
260 }
261 HANDLE_INSTRUCTION_END();
262
263 HANDLE_INSTRUCTION_START(RETURN_VOID_BARRIER) {
Ian Rogersb122a4b2013-11-19 18:00:50 -0800264 QuasiAtomic::MembarStoreLoad();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200265 JValue result;
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200266 if (UNLIKELY(self->TestAllFlags())) {
267 CheckSuspend(self);
268 }
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200269 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200270 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
Sebastien Hertz947ff082013-09-17 14:10:13 +0200271 instrumentation->MethodExitEvent(self, shadow_frame.GetThisObject(code_item->ins_size_),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200272 shadow_frame.GetMethod(), dex_pc,
273 result);
274 }
275 return result;
276 }
277 HANDLE_INSTRUCTION_END();
278
279 HANDLE_INSTRUCTION_START(RETURN) {
280 JValue result;
281 result.SetJ(0);
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200282 result.SetI(shadow_frame.GetVReg(inst->VRegA_11x(inst_data)));
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200283 if (UNLIKELY(self->TestAllFlags())) {
284 CheckSuspend(self);
285 }
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200286 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200287 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
Sebastien Hertz947ff082013-09-17 14:10:13 +0200288 instrumentation->MethodExitEvent(self, shadow_frame.GetThisObject(code_item->ins_size_),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200289 shadow_frame.GetMethod(), dex_pc,
290 result);
291 }
292 return result;
293 }
294 HANDLE_INSTRUCTION_END();
295
296 HANDLE_INSTRUCTION_START(RETURN_WIDE) {
297 JValue result;
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200298 result.SetJ(shadow_frame.GetVRegLong(inst->VRegA_11x(inst_data)));
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200299 if (UNLIKELY(self->TestAllFlags())) {
300 CheckSuspend(self);
301 }
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200302 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200303 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
Sebastien Hertz947ff082013-09-17 14:10:13 +0200304 instrumentation->MethodExitEvent(self, shadow_frame.GetThisObject(code_item->ins_size_),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200305 shadow_frame.GetMethod(), dex_pc,
306 result);
307 }
308 return result;
309 }
310 HANDLE_INSTRUCTION_END();
311
312 HANDLE_INSTRUCTION_START(RETURN_OBJECT) {
313 JValue result;
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200314 if (UNLIKELY(self->TestAllFlags())) {
315 CheckSuspend(self);
316 }
Mathieu Chartiere861ebd2013-10-09 15:01:21 -0700317 Object* obj_result = shadow_frame.GetVRegReference(inst->VRegA_11x(inst_data));
318 result.SetJ(0);
319 result.SetL(obj_result);
Jeff Haoa3faaf42013-09-03 19:07:00 -0700320 if (do_assignability_check && obj_result != NULL) {
321 Class* return_type = MethodHelper(shadow_frame.GetMethod()).GetReturnType();
322 if (return_type == NULL) {
323 // Return the pending exception.
324 HANDLE_PENDING_EXCEPTION();
325 }
326 if (!obj_result->VerifierInstanceOf(return_type)) {
327 // This should never happen.
328 self->ThrowNewExceptionF(self->GetCurrentLocationForThrow(),
329 "Ljava/lang/VirtualMachineError;",
330 "Returning '%s' that is not instance of return type '%s'",
331 ClassHelper(obj_result->GetClass()).GetDescriptor(),
332 ClassHelper(return_type).GetDescriptor());
333 HANDLE_PENDING_EXCEPTION();
334 }
335 }
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200336 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200337 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
Sebastien Hertz947ff082013-09-17 14:10:13 +0200338 instrumentation->MethodExitEvent(self, shadow_frame.GetThisObject(code_item->ins_size_),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200339 shadow_frame.GetMethod(), dex_pc,
340 result);
341 }
342 return result;
343 }
344 HANDLE_INSTRUCTION_END();
345
346 HANDLE_INSTRUCTION_START(CONST_4) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200347 uint32_t dst = inst->VRegA_11n(inst_data);
348 int32_t val = inst->VRegB_11n(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200349 shadow_frame.SetVReg(dst, val);
350 if (val == 0) {
351 shadow_frame.SetVRegReference(dst, NULL);
352 }
353 ADVANCE(1);
354 }
355 HANDLE_INSTRUCTION_END();
356
357 HANDLE_INSTRUCTION_START(CONST_16) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200358 uint32_t dst = inst->VRegA_21s(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200359 int32_t val = inst->VRegB_21s();
360 shadow_frame.SetVReg(dst, val);
361 if (val == 0) {
362 shadow_frame.SetVRegReference(dst, NULL);
363 }
364 ADVANCE(2);
365 }
366 HANDLE_INSTRUCTION_END();
367
368 HANDLE_INSTRUCTION_START(CONST) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200369 uint32_t dst = inst->VRegA_31i(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200370 int32_t val = inst->VRegB_31i();
371 shadow_frame.SetVReg(dst, val);
372 if (val == 0) {
373 shadow_frame.SetVRegReference(dst, NULL);
374 }
375 ADVANCE(3);
376 }
377 HANDLE_INSTRUCTION_END();
378
379 HANDLE_INSTRUCTION_START(CONST_HIGH16) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200380 uint32_t dst = inst->VRegA_21h(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200381 int32_t val = static_cast<int32_t>(inst->VRegB_21h() << 16);
382 shadow_frame.SetVReg(dst, val);
383 if (val == 0) {
384 shadow_frame.SetVRegReference(dst, NULL);
385 }
386 ADVANCE(2);
387 }
388 HANDLE_INSTRUCTION_END();
389
390 HANDLE_INSTRUCTION_START(CONST_WIDE_16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200391 shadow_frame.SetVRegLong(inst->VRegA_21s(inst_data), inst->VRegB_21s());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200392 ADVANCE(2);
393 HANDLE_INSTRUCTION_END();
394
395 HANDLE_INSTRUCTION_START(CONST_WIDE_32)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200396 shadow_frame.SetVRegLong(inst->VRegA_31i(inst_data), inst->VRegB_31i());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200397 ADVANCE(3);
398 HANDLE_INSTRUCTION_END();
399
400 HANDLE_INSTRUCTION_START(CONST_WIDE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200401 shadow_frame.SetVRegLong(inst->VRegA_51l(inst_data), inst->VRegB_51l());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200402 ADVANCE(5);
403 HANDLE_INSTRUCTION_END();
404
405 HANDLE_INSTRUCTION_START(CONST_WIDE_HIGH16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200406 shadow_frame.SetVRegLong(inst->VRegA_21h(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200407 static_cast<uint64_t>(inst->VRegB_21h()) << 48);
408 ADVANCE(2);
409 HANDLE_INSTRUCTION_END();
410
411 HANDLE_INSTRUCTION_START(CONST_STRING) {
412 String* s = ResolveString(self, mh, inst->VRegB_21c());
413 if (UNLIKELY(s == NULL)) {
414 HANDLE_PENDING_EXCEPTION();
415 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200416 shadow_frame.SetVRegReference(inst->VRegA_21c(inst_data), s);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200417 ADVANCE(2);
418 }
419 }
420 HANDLE_INSTRUCTION_END();
421
422 HANDLE_INSTRUCTION_START(CONST_STRING_JUMBO) {
423 String* s = ResolveString(self, mh, inst->VRegB_31c());
424 if (UNLIKELY(s == NULL)) {
425 HANDLE_PENDING_EXCEPTION();
426 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200427 shadow_frame.SetVRegReference(inst->VRegA_31c(inst_data), s);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200428 ADVANCE(3);
429 }
430 }
431 HANDLE_INSTRUCTION_END();
432
433 HANDLE_INSTRUCTION_START(CONST_CLASS) {
434 Class* c = ResolveVerifyAndClinit(inst->VRegB_21c(), shadow_frame.GetMethod(),
435 self, false, do_access_check);
436 if (UNLIKELY(c == NULL)) {
437 HANDLE_PENDING_EXCEPTION();
438 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200439 shadow_frame.SetVRegReference(inst->VRegA_21c(inst_data), c);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200440 ADVANCE(2);
441 }
442 }
443 HANDLE_INSTRUCTION_END();
444
445 HANDLE_INSTRUCTION_START(MONITOR_ENTER) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200446 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_11x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200447 if (UNLIKELY(obj == NULL)) {
448 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
449 HANDLE_PENDING_EXCEPTION();
450 } else {
451 DoMonitorEnter(self, obj);
452 POSSIBLY_HANDLE_PENDING_EXCEPTION(self->IsExceptionPending(), 1);
453 }
454 }
455 HANDLE_INSTRUCTION_END();
456
457 HANDLE_INSTRUCTION_START(MONITOR_EXIT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200458 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_11x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200459 if (UNLIKELY(obj == NULL)) {
460 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
461 HANDLE_PENDING_EXCEPTION();
462 } else {
463 DoMonitorExit(self, obj);
464 POSSIBLY_HANDLE_PENDING_EXCEPTION(self->IsExceptionPending(), 1);
465 }
466 }
467 HANDLE_INSTRUCTION_END();
468
469 HANDLE_INSTRUCTION_START(CHECK_CAST) {
470 Class* c = ResolveVerifyAndClinit(inst->VRegB_21c(), shadow_frame.GetMethod(),
471 self, false, do_access_check);
472 if (UNLIKELY(c == NULL)) {
473 HANDLE_PENDING_EXCEPTION();
474 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200475 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_21c(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200476 if (UNLIKELY(obj != NULL && !obj->InstanceOf(c))) {
477 ThrowClassCastException(c, obj->GetClass());
478 HANDLE_PENDING_EXCEPTION();
479 } else {
480 ADVANCE(2);
481 }
482 }
483 }
484 HANDLE_INSTRUCTION_END();
485
486 HANDLE_INSTRUCTION_START(INSTANCE_OF) {
487 Class* c = ResolveVerifyAndClinit(inst->VRegC_22c(), shadow_frame.GetMethod(),
488 self, false, do_access_check);
489 if (UNLIKELY(c == NULL)) {
490 HANDLE_PENDING_EXCEPTION();
491 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200492 Object* obj = shadow_frame.GetVRegReference(inst->VRegB_22c(inst_data));
493 shadow_frame.SetVReg(inst->VRegA_22c(inst_data), (obj != NULL && obj->InstanceOf(c)) ? 1 : 0);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200494 ADVANCE(2);
495 }
496 }
497 HANDLE_INSTRUCTION_END();
498
499 HANDLE_INSTRUCTION_START(ARRAY_LENGTH) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200500 Object* array = shadow_frame.GetVRegReference(inst->VRegB_12x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200501 if (UNLIKELY(array == NULL)) {
502 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
503 HANDLE_PENDING_EXCEPTION();
504 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200505 shadow_frame.SetVReg(inst->VRegA_12x(inst_data), array->AsArray()->GetLength());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200506 ADVANCE(1);
507 }
508 }
509 HANDLE_INSTRUCTION_END();
510
511 HANDLE_INSTRUCTION_START(NEW_INSTANCE) {
Mathieu Chartiercbb2d202013-11-14 17:45:16 -0800512 Object* obj = AllocObjectFromCode<do_access_check, true>(
513 inst->VRegB_21c(), shadow_frame.GetMethod(), self,
514 Runtime::Current()->GetHeap()->GetCurrentAllocator());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200515 if (UNLIKELY(obj == NULL)) {
516 HANDLE_PENDING_EXCEPTION();
517 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200518 shadow_frame.SetVRegReference(inst->VRegA_21c(inst_data), obj);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200519 ADVANCE(2);
520 }
521 }
522 HANDLE_INSTRUCTION_END();
523
524 HANDLE_INSTRUCTION_START(NEW_ARRAY) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200525 int32_t length = shadow_frame.GetVReg(inst->VRegB_22c(inst_data));
Mathieu Chartiercbb2d202013-11-14 17:45:16 -0800526 Object* obj = AllocArrayFromCode<do_access_check, true>(
527 inst->VRegC_22c(), shadow_frame.GetMethod(), length, self,
528 Runtime::Current()->GetHeap()->GetCurrentAllocator());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200529 if (UNLIKELY(obj == NULL)) {
530 HANDLE_PENDING_EXCEPTION();
531 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200532 shadow_frame.SetVRegReference(inst->VRegA_22c(inst_data), obj);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200533 ADVANCE(2);
534 }
535 }
536 HANDLE_INSTRUCTION_END();
537
538 HANDLE_INSTRUCTION_START(FILLED_NEW_ARRAY) {
539 bool success = DoFilledNewArray<false, do_access_check>(inst, shadow_frame,
540 self, &result_register);
541 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
542 }
543 HANDLE_INSTRUCTION_END();
544
545 HANDLE_INSTRUCTION_START(FILLED_NEW_ARRAY_RANGE) {
546 bool success = DoFilledNewArray<true, do_access_check>(inst, shadow_frame,
547 self, &result_register);
548 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
549 }
550 HANDLE_INSTRUCTION_END();
551
552 HANDLE_INSTRUCTION_START(FILL_ARRAY_DATA) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200553 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_31t(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200554 if (UNLIKELY(obj == NULL)) {
555 ThrowNullPointerException(NULL, "null array in FILL_ARRAY_DATA");
556 HANDLE_PENDING_EXCEPTION();
557 } else {
558 Array* array = obj->AsArray();
559 DCHECK(array->IsArrayInstance() && !array->IsObjectArray());
560 const uint16_t* payload_addr = reinterpret_cast<const uint16_t*>(inst) + inst->VRegB_31t();
561 const Instruction::ArrayDataPayload* payload =
562 reinterpret_cast<const Instruction::ArrayDataPayload*>(payload_addr);
563 if (UNLIKELY(static_cast<int32_t>(payload->element_count) > array->GetLength())) {
564 self->ThrowNewExceptionF(shadow_frame.GetCurrentLocationForThrow(),
565 "Ljava/lang/ArrayIndexOutOfBoundsException;",
566 "failed FILL_ARRAY_DATA; length=%d, index=%d",
567 array->GetLength(), payload->element_count);
568 HANDLE_PENDING_EXCEPTION();
569 } else {
570 uint32_t size_in_bytes = payload->element_count * payload->element_width;
571 memcpy(array->GetRawData(payload->element_width), payload->data, size_in_bytes);
572 ADVANCE(3);
573 }
574 }
575 }
576 HANDLE_INSTRUCTION_END();
577
578 HANDLE_INSTRUCTION_START(THROW) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200579 Object* exception = shadow_frame.GetVRegReference(inst->VRegA_11x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200580 if (UNLIKELY(exception == NULL)) {
581 ThrowNullPointerException(NULL, "throw with null exception");
Jeff Haoa3faaf42013-09-03 19:07:00 -0700582 } else if (do_assignability_check && !exception->GetClass()->IsThrowableClass()) {
583 // This should never happen.
584 self->ThrowNewExceptionF(self->GetCurrentLocationForThrow(),
585 "Ljava/lang/VirtualMachineError;",
586 "Throwing '%s' that is not instance of Throwable",
587 ClassHelper(exception->GetClass()).GetDescriptor());
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200588 } else {
589 self->SetException(shadow_frame.GetCurrentLocationForThrow(), exception->AsThrowable());
590 }
591 HANDLE_PENDING_EXCEPTION();
592 }
593 HANDLE_INSTRUCTION_END();
594
595 HANDLE_INSTRUCTION_START(GOTO) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200596 int8_t offset = inst->VRegA_10t(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200597 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200598 if (UNLIKELY(self->TestAllFlags())) {
599 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200600 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200601 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200602 }
603 ADVANCE(offset);
604 }
605 HANDLE_INSTRUCTION_END();
606
607 HANDLE_INSTRUCTION_START(GOTO_16) {
608 int16_t offset = inst->VRegA_20t();
609 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200610 if (UNLIKELY(self->TestAllFlags())) {
611 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200612 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200613 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200614 }
615 ADVANCE(offset);
616 }
617 HANDLE_INSTRUCTION_END();
618
619 HANDLE_INSTRUCTION_START(GOTO_32) {
620 int32_t offset = inst->VRegA_30t();
621 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200622 if (UNLIKELY(self->TestAllFlags())) {
623 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200624 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200625 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200626 }
627 ADVANCE(offset);
628 }
629 HANDLE_INSTRUCTION_END();
630
631 HANDLE_INSTRUCTION_START(PACKED_SWITCH) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200632 int32_t offset = DoPackedSwitch(inst, shadow_frame, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200633 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200634 if (UNLIKELY(self->TestAllFlags())) {
635 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200636 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200637 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200638 }
639 ADVANCE(offset);
640 }
641 HANDLE_INSTRUCTION_END();
642
643 HANDLE_INSTRUCTION_START(SPARSE_SWITCH) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200644 int32_t offset = DoSparseSwitch(inst, shadow_frame, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200645 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200646 if (UNLIKELY(self->TestAllFlags())) {
647 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200648 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200649 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200650 }
651 ADVANCE(offset);
652 }
653 HANDLE_INSTRUCTION_END();
654
655 HANDLE_INSTRUCTION_START(CMPL_FLOAT) {
656 float val1 = shadow_frame.GetVRegFloat(inst->VRegB_23x());
657 float val2 = shadow_frame.GetVRegFloat(inst->VRegC_23x());
658 int32_t result;
659 if (val1 > val2) {
660 result = 1;
661 } else if (val1 == val2) {
662 result = 0;
663 } else {
664 result = -1;
665 }
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200666 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200667 ADVANCE(2);
668 }
669 HANDLE_INSTRUCTION_END();
670
671 HANDLE_INSTRUCTION_START(CMPG_FLOAT) {
672 float val1 = shadow_frame.GetVRegFloat(inst->VRegB_23x());
673 float val2 = shadow_frame.GetVRegFloat(inst->VRegC_23x());
674 int32_t result;
675 if (val1 < val2) {
676 result = -1;
677 } else if (val1 == val2) {
678 result = 0;
679 } else {
680 result = 1;
681 }
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200682 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200683 ADVANCE(2);
684 }
685 HANDLE_INSTRUCTION_END();
686
687 HANDLE_INSTRUCTION_START(CMPL_DOUBLE) {
688 double val1 = shadow_frame.GetVRegDouble(inst->VRegB_23x());
689 double val2 = shadow_frame.GetVRegDouble(inst->VRegC_23x());
690 int32_t result;
691 if (val1 > val2) {
692 result = 1;
693 } else if (val1 == val2) {
694 result = 0;
695 } else {
696 result = -1;
697 }
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200698 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200699 ADVANCE(2);
700 }
701 HANDLE_INSTRUCTION_END();
702
703 HANDLE_INSTRUCTION_START(CMPG_DOUBLE) {
704 double val1 = shadow_frame.GetVRegDouble(inst->VRegB_23x());
705 double val2 = shadow_frame.GetVRegDouble(inst->VRegC_23x());
706 int32_t result;
707 if (val1 < val2) {
708 result = -1;
709 } else if (val1 == val2) {
710 result = 0;
711 } else {
712 result = 1;
713 }
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200714 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200715 ADVANCE(2);
716 }
717 HANDLE_INSTRUCTION_END();
718
719 HANDLE_INSTRUCTION_START(CMP_LONG) {
720 int64_t val1 = shadow_frame.GetVRegLong(inst->VRegB_23x());
721 int64_t val2 = shadow_frame.GetVRegLong(inst->VRegC_23x());
722 int32_t result;
723 if (val1 > val2) {
724 result = 1;
725 } else if (val1 == val2) {
726 result = 0;
727 } else {
728 result = -1;
729 }
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200730 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200731 ADVANCE(2);
732 }
733 HANDLE_INSTRUCTION_END();
734
735 HANDLE_INSTRUCTION_START(IF_EQ) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200736 if (shadow_frame.GetVReg(inst->VRegA_22t(inst_data)) == shadow_frame.GetVReg(inst->VRegB_22t(inst_data))) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200737 int16_t offset = inst->VRegC_22t();
738 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200739 if (UNLIKELY(self->TestAllFlags())) {
740 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200741 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200742 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200743 }
744 ADVANCE(offset);
745 } else {
746 ADVANCE(2);
747 }
748 }
749 HANDLE_INSTRUCTION_END();
750
751 HANDLE_INSTRUCTION_START(IF_NE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200752 if (shadow_frame.GetVReg(inst->VRegA_22t(inst_data)) != shadow_frame.GetVReg(inst->VRegB_22t(inst_data))) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200753 int16_t offset = inst->VRegC_22t();
754 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200755 if (UNLIKELY(self->TestAllFlags())) {
756 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200757 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200758 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200759 }
760 ADVANCE(offset);
761 } else {
762 ADVANCE(2);
763 }
764 }
765 HANDLE_INSTRUCTION_END();
766
767 HANDLE_INSTRUCTION_START(IF_LT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200768 if (shadow_frame.GetVReg(inst->VRegA_22t(inst_data)) < shadow_frame.GetVReg(inst->VRegB_22t(inst_data))) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200769 int16_t offset = inst->VRegC_22t();
770 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200771 if (UNLIKELY(self->TestAllFlags())) {
772 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200773 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200774 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200775 }
776 ADVANCE(offset);
777 } else {
778 ADVANCE(2);
779 }
780 }
781 HANDLE_INSTRUCTION_END();
782
783 HANDLE_INSTRUCTION_START(IF_GE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200784 if (shadow_frame.GetVReg(inst->VRegA_22t(inst_data)) >= shadow_frame.GetVReg(inst->VRegB_22t(inst_data))) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200785 int16_t offset = inst->VRegC_22t();
786 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200787 if (UNLIKELY(self->TestAllFlags())) {
788 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200789 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200790 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200791 }
792 ADVANCE(offset);
793 } else {
794 ADVANCE(2);
795 }
796 }
797 HANDLE_INSTRUCTION_END();
798
799 HANDLE_INSTRUCTION_START(IF_GT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200800 if (shadow_frame.GetVReg(inst->VRegA_22t(inst_data)) > shadow_frame.GetVReg(inst->VRegB_22t(inst_data))) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200801 int16_t offset = inst->VRegC_22t();
802 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200803 if (UNLIKELY(self->TestAllFlags())) {
804 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200805 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200806 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200807 }
808 ADVANCE(offset);
809 } else {
810 ADVANCE(2);
811 }
812 }
813 HANDLE_INSTRUCTION_END();
814
815 HANDLE_INSTRUCTION_START(IF_LE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200816 if (shadow_frame.GetVReg(inst->VRegA_22t(inst_data)) <= shadow_frame.GetVReg(inst->VRegB_22t(inst_data))) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200817 int16_t offset = inst->VRegC_22t();
818 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200819 if (UNLIKELY(self->TestAllFlags())) {
820 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200821 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200822 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200823 }
824 ADVANCE(offset);
825 } else {
826 ADVANCE(2);
827 }
828 }
829 HANDLE_INSTRUCTION_END();
830
831 HANDLE_INSTRUCTION_START(IF_EQZ) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200832 if (shadow_frame.GetVReg(inst->VRegA_21t(inst_data)) == 0) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200833 int16_t offset = inst->VRegB_21t();
834 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200835 if (UNLIKELY(self->TestAllFlags())) {
836 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200837 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200838 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200839 }
840 ADVANCE(offset);
841 } else {
842 ADVANCE(2);
843 }
844 }
845 HANDLE_INSTRUCTION_END();
846
847 HANDLE_INSTRUCTION_START(IF_NEZ) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200848 if (shadow_frame.GetVReg(inst->VRegA_21t(inst_data)) != 0) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200849 int16_t offset = inst->VRegB_21t();
850 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200851 if (UNLIKELY(self->TestAllFlags())) {
852 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200853 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200854 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200855 }
856 ADVANCE(offset);
857 } else {
858 ADVANCE(2);
859 }
860 }
861 HANDLE_INSTRUCTION_END();
862
863 HANDLE_INSTRUCTION_START(IF_LTZ) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200864 if (shadow_frame.GetVReg(inst->VRegA_21t(inst_data)) < 0) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200865 int16_t offset = inst->VRegB_21t();
866 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200867 if (UNLIKELY(self->TestAllFlags())) {
868 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200869 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200870 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200871 }
872 ADVANCE(offset);
873 } else {
874 ADVANCE(2);
875 }
876 }
877 HANDLE_INSTRUCTION_END();
878
879 HANDLE_INSTRUCTION_START(IF_GEZ) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200880 if (shadow_frame.GetVReg(inst->VRegA_21t(inst_data)) >= 0) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200881 int16_t offset = inst->VRegB_21t();
882 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200883 if (UNLIKELY(self->TestAllFlags())) {
884 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200885 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200886 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200887 }
888 ADVANCE(offset);
889 } else {
890 ADVANCE(2);
891 }
892 }
893 HANDLE_INSTRUCTION_END();
894
895 HANDLE_INSTRUCTION_START(IF_GTZ) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200896 if (shadow_frame.GetVReg(inst->VRegA_21t(inst_data)) > 0) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200897 int16_t offset = inst->VRegB_21t();
898 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200899 if (UNLIKELY(self->TestAllFlags())) {
900 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200901 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200902 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200903 }
904 ADVANCE(offset);
905 } else {
906 ADVANCE(2);
907 }
908 }
909 HANDLE_INSTRUCTION_END();
910
911 HANDLE_INSTRUCTION_START(IF_LEZ) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +0200912 if (shadow_frame.GetVReg(inst->VRegA_21t(inst_data)) <= 0) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200913 int16_t offset = inst->VRegB_21t();
914 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200915 if (UNLIKELY(self->TestAllFlags())) {
916 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +0200917 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200918 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200919 }
920 ADVANCE(offset);
921 } else {
922 ADVANCE(2);
923 }
924 }
925 HANDLE_INSTRUCTION_END();
926
927 HANDLE_INSTRUCTION_START(AGET_BOOLEAN) {
928 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
929 if (UNLIKELY(a == NULL)) {
930 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
931 HANDLE_PENDING_EXCEPTION();
932 } else {
933 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
934 BooleanArray* array = a->AsBooleanArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +0100935 if (LIKELY(array->CheckIsValidIndex(index))) {
936 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), array->GetWithoutChecks(index));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200937 ADVANCE(2);
938 } else {
939 HANDLE_PENDING_EXCEPTION();
940 }
941 }
942 }
943 HANDLE_INSTRUCTION_END();
944
945 HANDLE_INSTRUCTION_START(AGET_BYTE) {
946 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
947 if (UNLIKELY(a == NULL)) {
948 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
949 HANDLE_PENDING_EXCEPTION();
950 } else {
951 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
952 ByteArray* array = a->AsByteArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +0100953 if (LIKELY(array->CheckIsValidIndex(index))) {
954 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), array->GetWithoutChecks(index));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200955 ADVANCE(2);
956 } else {
957 HANDLE_PENDING_EXCEPTION();
958 }
959 }
960 }
961 HANDLE_INSTRUCTION_END();
962
963 HANDLE_INSTRUCTION_START(AGET_CHAR) {
964 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
965 if (UNLIKELY(a == NULL)) {
966 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
967 HANDLE_PENDING_EXCEPTION();
968 } else {
969 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
970 CharArray* array = a->AsCharArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +0100971 if (LIKELY(array->CheckIsValidIndex(index))) {
972 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), array->GetWithoutChecks(index));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200973 ADVANCE(2);
974 } else {
975 HANDLE_PENDING_EXCEPTION();
976 }
977 }
978 }
979 HANDLE_INSTRUCTION_END();
980
981 HANDLE_INSTRUCTION_START(AGET_SHORT) {
982 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
983 if (UNLIKELY(a == NULL)) {
984 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
985 HANDLE_PENDING_EXCEPTION();
986 } else {
987 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
988 ShortArray* array = a->AsShortArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +0100989 if (LIKELY(array->CheckIsValidIndex(index))) {
990 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), array->GetWithoutChecks(index));
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200991 ADVANCE(2);
992 } else {
993 HANDLE_PENDING_EXCEPTION();
994 }
995 }
996 }
997 HANDLE_INSTRUCTION_END();
998
999 HANDLE_INSTRUCTION_START(AGET) {
1000 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1001 if (UNLIKELY(a == NULL)) {
1002 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1003 HANDLE_PENDING_EXCEPTION();
1004 } else {
1005 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1006 IntArray* array = a->AsIntArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001007 if (LIKELY(array->CheckIsValidIndex(index))) {
1008 shadow_frame.SetVReg(inst->VRegA_23x(inst_data), array->GetWithoutChecks(index));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001009 ADVANCE(2);
1010 } else {
1011 HANDLE_PENDING_EXCEPTION();
1012 }
1013 }
1014 }
1015 HANDLE_INSTRUCTION_END();
1016
1017 HANDLE_INSTRUCTION_START(AGET_WIDE) {
1018 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1019 if (UNLIKELY(a == NULL)) {
1020 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1021 HANDLE_PENDING_EXCEPTION();
1022 } else {
1023 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1024 LongArray* array = a->AsLongArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001025 if (LIKELY(array->CheckIsValidIndex(index))) {
1026 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data), array->GetWithoutChecks(index));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001027 ADVANCE(2);
1028 } else {
1029 HANDLE_PENDING_EXCEPTION();
1030 }
1031 }
1032 }
1033 HANDLE_INSTRUCTION_END();
1034
1035 HANDLE_INSTRUCTION_START(AGET_OBJECT) {
1036 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1037 if (UNLIKELY(a == NULL)) {
1038 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1039 HANDLE_PENDING_EXCEPTION();
1040 } else {
1041 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1042 ObjectArray<Object>* array = a->AsObjectArray<Object>();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001043 if (LIKELY(array->CheckIsValidIndex(index))) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001044 shadow_frame.SetVRegReference(inst->VRegA_23x(inst_data), array->GetWithoutChecks(index));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001045 ADVANCE(2);
1046 } else {
1047 HANDLE_PENDING_EXCEPTION();
1048 }
1049 }
1050 }
1051 HANDLE_INSTRUCTION_END();
1052
1053 HANDLE_INSTRUCTION_START(APUT_BOOLEAN) {
1054 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1055 if (UNLIKELY(a == NULL)) {
1056 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1057 HANDLE_PENDING_EXCEPTION();
1058 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001059 uint8_t val = shadow_frame.GetVReg(inst->VRegA_23x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001060 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1061 BooleanArray* array = a->AsBooleanArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001062 if (LIKELY(array->CheckIsValidIndex(index))) {
1063 array->SetWithoutChecks(index, val);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001064 ADVANCE(2);
1065 } else {
1066 HANDLE_PENDING_EXCEPTION();
1067 }
1068 }
1069 }
1070 HANDLE_INSTRUCTION_END();
1071
1072 HANDLE_INSTRUCTION_START(APUT_BYTE) {
1073 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1074 if (UNLIKELY(a == NULL)) {
1075 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1076 HANDLE_PENDING_EXCEPTION();
1077 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001078 int8_t val = shadow_frame.GetVReg(inst->VRegA_23x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001079 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1080 ByteArray* array = a->AsByteArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001081 if (LIKELY(array->CheckIsValidIndex(index))) {
1082 array->SetWithoutChecks(index, val);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001083 ADVANCE(2);
1084 } else {
1085 HANDLE_PENDING_EXCEPTION();
1086 }
1087 }
1088 }
1089 HANDLE_INSTRUCTION_END();
1090
1091 HANDLE_INSTRUCTION_START(APUT_CHAR) {
1092 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1093 if (UNLIKELY(a == NULL)) {
1094 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1095 HANDLE_PENDING_EXCEPTION();
1096 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001097 uint16_t val = shadow_frame.GetVReg(inst->VRegA_23x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001098 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1099 CharArray* array = a->AsCharArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001100 if (LIKELY(array->CheckIsValidIndex(index))) {
1101 array->SetWithoutChecks(index, val);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001102 ADVANCE(2);
1103 } else {
1104 HANDLE_PENDING_EXCEPTION();
1105 }
1106 }
1107 }
1108 HANDLE_INSTRUCTION_END();
1109
1110 HANDLE_INSTRUCTION_START(APUT_SHORT) {
1111 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1112 if (UNLIKELY(a == NULL)) {
1113 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1114 HANDLE_PENDING_EXCEPTION();
1115 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001116 int16_t val = shadow_frame.GetVReg(inst->VRegA_23x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001117 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1118 ShortArray* array = a->AsShortArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001119 if (LIKELY(array->CheckIsValidIndex(index))) {
1120 array->SetWithoutChecks(index, val);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001121 ADVANCE(2);
1122 } else {
1123 HANDLE_PENDING_EXCEPTION();
1124 }
1125 }
1126 }
1127 HANDLE_INSTRUCTION_END();
1128
1129 HANDLE_INSTRUCTION_START(APUT) {
1130 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1131 if (UNLIKELY(a == NULL)) {
1132 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1133 HANDLE_PENDING_EXCEPTION();
1134 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001135 int32_t val = shadow_frame.GetVReg(inst->VRegA_23x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001136 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1137 IntArray* array = a->AsIntArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001138 if (LIKELY(array->CheckIsValidIndex(index))) {
1139 array->SetWithoutChecks(index, val);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001140 ADVANCE(2);
1141 } else {
1142 HANDLE_PENDING_EXCEPTION();
1143 }
1144 }
1145 }
1146 HANDLE_INSTRUCTION_END();
1147
1148 HANDLE_INSTRUCTION_START(APUT_WIDE) {
1149 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1150 if (UNLIKELY(a == NULL)) {
1151 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1152 HANDLE_PENDING_EXCEPTION();
1153 } else {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001154 int64_t val = shadow_frame.GetVRegLong(inst->VRegA_23x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001155 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1156 LongArray* array = a->AsLongArray();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001157 if (LIKELY(array->CheckIsValidIndex(index))) {
1158 array->SetWithoutChecks(index, val);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001159 ADVANCE(2);
1160 } else {
1161 HANDLE_PENDING_EXCEPTION();
1162 }
1163 }
1164 }
1165 HANDLE_INSTRUCTION_END();
1166
1167 HANDLE_INSTRUCTION_START(APUT_OBJECT) {
1168 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1169 if (UNLIKELY(a == NULL)) {
1170 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1171 HANDLE_PENDING_EXCEPTION();
1172 } else {
1173 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001174 Object* val = shadow_frame.GetVRegReference(inst->VRegA_23x(inst_data));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001175 ObjectArray<Object>* array = a->AsObjectArray<Object>();
Sebastien Hertzabff6432014-01-27 18:01:39 +01001176 if (LIKELY(array->CheckIsValidIndex(index) && array->CheckAssignable(val))) {
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001177 array->SetWithoutChecks(index, val);
1178 ADVANCE(2);
1179 } else {
1180 HANDLE_PENDING_EXCEPTION();
1181 }
1182 }
1183 }
1184 HANDLE_INSTRUCTION_END();
1185
1186 HANDLE_INSTRUCTION_START(IGET_BOOLEAN) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001187 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001188 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1189 }
1190 HANDLE_INSTRUCTION_END();
1191
1192 HANDLE_INSTRUCTION_START(IGET_BYTE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001193 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001194 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1195 }
1196 HANDLE_INSTRUCTION_END();
1197
1198 HANDLE_INSTRUCTION_START(IGET_CHAR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001199 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001200 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1201 }
1202 HANDLE_INSTRUCTION_END();
1203
1204 HANDLE_INSTRUCTION_START(IGET_SHORT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001205 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001206 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1207 }
1208 HANDLE_INSTRUCTION_END();
1209
1210 HANDLE_INSTRUCTION_START(IGET) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001211 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001212 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1213 }
1214 HANDLE_INSTRUCTION_END();
1215
1216 HANDLE_INSTRUCTION_START(IGET_WIDE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001217 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001218 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1219 }
1220 HANDLE_INSTRUCTION_END();
1221
1222 HANDLE_INSTRUCTION_START(IGET_OBJECT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001223 bool success = DoFieldGet<InstanceObjectRead, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001224 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1225 }
1226 HANDLE_INSTRUCTION_END();
1227
1228 HANDLE_INSTRUCTION_START(IGET_QUICK) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001229 bool success = DoIGetQuick<Primitive::kPrimInt>(shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001230 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1231 }
1232 HANDLE_INSTRUCTION_END();
1233
1234 HANDLE_INSTRUCTION_START(IGET_WIDE_QUICK) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001235 bool success = DoIGetQuick<Primitive::kPrimLong>(shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001236 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1237 }
1238 HANDLE_INSTRUCTION_END();
1239
1240 HANDLE_INSTRUCTION_START(IGET_OBJECT_QUICK) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001241 bool success = DoIGetQuick<Primitive::kPrimNot>(shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001242 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1243 }
1244 HANDLE_INSTRUCTION_END();
1245
1246 HANDLE_INSTRUCTION_START(SGET_BOOLEAN) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001247 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001248 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1249 }
1250 HANDLE_INSTRUCTION_END();
1251
1252 HANDLE_INSTRUCTION_START(SGET_BYTE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001253 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001254 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1255 }
1256 HANDLE_INSTRUCTION_END();
1257
1258 HANDLE_INSTRUCTION_START(SGET_CHAR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001259 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001260 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1261 }
1262 HANDLE_INSTRUCTION_END();
1263
1264 HANDLE_INSTRUCTION_START(SGET_SHORT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001265 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001266 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1267 }
1268 HANDLE_INSTRUCTION_END();
1269
1270 HANDLE_INSTRUCTION_START(SGET) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001271 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001272 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1273 }
1274 HANDLE_INSTRUCTION_END();
1275
1276 HANDLE_INSTRUCTION_START(SGET_WIDE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001277 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001278 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1279 }
1280 HANDLE_INSTRUCTION_END();
1281
1282 HANDLE_INSTRUCTION_START(SGET_OBJECT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001283 bool success = DoFieldGet<StaticObjectRead, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001284 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1285 }
1286 HANDLE_INSTRUCTION_END();
1287
1288 HANDLE_INSTRUCTION_START(IPUT_BOOLEAN) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001289 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001290 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1291 }
1292 HANDLE_INSTRUCTION_END();
1293
1294 HANDLE_INSTRUCTION_START(IPUT_BYTE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001295 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001296 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1297 }
1298 HANDLE_INSTRUCTION_END();
1299
1300 HANDLE_INSTRUCTION_START(IPUT_CHAR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001301 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001302 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1303 }
1304 HANDLE_INSTRUCTION_END();
1305
1306 HANDLE_INSTRUCTION_START(IPUT_SHORT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001307 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001308 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1309 }
1310 HANDLE_INSTRUCTION_END();
1311
1312 HANDLE_INSTRUCTION_START(IPUT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001313 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001314 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1315 }
1316 HANDLE_INSTRUCTION_END();
1317
1318 HANDLE_INSTRUCTION_START(IPUT_WIDE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001319 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001320 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1321 }
1322 HANDLE_INSTRUCTION_END();
1323
1324 HANDLE_INSTRUCTION_START(IPUT_OBJECT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001325 bool success = DoFieldPut<InstanceObjectWrite, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001326 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1327 }
1328 HANDLE_INSTRUCTION_END();
1329
1330 HANDLE_INSTRUCTION_START(IPUT_QUICK) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001331 bool success = DoIPutQuick<Primitive::kPrimInt>(shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001332 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1333 }
1334 HANDLE_INSTRUCTION_END();
1335
1336 HANDLE_INSTRUCTION_START(IPUT_WIDE_QUICK) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001337 bool success = DoIPutQuick<Primitive::kPrimLong>(shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001338 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1339 }
1340 HANDLE_INSTRUCTION_END();
1341
1342 HANDLE_INSTRUCTION_START(IPUT_OBJECT_QUICK) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001343 bool success = DoIPutQuick<Primitive::kPrimNot>(shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001344 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1345 }
1346 HANDLE_INSTRUCTION_END();
1347
1348 HANDLE_INSTRUCTION_START(SPUT_BOOLEAN) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001349 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001350 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1351 }
1352 HANDLE_INSTRUCTION_END();
1353
1354 HANDLE_INSTRUCTION_START(SPUT_BYTE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001355 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001356 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1357 }
1358 HANDLE_INSTRUCTION_END();
1359
1360 HANDLE_INSTRUCTION_START(SPUT_CHAR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001361 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001362 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1363 }
1364 HANDLE_INSTRUCTION_END();
1365
1366 HANDLE_INSTRUCTION_START(SPUT_SHORT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001367 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001368 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1369 }
1370 HANDLE_INSTRUCTION_END();
1371
1372 HANDLE_INSTRUCTION_START(SPUT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001373 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001374 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1375 }
1376 HANDLE_INSTRUCTION_END();
1377
1378 HANDLE_INSTRUCTION_START(SPUT_WIDE) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001379 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001380 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1381 }
1382 HANDLE_INSTRUCTION_END();
1383
1384 HANDLE_INSTRUCTION_START(SPUT_OBJECT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001385 bool success = DoFieldPut<StaticObjectWrite, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst, inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001386 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1387 }
1388 HANDLE_INSTRUCTION_END();
1389
1390 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001391 bool success = DoInvoke<kVirtual, false, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001392 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001393 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1394 }
1395 HANDLE_INSTRUCTION_END();
1396
1397 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL_RANGE) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001398 bool success = DoInvoke<kVirtual, true, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001399 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001400 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1401 }
1402 HANDLE_INSTRUCTION_END();
1403
1404 HANDLE_INSTRUCTION_START(INVOKE_SUPER) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001405 bool success = DoInvoke<kSuper, false, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001406 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001407 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1408 }
1409 HANDLE_INSTRUCTION_END();
1410
1411 HANDLE_INSTRUCTION_START(INVOKE_SUPER_RANGE) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001412 bool success = DoInvoke<kSuper, true, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001413 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001414 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1415 }
1416 HANDLE_INSTRUCTION_END();
1417
1418 HANDLE_INSTRUCTION_START(INVOKE_DIRECT) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001419 bool success = DoInvoke<kDirect, false, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001420 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001421 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1422 }
1423 HANDLE_INSTRUCTION_END();
1424
1425 HANDLE_INSTRUCTION_START(INVOKE_DIRECT_RANGE) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001426 bool success = DoInvoke<kDirect, true, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001427 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001428 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1429 }
1430 HANDLE_INSTRUCTION_END();
1431
1432 HANDLE_INSTRUCTION_START(INVOKE_INTERFACE) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001433 bool success = DoInvoke<kInterface, false, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001434 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001435 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1436 }
1437 HANDLE_INSTRUCTION_END();
1438
1439 HANDLE_INSTRUCTION_START(INVOKE_INTERFACE_RANGE) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001440 bool success = DoInvoke<kInterface, true, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001441 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001442 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1443 }
1444 HANDLE_INSTRUCTION_END();
1445
1446 HANDLE_INSTRUCTION_START(INVOKE_STATIC) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001447 bool success = DoInvoke<kStatic, false, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001448 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001449 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1450 }
1451 HANDLE_INSTRUCTION_END();
1452
1453 HANDLE_INSTRUCTION_START(INVOKE_STATIC_RANGE) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001454 bool success = DoInvoke<kStatic, true, do_access_check>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001455 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001456 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1457 }
1458 HANDLE_INSTRUCTION_END();
1459
1460 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL_QUICK) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001461 bool success = DoInvokeVirtualQuick<false>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001462 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001463 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1464 }
1465 HANDLE_INSTRUCTION_END();
1466
1467 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL_RANGE_QUICK) {
Sebastien Hertzc61124b2013-09-10 11:44:19 +02001468 bool success = DoInvokeVirtualQuick<true>(self, shadow_frame, inst, inst_data, &result_register);
Sebastien Hertzcdf2d4c2013-09-13 14:57:51 +02001469 UPDATE_HANDLER_TABLE();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001470 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1471 }
1472 HANDLE_INSTRUCTION_END();
1473
1474 HANDLE_INSTRUCTION_START(NEG_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001475 shadow_frame.SetVReg(inst->VRegA_12x(inst_data), -shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001476 ADVANCE(1);
1477 HANDLE_INSTRUCTION_END();
1478
1479 HANDLE_INSTRUCTION_START(NOT_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001480 shadow_frame.SetVReg(inst->VRegA_12x(inst_data), ~shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001481 ADVANCE(1);
1482 HANDLE_INSTRUCTION_END();
1483
1484 HANDLE_INSTRUCTION_START(NEG_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001485 shadow_frame.SetVRegLong(inst->VRegA_12x(inst_data), -shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001486 ADVANCE(1);
1487 HANDLE_INSTRUCTION_END();
1488
1489 HANDLE_INSTRUCTION_START(NOT_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001490 shadow_frame.SetVRegLong(inst->VRegA_12x(inst_data), ~shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001491 ADVANCE(1);
1492 HANDLE_INSTRUCTION_END();
1493
1494 HANDLE_INSTRUCTION_START(NEG_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001495 shadow_frame.SetVRegFloat(inst->VRegA_12x(inst_data), -shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001496 ADVANCE(1);
1497 HANDLE_INSTRUCTION_END();
1498
1499 HANDLE_INSTRUCTION_START(NEG_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001500 shadow_frame.SetVRegDouble(inst->VRegA_12x(inst_data), -shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001501 ADVANCE(1);
1502 HANDLE_INSTRUCTION_END();
1503
1504 HANDLE_INSTRUCTION_START(INT_TO_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001505 shadow_frame.SetVRegLong(inst->VRegA_12x(inst_data), shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001506 ADVANCE(1);
1507 HANDLE_INSTRUCTION_END();
1508
1509 HANDLE_INSTRUCTION_START(INT_TO_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001510 shadow_frame.SetVRegFloat(inst->VRegA_12x(inst_data), shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001511 ADVANCE(1);
1512 HANDLE_INSTRUCTION_END();
1513
1514 HANDLE_INSTRUCTION_START(INT_TO_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001515 shadow_frame.SetVRegDouble(inst->VRegA_12x(inst_data), shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001516 ADVANCE(1);
1517 HANDLE_INSTRUCTION_END();
1518
1519 HANDLE_INSTRUCTION_START(LONG_TO_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001520 shadow_frame.SetVReg(inst->VRegA_12x(inst_data), shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001521 ADVANCE(1);
1522 HANDLE_INSTRUCTION_END();
1523
1524 HANDLE_INSTRUCTION_START(LONG_TO_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001525 shadow_frame.SetVRegFloat(inst->VRegA_12x(inst_data), shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001526 ADVANCE(1);
1527 HANDLE_INSTRUCTION_END();
1528
1529 HANDLE_INSTRUCTION_START(LONG_TO_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001530 shadow_frame.SetVRegDouble(inst->VRegA_12x(inst_data), shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001531 ADVANCE(1);
1532 HANDLE_INSTRUCTION_END();
1533
1534 HANDLE_INSTRUCTION_START(FLOAT_TO_INT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001535 float val = shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data));
Ian Rogers450dcb52013-09-20 17:36:02 -07001536 int32_t result = art_float_to_integral<int32_t, float>(val);
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001537 shadow_frame.SetVReg(inst->VRegA_12x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001538 ADVANCE(1);
1539 }
1540 HANDLE_INSTRUCTION_END();
1541
1542 HANDLE_INSTRUCTION_START(FLOAT_TO_LONG) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001543 float val = shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data));
Ian Rogers450dcb52013-09-20 17:36:02 -07001544 int64_t result = art_float_to_integral<int64_t, float>(val);
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001545 shadow_frame.SetVRegLong(inst->VRegA_12x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001546 ADVANCE(1);
1547 }
1548 HANDLE_INSTRUCTION_END();
1549
1550 HANDLE_INSTRUCTION_START(FLOAT_TO_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001551 shadow_frame.SetVRegDouble(inst->VRegA_12x(inst_data), shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001552 ADVANCE(1);
1553 HANDLE_INSTRUCTION_END();
1554
1555 HANDLE_INSTRUCTION_START(DOUBLE_TO_INT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001556 double val = shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data));
Ian Rogers450dcb52013-09-20 17:36:02 -07001557 int32_t result = art_float_to_integral<int32_t, double>(val);
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001558 shadow_frame.SetVReg(inst->VRegA_12x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001559 ADVANCE(1);
1560 }
1561 HANDLE_INSTRUCTION_END();
1562
1563 HANDLE_INSTRUCTION_START(DOUBLE_TO_LONG) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001564 double val = shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data));
Ian Rogers450dcb52013-09-20 17:36:02 -07001565 int64_t result = art_float_to_integral<int64_t, double>(val);
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001566 shadow_frame.SetVRegLong(inst->VRegA_12x(inst_data), result);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001567 ADVANCE(1);
1568 }
1569 HANDLE_INSTRUCTION_END();
1570
1571 HANDLE_INSTRUCTION_START(DOUBLE_TO_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001572 shadow_frame.SetVRegFloat(inst->VRegA_12x(inst_data), shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001573 ADVANCE(1);
1574 HANDLE_INSTRUCTION_END();
1575
1576 HANDLE_INSTRUCTION_START(INT_TO_BYTE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001577 shadow_frame.SetVReg(inst->VRegA_12x(inst_data),
1578 static_cast<int8_t>(shadow_frame.GetVReg(inst->VRegB_12x(inst_data))));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001579 ADVANCE(1);
1580 HANDLE_INSTRUCTION_END();
1581
1582 HANDLE_INSTRUCTION_START(INT_TO_CHAR)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001583 shadow_frame.SetVReg(inst->VRegA_12x(inst_data),
1584 static_cast<uint16_t>(shadow_frame.GetVReg(inst->VRegB_12x(inst_data))));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001585 ADVANCE(1);
1586 HANDLE_INSTRUCTION_END();
1587
1588 HANDLE_INSTRUCTION_START(INT_TO_SHORT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001589 shadow_frame.SetVReg(inst->VRegA_12x(inst_data),
1590 static_cast<int16_t>(shadow_frame.GetVReg(inst->VRegB_12x(inst_data))));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001591 ADVANCE(1);
1592 HANDLE_INSTRUCTION_END();
1593
1594 HANDLE_INSTRUCTION_START(ADD_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001595 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001596 shadow_frame.GetVReg(inst->VRegB_23x()) +
1597 shadow_frame.GetVReg(inst->VRegC_23x()));
1598 ADVANCE(2);
1599 HANDLE_INSTRUCTION_END();
1600
1601 HANDLE_INSTRUCTION_START(SUB_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001602 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001603 shadow_frame.GetVReg(inst->VRegB_23x()) -
1604 shadow_frame.GetVReg(inst->VRegC_23x()));
1605 ADVANCE(2);
1606 HANDLE_INSTRUCTION_END();
1607
1608 HANDLE_INSTRUCTION_START(MUL_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001609 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001610 shadow_frame.GetVReg(inst->VRegB_23x()) *
1611 shadow_frame.GetVReg(inst->VRegC_23x()));
1612 ADVANCE(2);
1613 HANDLE_INSTRUCTION_END();
1614
1615 HANDLE_INSTRUCTION_START(DIV_INT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001616 bool success = DoIntDivide(shadow_frame, inst->VRegA_23x(inst_data),
1617 shadow_frame.GetVReg(inst->VRegB_23x()),
1618 shadow_frame.GetVReg(inst->VRegC_23x()));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001619 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1620 }
1621 HANDLE_INSTRUCTION_END();
1622
1623 HANDLE_INSTRUCTION_START(REM_INT) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001624 bool success = DoIntRemainder(shadow_frame, inst->VRegA_23x(inst_data),
1625 shadow_frame.GetVReg(inst->VRegB_23x()),
1626 shadow_frame.GetVReg(inst->VRegC_23x()));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001627 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1628 }
1629 HANDLE_INSTRUCTION_END();
1630
1631 HANDLE_INSTRUCTION_START(SHL_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001632 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001633 shadow_frame.GetVReg(inst->VRegB_23x()) <<
1634 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x1f));
1635 ADVANCE(2);
1636 HANDLE_INSTRUCTION_END();
1637
1638 HANDLE_INSTRUCTION_START(SHR_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001639 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001640 shadow_frame.GetVReg(inst->VRegB_23x()) >>
1641 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x1f));
1642 ADVANCE(2);
1643 HANDLE_INSTRUCTION_END();
1644
1645 HANDLE_INSTRUCTION_START(USHR_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001646 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001647 static_cast<uint32_t>(shadow_frame.GetVReg(inst->VRegB_23x())) >>
1648 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x1f));
1649 ADVANCE(2);
1650 HANDLE_INSTRUCTION_END();
1651
1652 HANDLE_INSTRUCTION_START(AND_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001653 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001654 shadow_frame.GetVReg(inst->VRegB_23x()) &
1655 shadow_frame.GetVReg(inst->VRegC_23x()));
1656 ADVANCE(2);
1657 HANDLE_INSTRUCTION_END();
1658
1659 HANDLE_INSTRUCTION_START(OR_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001660 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001661 shadow_frame.GetVReg(inst->VRegB_23x()) |
1662 shadow_frame.GetVReg(inst->VRegC_23x()));
1663 ADVANCE(2);
1664 HANDLE_INSTRUCTION_END();
1665
1666 HANDLE_INSTRUCTION_START(XOR_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001667 shadow_frame.SetVReg(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001668 shadow_frame.GetVReg(inst->VRegB_23x()) ^
1669 shadow_frame.GetVReg(inst->VRegC_23x()));
1670 ADVANCE(2);
1671 HANDLE_INSTRUCTION_END();
1672
1673 HANDLE_INSTRUCTION_START(ADD_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001674 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001675 shadow_frame.GetVRegLong(inst->VRegB_23x()) +
1676 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1677 ADVANCE(2);
1678 HANDLE_INSTRUCTION_END();
1679
1680 HANDLE_INSTRUCTION_START(SUB_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001681 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001682 shadow_frame.GetVRegLong(inst->VRegB_23x()) -
1683 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1684 ADVANCE(2);
1685 HANDLE_INSTRUCTION_END();
1686
1687 HANDLE_INSTRUCTION_START(MUL_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001688 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001689 shadow_frame.GetVRegLong(inst->VRegB_23x()) *
1690 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1691 ADVANCE(2);
1692 HANDLE_INSTRUCTION_END();
1693
1694 HANDLE_INSTRUCTION_START(DIV_LONG) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001695 bool success = DoLongDivide(shadow_frame, inst->VRegA_23x(inst_data),
1696 shadow_frame.GetVRegLong(inst->VRegB_23x()),
1697 shadow_frame.GetVRegLong(inst->VRegC_23x()));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001698 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1699 }
1700 HANDLE_INSTRUCTION_END();
1701
1702 HANDLE_INSTRUCTION_START(REM_LONG) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001703 bool success = DoLongRemainder(shadow_frame, inst->VRegA_23x(inst_data),
1704 shadow_frame.GetVRegLong(inst->VRegB_23x()),
1705 shadow_frame.GetVRegLong(inst->VRegC_23x()));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001706 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1707 }
1708 HANDLE_INSTRUCTION_END();
1709
1710 HANDLE_INSTRUCTION_START(AND_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001711 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001712 shadow_frame.GetVRegLong(inst->VRegB_23x()) &
1713 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1714 ADVANCE(2);
1715 HANDLE_INSTRUCTION_END();
1716
1717 HANDLE_INSTRUCTION_START(OR_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001718 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001719 shadow_frame.GetVRegLong(inst->VRegB_23x()) |
1720 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1721 ADVANCE(2);
1722 HANDLE_INSTRUCTION_END();
1723
1724 HANDLE_INSTRUCTION_START(XOR_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001725 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001726 shadow_frame.GetVRegLong(inst->VRegB_23x()) ^
1727 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1728 ADVANCE(2);
1729 HANDLE_INSTRUCTION_END();
1730
1731 HANDLE_INSTRUCTION_START(SHL_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001732 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001733 shadow_frame.GetVRegLong(inst->VRegB_23x()) <<
1734 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x3f));
1735 ADVANCE(2);
1736 HANDLE_INSTRUCTION_END();
1737
1738 HANDLE_INSTRUCTION_START(SHR_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001739 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001740 shadow_frame.GetVRegLong(inst->VRegB_23x()) >>
1741 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x3f));
1742 ADVANCE(2);
1743 HANDLE_INSTRUCTION_END();
1744
1745 HANDLE_INSTRUCTION_START(USHR_LONG)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001746 shadow_frame.SetVRegLong(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001747 static_cast<uint64_t>(shadow_frame.GetVRegLong(inst->VRegB_23x())) >>
1748 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x3f));
1749 ADVANCE(2);
1750 HANDLE_INSTRUCTION_END();
1751
1752 HANDLE_INSTRUCTION_START(ADD_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001753 shadow_frame.SetVRegFloat(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001754 shadow_frame.GetVRegFloat(inst->VRegB_23x()) +
1755 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1756 ADVANCE(2);
1757 HANDLE_INSTRUCTION_END();
1758
1759 HANDLE_INSTRUCTION_START(SUB_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001760 shadow_frame.SetVRegFloat(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001761 shadow_frame.GetVRegFloat(inst->VRegB_23x()) -
1762 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1763 ADVANCE(2);
1764 HANDLE_INSTRUCTION_END();
1765
1766 HANDLE_INSTRUCTION_START(MUL_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001767 shadow_frame.SetVRegFloat(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001768 shadow_frame.GetVRegFloat(inst->VRegB_23x()) *
1769 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1770 ADVANCE(2);
1771 HANDLE_INSTRUCTION_END();
1772
1773 HANDLE_INSTRUCTION_START(DIV_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001774 shadow_frame.SetVRegFloat(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001775 shadow_frame.GetVRegFloat(inst->VRegB_23x()) /
1776 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1777 ADVANCE(2);
1778 HANDLE_INSTRUCTION_END();
1779
1780 HANDLE_INSTRUCTION_START(REM_FLOAT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001781 shadow_frame.SetVRegFloat(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001782 fmodf(shadow_frame.GetVRegFloat(inst->VRegB_23x()),
1783 shadow_frame.GetVRegFloat(inst->VRegC_23x())));
1784 ADVANCE(2);
1785 HANDLE_INSTRUCTION_END();
1786
1787 HANDLE_INSTRUCTION_START(ADD_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001788 shadow_frame.SetVRegDouble(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001789 shadow_frame.GetVRegDouble(inst->VRegB_23x()) +
1790 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1791 ADVANCE(2);
1792 HANDLE_INSTRUCTION_END();
1793
1794 HANDLE_INSTRUCTION_START(SUB_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001795 shadow_frame.SetVRegDouble(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001796 shadow_frame.GetVRegDouble(inst->VRegB_23x()) -
1797 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1798 ADVANCE(2);
1799 HANDLE_INSTRUCTION_END();
1800
1801 HANDLE_INSTRUCTION_START(MUL_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001802 shadow_frame.SetVRegDouble(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001803 shadow_frame.GetVRegDouble(inst->VRegB_23x()) *
1804 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1805 ADVANCE(2);
1806 HANDLE_INSTRUCTION_END();
1807
1808 HANDLE_INSTRUCTION_START(DIV_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001809 shadow_frame.SetVRegDouble(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001810 shadow_frame.GetVRegDouble(inst->VRegB_23x()) /
1811 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1812 ADVANCE(2);
1813 HANDLE_INSTRUCTION_END();
1814
1815 HANDLE_INSTRUCTION_START(REM_DOUBLE)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001816 shadow_frame.SetVRegDouble(inst->VRegA_23x(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001817 fmod(shadow_frame.GetVRegDouble(inst->VRegB_23x()),
1818 shadow_frame.GetVRegDouble(inst->VRegC_23x())));
1819 ADVANCE(2);
1820 HANDLE_INSTRUCTION_END();
1821
1822 HANDLE_INSTRUCTION_START(ADD_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001823 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001824 shadow_frame.SetVReg(vregA,
1825 shadow_frame.GetVReg(vregA) +
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001826 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001827 ADVANCE(1);
1828 }
1829 HANDLE_INSTRUCTION_END();
1830
1831 HANDLE_INSTRUCTION_START(SUB_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001832 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001833 shadow_frame.SetVReg(vregA,
1834 shadow_frame.GetVReg(vregA) -
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001835 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001836 ADVANCE(1);
1837 }
1838 HANDLE_INSTRUCTION_END();
1839
1840 HANDLE_INSTRUCTION_START(MUL_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001841 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001842 shadow_frame.SetVReg(vregA,
1843 shadow_frame.GetVReg(vregA) *
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001844 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001845 ADVANCE(1);
1846 }
1847 HANDLE_INSTRUCTION_END();
1848
1849 HANDLE_INSTRUCTION_START(DIV_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001850 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001851 bool success = DoIntDivide(shadow_frame, vregA, shadow_frame.GetVReg(vregA),
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001852 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001853 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1854 }
1855 HANDLE_INSTRUCTION_END();
1856
1857 HANDLE_INSTRUCTION_START(REM_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001858 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001859 bool success = DoIntRemainder(shadow_frame, vregA, shadow_frame.GetVReg(vregA),
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001860 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001861 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1862 }
1863 HANDLE_INSTRUCTION_END();
1864
1865 HANDLE_INSTRUCTION_START(SHL_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001866 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001867 shadow_frame.SetVReg(vregA,
1868 shadow_frame.GetVReg(vregA) <<
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001869 (shadow_frame.GetVReg(inst->VRegB_12x(inst_data)) & 0x1f));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001870 ADVANCE(1);
1871 }
1872 HANDLE_INSTRUCTION_END();
1873
1874 HANDLE_INSTRUCTION_START(SHR_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001875 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001876 shadow_frame.SetVReg(vregA,
1877 shadow_frame.GetVReg(vregA) >>
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001878 (shadow_frame.GetVReg(inst->VRegB_12x(inst_data)) & 0x1f));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001879 ADVANCE(1);
1880 }
1881 HANDLE_INSTRUCTION_END();
1882
1883 HANDLE_INSTRUCTION_START(USHR_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001884 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001885 shadow_frame.SetVReg(vregA,
1886 static_cast<uint32_t>(shadow_frame.GetVReg(vregA)) >>
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001887 (shadow_frame.GetVReg(inst->VRegB_12x(inst_data)) & 0x1f));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001888 ADVANCE(1);
1889 }
1890 HANDLE_INSTRUCTION_END();
1891
1892 HANDLE_INSTRUCTION_START(AND_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001893 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001894 shadow_frame.SetVReg(vregA,
1895 shadow_frame.GetVReg(vregA) &
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001896 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001897 ADVANCE(1);
1898 }
1899 HANDLE_INSTRUCTION_END();
1900
1901 HANDLE_INSTRUCTION_START(OR_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001902 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001903 shadow_frame.SetVReg(vregA,
1904 shadow_frame.GetVReg(vregA) |
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001905 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001906 ADVANCE(1);
1907 }
1908 HANDLE_INSTRUCTION_END();
1909
1910 HANDLE_INSTRUCTION_START(XOR_INT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001911 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001912 shadow_frame.SetVReg(vregA,
1913 shadow_frame.GetVReg(vregA) ^
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001914 shadow_frame.GetVReg(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001915 ADVANCE(1);
1916 }
1917 HANDLE_INSTRUCTION_END();
1918
1919 HANDLE_INSTRUCTION_START(ADD_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001920 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001921 shadow_frame.SetVRegLong(vregA,
1922 shadow_frame.GetVRegLong(vregA) +
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001923 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001924 ADVANCE(1);
1925 }
1926 HANDLE_INSTRUCTION_END();
1927
1928 HANDLE_INSTRUCTION_START(SUB_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001929 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001930 shadow_frame.SetVRegLong(vregA,
1931 shadow_frame.GetVRegLong(vregA) -
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001932 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001933 ADVANCE(1);
1934 }
1935 HANDLE_INSTRUCTION_END();
1936
1937 HANDLE_INSTRUCTION_START(MUL_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001938 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001939 shadow_frame.SetVRegLong(vregA,
1940 shadow_frame.GetVRegLong(vregA) *
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001941 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001942 ADVANCE(1);
1943 }
1944 HANDLE_INSTRUCTION_END();
1945
1946 HANDLE_INSTRUCTION_START(DIV_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001947 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001948 bool success = DoLongDivide(shadow_frame, vregA, shadow_frame.GetVRegLong(vregA),
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001949 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001950 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1951 }
1952 HANDLE_INSTRUCTION_END();
1953
1954 HANDLE_INSTRUCTION_START(REM_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001955 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001956 bool success = DoLongRemainder(shadow_frame, vregA, shadow_frame.GetVRegLong(vregA),
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001957 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001958 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1959 }
1960 HANDLE_INSTRUCTION_END();
1961
1962 HANDLE_INSTRUCTION_START(AND_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001963 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001964 shadow_frame.SetVRegLong(vregA,
1965 shadow_frame.GetVRegLong(vregA) &
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001966 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001967 ADVANCE(1);
1968 }
1969 HANDLE_INSTRUCTION_END();
1970
1971 HANDLE_INSTRUCTION_START(OR_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001972 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001973 shadow_frame.SetVRegLong(vregA,
1974 shadow_frame.GetVRegLong(vregA) |
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001975 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001976 ADVANCE(1);
1977 }
1978 HANDLE_INSTRUCTION_END();
1979
1980 HANDLE_INSTRUCTION_START(XOR_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001981 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001982 shadow_frame.SetVRegLong(vregA,
1983 shadow_frame.GetVRegLong(vregA) ^
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001984 shadow_frame.GetVRegLong(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001985 ADVANCE(1);
1986 }
1987 HANDLE_INSTRUCTION_END();
1988
1989 HANDLE_INSTRUCTION_START(SHL_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001990 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001991 shadow_frame.SetVRegLong(vregA,
1992 shadow_frame.GetVRegLong(vregA) <<
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001993 (shadow_frame.GetVReg(inst->VRegB_12x(inst_data)) & 0x3f));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02001994 ADVANCE(1);
1995 }
1996 HANDLE_INSTRUCTION_END();
1997
1998 HANDLE_INSTRUCTION_START(SHR_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02001999 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002000 shadow_frame.SetVRegLong(vregA,
2001 shadow_frame.GetVRegLong(vregA) >>
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002002 (shadow_frame.GetVReg(inst->VRegB_12x(inst_data)) & 0x3f));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002003 ADVANCE(1);
2004 }
2005 HANDLE_INSTRUCTION_END();
2006
2007 HANDLE_INSTRUCTION_START(USHR_LONG_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002008 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002009 shadow_frame.SetVRegLong(vregA,
2010 static_cast<uint64_t>(shadow_frame.GetVRegLong(vregA)) >>
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002011 (shadow_frame.GetVReg(inst->VRegB_12x(inst_data)) & 0x3f));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002012 ADVANCE(1);
2013 }
2014 HANDLE_INSTRUCTION_END();
2015
2016 HANDLE_INSTRUCTION_START(ADD_FLOAT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002017 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002018 shadow_frame.SetVRegFloat(vregA,
2019 shadow_frame.GetVRegFloat(vregA) +
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002020 shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002021 ADVANCE(1);
2022 }
2023 HANDLE_INSTRUCTION_END();
2024
2025 HANDLE_INSTRUCTION_START(SUB_FLOAT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002026 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002027 shadow_frame.SetVRegFloat(vregA,
2028 shadow_frame.GetVRegFloat(vregA) -
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002029 shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002030 ADVANCE(1);
2031 }
2032 HANDLE_INSTRUCTION_END();
2033
2034 HANDLE_INSTRUCTION_START(MUL_FLOAT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002035 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002036 shadow_frame.SetVRegFloat(vregA,
2037 shadow_frame.GetVRegFloat(vregA) *
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002038 shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002039 ADVANCE(1);
2040 }
2041 HANDLE_INSTRUCTION_END();
2042
2043 HANDLE_INSTRUCTION_START(DIV_FLOAT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002044 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002045 shadow_frame.SetVRegFloat(vregA,
2046 shadow_frame.GetVRegFloat(vregA) /
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002047 shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002048 ADVANCE(1);
2049 }
2050 HANDLE_INSTRUCTION_END();
2051
2052 HANDLE_INSTRUCTION_START(REM_FLOAT_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002053 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002054 shadow_frame.SetVRegFloat(vregA,
2055 fmodf(shadow_frame.GetVRegFloat(vregA),
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002056 shadow_frame.GetVRegFloat(inst->VRegB_12x(inst_data))));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002057 ADVANCE(1);
2058 }
2059 HANDLE_INSTRUCTION_END();
2060
2061 HANDLE_INSTRUCTION_START(ADD_DOUBLE_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002062 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002063 shadow_frame.SetVRegDouble(vregA,
2064 shadow_frame.GetVRegDouble(vregA) +
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002065 shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002066 ADVANCE(1);
2067 }
2068 HANDLE_INSTRUCTION_END();
2069
2070 HANDLE_INSTRUCTION_START(SUB_DOUBLE_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002071 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002072 shadow_frame.SetVRegDouble(vregA,
2073 shadow_frame.GetVRegDouble(vregA) -
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002074 shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002075 ADVANCE(1);
2076 }
2077 HANDLE_INSTRUCTION_END();
2078
2079 HANDLE_INSTRUCTION_START(MUL_DOUBLE_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002080 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002081 shadow_frame.SetVRegDouble(vregA,
2082 shadow_frame.GetVRegDouble(vregA) *
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002083 shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002084 ADVANCE(1);
2085 }
2086 HANDLE_INSTRUCTION_END();
2087
2088 HANDLE_INSTRUCTION_START(DIV_DOUBLE_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002089 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002090 shadow_frame.SetVRegDouble(vregA,
2091 shadow_frame.GetVRegDouble(vregA) /
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002092 shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002093 ADVANCE(1);
2094 }
2095 HANDLE_INSTRUCTION_END();
2096
2097 HANDLE_INSTRUCTION_START(REM_DOUBLE_2ADDR) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002098 uint32_t vregA = inst->VRegA_12x(inst_data);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002099 shadow_frame.SetVRegDouble(vregA,
2100 fmod(shadow_frame.GetVRegDouble(vregA),
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002101 shadow_frame.GetVRegDouble(inst->VRegB_12x(inst_data))));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002102 ADVANCE(1);
2103 }
2104 HANDLE_INSTRUCTION_END();
2105
2106 HANDLE_INSTRUCTION_START(ADD_INT_LIT16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002107 shadow_frame.SetVReg(inst->VRegA_22s(inst_data),
2108 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)) +
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002109 inst->VRegC_22s());
2110 ADVANCE(2);
2111 HANDLE_INSTRUCTION_END();
2112
2113 HANDLE_INSTRUCTION_START(RSUB_INT)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002114 shadow_frame.SetVReg(inst->VRegA_22s(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002115 inst->VRegC_22s() -
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002116 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)));
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002117 ADVANCE(2);
2118 HANDLE_INSTRUCTION_END();
2119
2120 HANDLE_INSTRUCTION_START(MUL_INT_LIT16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002121 shadow_frame.SetVReg(inst->VRegA_22s(inst_data),
2122 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)) *
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002123 inst->VRegC_22s());
2124 ADVANCE(2);
2125 HANDLE_INSTRUCTION_END();
2126
2127 HANDLE_INSTRUCTION_START(DIV_INT_LIT16) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002128 bool success = DoIntDivide(shadow_frame, inst->VRegA_22s(inst_data),
2129 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)), inst->VRegC_22s());
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002130 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2131 }
2132 HANDLE_INSTRUCTION_END();
2133
2134 HANDLE_INSTRUCTION_START(REM_INT_LIT16) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002135 bool success = DoIntRemainder(shadow_frame, inst->VRegA_22s(inst_data),
2136 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)), inst->VRegC_22s());
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002137 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2138 }
2139 HANDLE_INSTRUCTION_END();
2140
2141 HANDLE_INSTRUCTION_START(AND_INT_LIT16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002142 shadow_frame.SetVReg(inst->VRegA_22s(inst_data),
2143 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)) &
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002144 inst->VRegC_22s());
2145 ADVANCE(2);
2146 HANDLE_INSTRUCTION_END();
2147
2148 HANDLE_INSTRUCTION_START(OR_INT_LIT16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002149 shadow_frame.SetVReg(inst->VRegA_22s(inst_data),
2150 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)) |
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002151 inst->VRegC_22s());
2152 ADVANCE(2);
2153 HANDLE_INSTRUCTION_END();
2154
2155 HANDLE_INSTRUCTION_START(XOR_INT_LIT16)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002156 shadow_frame.SetVReg(inst->VRegA_22s(inst_data),
2157 shadow_frame.GetVReg(inst->VRegB_22s(inst_data)) ^
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002158 inst->VRegC_22s());
2159 ADVANCE(2);
2160 HANDLE_INSTRUCTION_END();
2161
2162 HANDLE_INSTRUCTION_START(ADD_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002163 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002164 shadow_frame.GetVReg(inst->VRegB_22b()) +
2165 inst->VRegC_22b());
2166 ADVANCE(2);
2167 HANDLE_INSTRUCTION_END();
2168
2169 HANDLE_INSTRUCTION_START(RSUB_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002170 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002171 inst->VRegC_22b() -
2172 shadow_frame.GetVReg(inst->VRegB_22b()));
2173 ADVANCE(2);
2174 HANDLE_INSTRUCTION_END();
2175
2176 HANDLE_INSTRUCTION_START(MUL_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002177 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002178 shadow_frame.GetVReg(inst->VRegB_22b()) *
2179 inst->VRegC_22b());
2180 ADVANCE(2);
2181 HANDLE_INSTRUCTION_END();
2182
2183 HANDLE_INSTRUCTION_START(DIV_INT_LIT8) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002184 bool success = DoIntDivide(shadow_frame, inst->VRegA_22b(inst_data),
2185 shadow_frame.GetVReg(inst->VRegB_22b()), inst->VRegC_22b());
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002186 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2187 }
2188 HANDLE_INSTRUCTION_END();
2189
2190 HANDLE_INSTRUCTION_START(REM_INT_LIT8) {
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002191 bool success = DoIntRemainder(shadow_frame, inst->VRegA_22b(inst_data),
2192 shadow_frame.GetVReg(inst->VRegB_22b()), inst->VRegC_22b());
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002193 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2194 }
2195 HANDLE_INSTRUCTION_END();
2196
2197 HANDLE_INSTRUCTION_START(AND_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002198 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002199 shadow_frame.GetVReg(inst->VRegB_22b()) &
2200 inst->VRegC_22b());
2201 ADVANCE(2);
2202 HANDLE_INSTRUCTION_END();
2203
2204 HANDLE_INSTRUCTION_START(OR_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002205 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002206 shadow_frame.GetVReg(inst->VRegB_22b()) |
2207 inst->VRegC_22b());
2208 ADVANCE(2);
2209 HANDLE_INSTRUCTION_END();
2210
2211 HANDLE_INSTRUCTION_START(XOR_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002212 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002213 shadow_frame.GetVReg(inst->VRegB_22b()) ^
2214 inst->VRegC_22b());
2215 ADVANCE(2);
2216 HANDLE_INSTRUCTION_END();
2217
2218 HANDLE_INSTRUCTION_START(SHL_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002219 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002220 shadow_frame.GetVReg(inst->VRegB_22b()) <<
2221 (inst->VRegC_22b() & 0x1f));
2222 ADVANCE(2);
2223 HANDLE_INSTRUCTION_END();
2224
2225 HANDLE_INSTRUCTION_START(SHR_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002226 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002227 shadow_frame.GetVReg(inst->VRegB_22b()) >>
2228 (inst->VRegC_22b() & 0x1f));
2229 ADVANCE(2);
2230 HANDLE_INSTRUCTION_END();
2231
2232 HANDLE_INSTRUCTION_START(USHR_INT_LIT8)
Sebastien Hertz3b588e02013-09-11 14:33:18 +02002233 shadow_frame.SetVReg(inst->VRegA_22b(inst_data),
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002234 static_cast<uint32_t>(shadow_frame.GetVReg(inst->VRegB_22b())) >>
2235 (inst->VRegC_22b() & 0x1f));
2236 ADVANCE(2);
2237 HANDLE_INSTRUCTION_END();
2238
2239 HANDLE_INSTRUCTION_START(UNUSED_3E)
2240 UnexpectedOpcode(inst, mh);
2241 HANDLE_INSTRUCTION_END();
2242
2243 HANDLE_INSTRUCTION_START(UNUSED_3F)
2244 UnexpectedOpcode(inst, mh);
2245 HANDLE_INSTRUCTION_END();
2246
2247 HANDLE_INSTRUCTION_START(UNUSED_40)
2248 UnexpectedOpcode(inst, mh);
2249 HANDLE_INSTRUCTION_END();
2250
2251 HANDLE_INSTRUCTION_START(UNUSED_41)
2252 UnexpectedOpcode(inst, mh);
2253 HANDLE_INSTRUCTION_END();
2254
2255 HANDLE_INSTRUCTION_START(UNUSED_42)
2256 UnexpectedOpcode(inst, mh);
2257 HANDLE_INSTRUCTION_END();
2258
2259 HANDLE_INSTRUCTION_START(UNUSED_43)
2260 UnexpectedOpcode(inst, mh);
2261 HANDLE_INSTRUCTION_END();
2262
2263 HANDLE_INSTRUCTION_START(UNUSED_79)
2264 UnexpectedOpcode(inst, mh);
2265 HANDLE_INSTRUCTION_END();
2266
2267 HANDLE_INSTRUCTION_START(UNUSED_7A)
2268 UnexpectedOpcode(inst, mh);
2269 HANDLE_INSTRUCTION_END();
2270
2271 HANDLE_INSTRUCTION_START(UNUSED_EB)
2272 UnexpectedOpcode(inst, mh);
2273 HANDLE_INSTRUCTION_END();
2274
2275 HANDLE_INSTRUCTION_START(UNUSED_EC)
2276 UnexpectedOpcode(inst, mh);
2277 HANDLE_INSTRUCTION_END();
2278
2279 HANDLE_INSTRUCTION_START(UNUSED_ED)
2280 UnexpectedOpcode(inst, mh);
2281 HANDLE_INSTRUCTION_END();
2282
2283 HANDLE_INSTRUCTION_START(UNUSED_EE)
2284 UnexpectedOpcode(inst, mh);
2285 HANDLE_INSTRUCTION_END();
2286
2287 HANDLE_INSTRUCTION_START(UNUSED_EF)
2288 UnexpectedOpcode(inst, mh);
2289 HANDLE_INSTRUCTION_END();
2290
2291 HANDLE_INSTRUCTION_START(UNUSED_F0)
2292 UnexpectedOpcode(inst, mh);
2293 HANDLE_INSTRUCTION_END();
2294
2295 HANDLE_INSTRUCTION_START(UNUSED_F1)
2296 UnexpectedOpcode(inst, mh);
2297 HANDLE_INSTRUCTION_END();
2298
2299 HANDLE_INSTRUCTION_START(UNUSED_F2)
2300 UnexpectedOpcode(inst, mh);
2301 HANDLE_INSTRUCTION_END();
2302
2303 HANDLE_INSTRUCTION_START(UNUSED_F3)
2304 UnexpectedOpcode(inst, mh);
2305 HANDLE_INSTRUCTION_END();
2306
2307 HANDLE_INSTRUCTION_START(UNUSED_F4)
2308 UnexpectedOpcode(inst, mh);
2309 HANDLE_INSTRUCTION_END();
2310
2311 HANDLE_INSTRUCTION_START(UNUSED_F5)
2312 UnexpectedOpcode(inst, mh);
2313 HANDLE_INSTRUCTION_END();
2314
2315 HANDLE_INSTRUCTION_START(UNUSED_F6)
2316 UnexpectedOpcode(inst, mh);
2317 HANDLE_INSTRUCTION_END();
2318
2319 HANDLE_INSTRUCTION_START(UNUSED_F7)
2320 UnexpectedOpcode(inst, mh);
2321 HANDLE_INSTRUCTION_END();
2322
2323 HANDLE_INSTRUCTION_START(UNUSED_F8)
2324 UnexpectedOpcode(inst, mh);
2325 HANDLE_INSTRUCTION_END();
2326
2327 HANDLE_INSTRUCTION_START(UNUSED_F9)
2328 UnexpectedOpcode(inst, mh);
2329 HANDLE_INSTRUCTION_END();
2330
2331 HANDLE_INSTRUCTION_START(UNUSED_FA)
2332 UnexpectedOpcode(inst, mh);
2333 HANDLE_INSTRUCTION_END();
2334
2335 HANDLE_INSTRUCTION_START(UNUSED_FB)
2336 UnexpectedOpcode(inst, mh);
2337 HANDLE_INSTRUCTION_END();
2338
2339 HANDLE_INSTRUCTION_START(UNUSED_FC)
2340 UnexpectedOpcode(inst, mh);
2341 HANDLE_INSTRUCTION_END();
2342
2343 HANDLE_INSTRUCTION_START(UNUSED_FD)
2344 UnexpectedOpcode(inst, mh);
2345 HANDLE_INSTRUCTION_END();
2346
2347 HANDLE_INSTRUCTION_START(UNUSED_FE)
2348 UnexpectedOpcode(inst, mh);
2349 HANDLE_INSTRUCTION_END();
2350
2351 HANDLE_INSTRUCTION_START(UNUSED_FF)
2352 UnexpectedOpcode(inst, mh);
2353 HANDLE_INSTRUCTION_END();
2354
2355 exception_pending_label: {
2356 CHECK(self->IsExceptionPending());
Sebastien Hertz1eda2262013-09-09 16:53:14 +02002357 if (UNLIKELY(self->TestAllFlags())) {
2358 CheckSuspend(self);
Sebastien Hertzee1997a2013-09-19 14:47:09 +02002359 UPDATE_HANDLER_TABLE();
Sebastien Hertz1eda2262013-09-09 16:53:14 +02002360 }
Sebastien Hertz947ff082013-09-17 14:10:13 +02002361 Object* this_object = shadow_frame.GetThisObject(code_item->ins_size_);
Sebastien Hertzee1997a2013-09-19 14:47:09 +02002362 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation();
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002363 uint32_t found_dex_pc = FindNextInstructionFollowingException(self, shadow_frame, dex_pc,
Sebastien Hertz947ff082013-09-17 14:10:13 +02002364 this_object,
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002365 instrumentation);
2366 if (found_dex_pc == DexFile::kDexNoIndex) {
2367 return JValue(); /* Handled in caller. */
2368 } else {
2369 int32_t displacement = static_cast<int32_t>(found_dex_pc) - static_cast<int32_t>(dex_pc);
2370 ADVANCE(displacement);
2371 }
2372 }
2373
2374 // Create alternative instruction handlers dedicated to instrumentation.
Sebastien Hertzee1997a2013-09-19 14:47:09 +02002375#define INSTRUMENTATION_INSTRUCTION_HANDLER(o, code, n, f, r, i, a, v) \
2376 alt_op_##code: { \
2377 instrumentation::Instrumentation* instrumentation = Runtime::Current()->GetInstrumentation(); \
2378 if (UNLIKELY(instrumentation->HasDexPcListeners())) { \
2379 instrumentation->DexPcMovedEvent(self, shadow_frame.GetThisObject(code_item->ins_size_), \
2380 shadow_frame.GetMethod(), dex_pc); \
2381 } \
2382 UPDATE_HANDLER_TABLE(); \
2383 goto *handlersTable[instrumentation::kMainHandlerTable][Instruction::code]; \
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002384 }
2385#include "dex_instruction_list.h"
2386 DEX_INSTRUCTION_LIST(INSTRUMENTATION_INSTRUCTION_HANDLER)
2387#undef DEX_INSTRUCTION_LIST
2388#undef INSTRUMENTATION_INSTRUCTION_HANDLER
2389} // NOLINT(readability/fn_size)
2390
2391// Explicit definitions of ExecuteGotoImpl.
Sebastien Hertzc6714852013-09-30 16:42:32 +02002392template SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) HOT_ATTR
2393JValue ExecuteGotoImpl<true>(Thread* self, MethodHelper& mh,
2394 const DexFile::CodeItem* code_item,
2395 ShadowFrame& shadow_frame, JValue result_register);
2396template SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) HOT_ATTR
2397JValue ExecuteGotoImpl<false>(Thread* self, MethodHelper& mh,
2398 const DexFile::CodeItem* code_item,
2399 ShadowFrame& shadow_frame, JValue result_register);
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002400
2401} // namespace interpreter
2402} // namespace art