blob: 67517ea0f679c7dd459f2dfcfb74f81604b87774 [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*.
25// - "dex_pc": the current pc.
26// - "shadow_frame": the current shadow frame.
27// - "insns": the start of current method's code item.
28// - "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.
32// TODO: move check suspend to backward branch, return and exception handling.
33#define ADVANCE(_offset) \
34 do { \
35 int32_t disp = static_cast<int32_t>(_offset); \
36 inst = inst->RelativeAt(disp); \
37 dex_pc = static_cast<uint32_t>(static_cast<int32_t>(dex_pc) + disp); \
38 shadow_frame.SetDexPC(dex_pc); \
Sebastien Hertz8ece0502013-08-07 11:26:41 +020039 TraceExecution(shadow_frame, inst, dex_pc, mh); \
40 goto *currentHandlersTable[inst->Opcode()]; \
41 } 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
54#define UNREACHABLE_CODE_CHECK() \
55 do { \
56 if (kIsDebugBuild) { \
57 LOG(FATAL) << "We should not be here !"; \
58 } \
59 } while (false)
60
61#define HANDLE_INSTRUCTION_START(opcode) op_##opcode: // NOLINT(whitespace/labels)
62#define HANDLE_INSTRUCTION_END() UNREACHABLE_CODE_CHECK()
63
Sebastien Hertz8ece0502013-08-07 11:26:41 +020064template<bool do_access_check>
65JValue ExecuteGotoImpl(Thread* self, MethodHelper& mh, const DexFile::CodeItem* code_item,
66 ShadowFrame& shadow_frame, JValue result_register) {
67 if (UNLIKELY(!shadow_frame.HasReferenceArray())) {
68 LOG(FATAL) << "Invalid shadow frame for interpreter use";
69 return JValue();
70 }
71 self->VerifyStack();
72 instrumentation::Instrumentation* const instrumentation = Runtime::Current()->GetInstrumentation();
73
74 // As the 'this' object won't change during the execution of current code, we
75 // want to cache it in local variables. Nevertheless, in order to let the
76 // garbage collector access it, we store it into sirt references.
77 SirtRef<Object> this_object_ref(self, shadow_frame.GetThisObject(code_item->ins_size_));
78
79 uint32_t dex_pc = shadow_frame.GetDexPC();
80 if (LIKELY(dex_pc == 0)) { // We are entering the method as opposed to deoptimizing..
81 if (UNLIKELY(instrumentation->HasMethodEntryListeners())) {
82 instrumentation->MethodEnterEvent(self, this_object_ref.get(),
83 shadow_frame.GetMethod(), 0);
84 }
85 }
86 const uint16_t* const insns = code_item->insns_;
87 const Instruction* inst = Instruction::At(insns + dex_pc);
88
89 // Define handlers table.
90 static const void* handlersTable[kNumPackedOpcodes] = {
91#define INSTRUCTION_HANDLER(o, code, n, f, r, i, a, v) &&op_##code,
92#include "dex_instruction_list.h"
93 DEX_INSTRUCTION_LIST(INSTRUCTION_HANDLER)
94#undef DEX_INSTRUCTION_LIST
95#undef INSTRUCTION_HANDLER
96 };
97
98 static const void* instrumentationHandlersTable[kNumPackedOpcodes] = {
99#define INSTRUCTION_HANDLER(o, code, n, f, r, i, a, v) &&instrumentation_op_##code,
100#include "dex_instruction_list.h"
101 DEX_INSTRUCTION_LIST(INSTRUCTION_HANDLER)
102#undef DEX_INSTRUCTION_LIST
103#undef INSTRUCTION_HANDLER
104 };
105
106 const void** currentHandlersTable;
107 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
108 currentHandlersTable = instrumentationHandlersTable;
109 } else {
110 currentHandlersTable = handlersTable;
111 }
112
113 // Jump to first instruction.
114 ADVANCE(0);
115 UNREACHABLE_CODE_CHECK();
116
117 HANDLE_INSTRUCTION_START(NOP)
118 ADVANCE(1);
119 HANDLE_INSTRUCTION_END();
120
121 HANDLE_INSTRUCTION_START(MOVE)
122 shadow_frame.SetVReg(inst->VRegA_12x(),
123 shadow_frame.GetVReg(inst->VRegB_12x()));
124 ADVANCE(1);
125 HANDLE_INSTRUCTION_END();
126
127 HANDLE_INSTRUCTION_START(MOVE_FROM16)
128 shadow_frame.SetVReg(inst->VRegA_22x(),
129 shadow_frame.GetVReg(inst->VRegB_22x()));
130 ADVANCE(2);
131 HANDLE_INSTRUCTION_END();
132
133 HANDLE_INSTRUCTION_START(MOVE_16)
134 shadow_frame.SetVReg(inst->VRegA_32x(),
135 shadow_frame.GetVReg(inst->VRegB_32x()));
136 ADVANCE(3);
137 HANDLE_INSTRUCTION_END();
138
139 HANDLE_INSTRUCTION_START(MOVE_WIDE)
140 shadow_frame.SetVRegLong(inst->VRegA_12x(),
141 shadow_frame.GetVRegLong(inst->VRegB_12x()));
142 ADVANCE(1);
143 HANDLE_INSTRUCTION_END();
144
145 HANDLE_INSTRUCTION_START(MOVE_WIDE_FROM16)
146 shadow_frame.SetVRegLong(inst->VRegA_22x(),
147 shadow_frame.GetVRegLong(inst->VRegB_22x()));
148 ADVANCE(2);
149 HANDLE_INSTRUCTION_END();
150
151 HANDLE_INSTRUCTION_START(MOVE_WIDE_16)
152 shadow_frame.SetVRegLong(inst->VRegA_32x(),
153 shadow_frame.GetVRegLong(inst->VRegB_32x()));
154 ADVANCE(3);
155 HANDLE_INSTRUCTION_END();
156
157 HANDLE_INSTRUCTION_START(MOVE_OBJECT)
158 shadow_frame.SetVRegReference(inst->VRegA_12x(),
159 shadow_frame.GetVRegReference(inst->VRegB_12x()));
160 ADVANCE(1);
161 HANDLE_INSTRUCTION_END();
162
163 HANDLE_INSTRUCTION_START(MOVE_OBJECT_FROM16)
164 shadow_frame.SetVRegReference(inst->VRegA_22x(),
165 shadow_frame.GetVRegReference(inst->VRegB_22x()));
166 ADVANCE(2);
167 HANDLE_INSTRUCTION_END();
168
169 HANDLE_INSTRUCTION_START(MOVE_OBJECT_16)
170 shadow_frame.SetVRegReference(inst->VRegA_32x(),
171 shadow_frame.GetVRegReference(inst->VRegB_32x()));
172 ADVANCE(3);
173 HANDLE_INSTRUCTION_END();
174
175 HANDLE_INSTRUCTION_START(MOVE_RESULT)
176 shadow_frame.SetVReg(inst->VRegA_11x(), result_register.GetI());
177 ADVANCE(1);
178 HANDLE_INSTRUCTION_END();
179
180 HANDLE_INSTRUCTION_START(MOVE_RESULT_WIDE)
181 shadow_frame.SetVRegLong(inst->VRegA_11x(), result_register.GetJ());
182 ADVANCE(1);
183 HANDLE_INSTRUCTION_END();
184
185 HANDLE_INSTRUCTION_START(MOVE_RESULT_OBJECT)
186 shadow_frame.SetVRegReference(inst->VRegA_11x(), result_register.GetL());
187 ADVANCE(1);
188 HANDLE_INSTRUCTION_END();
189
190 HANDLE_INSTRUCTION_START(MOVE_EXCEPTION) {
191 Throwable* exception = self->GetException(NULL);
192 self->ClearException();
193 shadow_frame.SetVRegReference(inst->VRegA_11x(), exception);
194 ADVANCE(1);
195 }
196 HANDLE_INSTRUCTION_END();
197
198 HANDLE_INSTRUCTION_START(RETURN_VOID) {
199 JValue result;
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200200 if (UNLIKELY(self->TestAllFlags())) {
201 CheckSuspend(self);
202 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200203 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
204 instrumentation->MethodExitEvent(self, this_object_ref.get(),
205 shadow_frame.GetMethod(), dex_pc,
206 result);
207 }
208 return result;
209 }
210 HANDLE_INSTRUCTION_END();
211
212 HANDLE_INSTRUCTION_START(RETURN_VOID_BARRIER) {
213 ANDROID_MEMBAR_STORE();
214 JValue result;
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200215 if (UNLIKELY(self->TestAllFlags())) {
216 CheckSuspend(self);
217 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200218 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
219 instrumentation->MethodExitEvent(self, this_object_ref.get(),
220 shadow_frame.GetMethod(), dex_pc,
221 result);
222 }
223 return result;
224 }
225 HANDLE_INSTRUCTION_END();
226
227 HANDLE_INSTRUCTION_START(RETURN) {
228 JValue result;
229 result.SetJ(0);
230 result.SetI(shadow_frame.GetVReg(inst->VRegA_11x()));
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200231 if (UNLIKELY(self->TestAllFlags())) {
232 CheckSuspend(self);
233 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200234 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
235 instrumentation->MethodExitEvent(self, this_object_ref.get(),
236 shadow_frame.GetMethod(), dex_pc,
237 result);
238 }
239 return result;
240 }
241 HANDLE_INSTRUCTION_END();
242
243 HANDLE_INSTRUCTION_START(RETURN_WIDE) {
244 JValue result;
245 result.SetJ(shadow_frame.GetVRegLong(inst->VRegA_11x()));
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200246 if (UNLIKELY(self->TestAllFlags())) {
247 CheckSuspend(self);
248 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200249 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
250 instrumentation->MethodExitEvent(self, this_object_ref.get(),
251 shadow_frame.GetMethod(), dex_pc,
252 result);
253 }
254 return result;
255 }
256 HANDLE_INSTRUCTION_END();
257
258 HANDLE_INSTRUCTION_START(RETURN_OBJECT) {
259 JValue result;
260 result.SetJ(0);
261 result.SetL(shadow_frame.GetVRegReference(inst->VRegA_11x()));
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200262 if (UNLIKELY(self->TestAllFlags())) {
263 CheckSuspend(self);
264 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200265 if (UNLIKELY(instrumentation->HasMethodExitListeners())) {
266 instrumentation->MethodExitEvent(self, this_object_ref.get(),
267 shadow_frame.GetMethod(), dex_pc,
268 result);
269 }
270 return result;
271 }
272 HANDLE_INSTRUCTION_END();
273
274 HANDLE_INSTRUCTION_START(CONST_4) {
275 uint32_t dst = inst->VRegA_11n();
276 int32_t val = inst->VRegB_11n();
277 shadow_frame.SetVReg(dst, val);
278 if (val == 0) {
279 shadow_frame.SetVRegReference(dst, NULL);
280 }
281 ADVANCE(1);
282 }
283 HANDLE_INSTRUCTION_END();
284
285 HANDLE_INSTRUCTION_START(CONST_16) {
286 uint32_t dst = inst->VRegA_21s();
287 int32_t val = inst->VRegB_21s();
288 shadow_frame.SetVReg(dst, val);
289 if (val == 0) {
290 shadow_frame.SetVRegReference(dst, NULL);
291 }
292 ADVANCE(2);
293 }
294 HANDLE_INSTRUCTION_END();
295
296 HANDLE_INSTRUCTION_START(CONST) {
297 uint32_t dst = inst->VRegA_31i();
298 int32_t val = inst->VRegB_31i();
299 shadow_frame.SetVReg(dst, val);
300 if (val == 0) {
301 shadow_frame.SetVRegReference(dst, NULL);
302 }
303 ADVANCE(3);
304 }
305 HANDLE_INSTRUCTION_END();
306
307 HANDLE_INSTRUCTION_START(CONST_HIGH16) {
308 uint32_t dst = inst->VRegA_21h();
309 int32_t val = static_cast<int32_t>(inst->VRegB_21h() << 16);
310 shadow_frame.SetVReg(dst, val);
311 if (val == 0) {
312 shadow_frame.SetVRegReference(dst, NULL);
313 }
314 ADVANCE(2);
315 }
316 HANDLE_INSTRUCTION_END();
317
318 HANDLE_INSTRUCTION_START(CONST_WIDE_16)
319 shadow_frame.SetVRegLong(inst->VRegA_21s(), inst->VRegB_21s());
320 ADVANCE(2);
321 HANDLE_INSTRUCTION_END();
322
323 HANDLE_INSTRUCTION_START(CONST_WIDE_32)
324 shadow_frame.SetVRegLong(inst->VRegA_31i(), inst->VRegB_31i());
325 ADVANCE(3);
326 HANDLE_INSTRUCTION_END();
327
328 HANDLE_INSTRUCTION_START(CONST_WIDE)
329 shadow_frame.SetVRegLong(inst->VRegA_51l(), inst->VRegB_51l());
330 ADVANCE(5);
331 HANDLE_INSTRUCTION_END();
332
333 HANDLE_INSTRUCTION_START(CONST_WIDE_HIGH16)
334 shadow_frame.SetVRegLong(inst->VRegA_21h(),
335 static_cast<uint64_t>(inst->VRegB_21h()) << 48);
336 ADVANCE(2);
337 HANDLE_INSTRUCTION_END();
338
339 HANDLE_INSTRUCTION_START(CONST_STRING) {
340 String* s = ResolveString(self, mh, inst->VRegB_21c());
341 if (UNLIKELY(s == NULL)) {
342 HANDLE_PENDING_EXCEPTION();
343 } else {
344 shadow_frame.SetVRegReference(inst->VRegA_21c(), s);
345 ADVANCE(2);
346 }
347 }
348 HANDLE_INSTRUCTION_END();
349
350 HANDLE_INSTRUCTION_START(CONST_STRING_JUMBO) {
351 String* s = ResolveString(self, mh, inst->VRegB_31c());
352 if (UNLIKELY(s == NULL)) {
353 HANDLE_PENDING_EXCEPTION();
354 } else {
355 shadow_frame.SetVRegReference(inst->VRegA_31c(), s);
356 ADVANCE(3);
357 }
358 }
359 HANDLE_INSTRUCTION_END();
360
361 HANDLE_INSTRUCTION_START(CONST_CLASS) {
362 Class* c = ResolveVerifyAndClinit(inst->VRegB_21c(), shadow_frame.GetMethod(),
363 self, false, do_access_check);
364 if (UNLIKELY(c == NULL)) {
365 HANDLE_PENDING_EXCEPTION();
366 } else {
367 shadow_frame.SetVRegReference(inst->VRegA_21c(), c);
368 ADVANCE(2);
369 }
370 }
371 HANDLE_INSTRUCTION_END();
372
373 HANDLE_INSTRUCTION_START(MONITOR_ENTER) {
374 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_11x());
375 if (UNLIKELY(obj == NULL)) {
376 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
377 HANDLE_PENDING_EXCEPTION();
378 } else {
379 DoMonitorEnter(self, obj);
380 POSSIBLY_HANDLE_PENDING_EXCEPTION(self->IsExceptionPending(), 1);
381 }
382 }
383 HANDLE_INSTRUCTION_END();
384
385 HANDLE_INSTRUCTION_START(MONITOR_EXIT) {
386 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_11x());
387 if (UNLIKELY(obj == NULL)) {
388 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
389 HANDLE_PENDING_EXCEPTION();
390 } else {
391 DoMonitorExit(self, obj);
392 POSSIBLY_HANDLE_PENDING_EXCEPTION(self->IsExceptionPending(), 1);
393 }
394 }
395 HANDLE_INSTRUCTION_END();
396
397 HANDLE_INSTRUCTION_START(CHECK_CAST) {
398 Class* c = ResolveVerifyAndClinit(inst->VRegB_21c(), shadow_frame.GetMethod(),
399 self, false, do_access_check);
400 if (UNLIKELY(c == NULL)) {
401 HANDLE_PENDING_EXCEPTION();
402 } else {
403 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_21c());
404 if (UNLIKELY(obj != NULL && !obj->InstanceOf(c))) {
405 ThrowClassCastException(c, obj->GetClass());
406 HANDLE_PENDING_EXCEPTION();
407 } else {
408 ADVANCE(2);
409 }
410 }
411 }
412 HANDLE_INSTRUCTION_END();
413
414 HANDLE_INSTRUCTION_START(INSTANCE_OF) {
415 Class* c = ResolveVerifyAndClinit(inst->VRegC_22c(), shadow_frame.GetMethod(),
416 self, false, do_access_check);
417 if (UNLIKELY(c == NULL)) {
418 HANDLE_PENDING_EXCEPTION();
419 } else {
420 Object* obj = shadow_frame.GetVRegReference(inst->VRegB_22c());
421 shadow_frame.SetVReg(inst->VRegA_22c(), (obj != NULL && obj->InstanceOf(c)) ? 1 : 0);
422 ADVANCE(2);
423 }
424 }
425 HANDLE_INSTRUCTION_END();
426
427 HANDLE_INSTRUCTION_START(ARRAY_LENGTH) {
428 Object* array = shadow_frame.GetVRegReference(inst->VRegB_12x());
429 if (UNLIKELY(array == NULL)) {
430 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
431 HANDLE_PENDING_EXCEPTION();
432 } else {
433 shadow_frame.SetVReg(inst->VRegA_12x(), array->AsArray()->GetLength());
434 ADVANCE(1);
435 }
436 }
437 HANDLE_INSTRUCTION_END();
438
439 HANDLE_INSTRUCTION_START(NEW_INSTANCE) {
440 Object* obj = AllocObjectFromCode(inst->VRegB_21c(), shadow_frame.GetMethod(),
441 self, do_access_check);
442 if (UNLIKELY(obj == NULL)) {
443 HANDLE_PENDING_EXCEPTION();
444 } else {
445 shadow_frame.SetVRegReference(inst->VRegA_21c(), obj);
446 ADVANCE(2);
447 }
448 }
449 HANDLE_INSTRUCTION_END();
450
451 HANDLE_INSTRUCTION_START(NEW_ARRAY) {
452 int32_t length = shadow_frame.GetVReg(inst->VRegB_22c());
453 Object* obj = AllocArrayFromCode(inst->VRegC_22c(), shadow_frame.GetMethod(),
454 length, self, do_access_check);
455 if (UNLIKELY(obj == NULL)) {
456 HANDLE_PENDING_EXCEPTION();
457 } else {
458 shadow_frame.SetVRegReference(inst->VRegA_22c(), obj);
459 ADVANCE(2);
460 }
461 }
462 HANDLE_INSTRUCTION_END();
463
464 HANDLE_INSTRUCTION_START(FILLED_NEW_ARRAY) {
465 bool success = DoFilledNewArray<false, do_access_check>(inst, shadow_frame,
466 self, &result_register);
467 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
468 }
469 HANDLE_INSTRUCTION_END();
470
471 HANDLE_INSTRUCTION_START(FILLED_NEW_ARRAY_RANGE) {
472 bool success = DoFilledNewArray<true, do_access_check>(inst, shadow_frame,
473 self, &result_register);
474 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
475 }
476 HANDLE_INSTRUCTION_END();
477
478 HANDLE_INSTRUCTION_START(FILL_ARRAY_DATA) {
479 Object* obj = shadow_frame.GetVRegReference(inst->VRegA_31t());
480 if (UNLIKELY(obj == NULL)) {
481 ThrowNullPointerException(NULL, "null array in FILL_ARRAY_DATA");
482 HANDLE_PENDING_EXCEPTION();
483 } else {
484 Array* array = obj->AsArray();
485 DCHECK(array->IsArrayInstance() && !array->IsObjectArray());
486 const uint16_t* payload_addr = reinterpret_cast<const uint16_t*>(inst) + inst->VRegB_31t();
487 const Instruction::ArrayDataPayload* payload =
488 reinterpret_cast<const Instruction::ArrayDataPayload*>(payload_addr);
489 if (UNLIKELY(static_cast<int32_t>(payload->element_count) > array->GetLength())) {
490 self->ThrowNewExceptionF(shadow_frame.GetCurrentLocationForThrow(),
491 "Ljava/lang/ArrayIndexOutOfBoundsException;",
492 "failed FILL_ARRAY_DATA; length=%d, index=%d",
493 array->GetLength(), payload->element_count);
494 HANDLE_PENDING_EXCEPTION();
495 } else {
496 uint32_t size_in_bytes = payload->element_count * payload->element_width;
497 memcpy(array->GetRawData(payload->element_width), payload->data, size_in_bytes);
498 ADVANCE(3);
499 }
500 }
501 }
502 HANDLE_INSTRUCTION_END();
503
504 HANDLE_INSTRUCTION_START(THROW) {
505 Object* exception = shadow_frame.GetVRegReference(inst->VRegA_11x());
506 if (UNLIKELY(exception == NULL)) {
507 ThrowNullPointerException(NULL, "throw with null exception");
508 } else {
509 self->SetException(shadow_frame.GetCurrentLocationForThrow(), exception->AsThrowable());
510 }
511 HANDLE_PENDING_EXCEPTION();
512 }
513 HANDLE_INSTRUCTION_END();
514
515 HANDLE_INSTRUCTION_START(GOTO) {
516 int8_t offset = inst->VRegA_10t();
517 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200518 if (UNLIKELY(self->TestAllFlags())) {
519 CheckSuspend(self);
520 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200521 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
522 currentHandlersTable = instrumentationHandlersTable;
523 } else {
524 currentHandlersTable = handlersTable;
525 }
526 }
527 ADVANCE(offset);
528 }
529 HANDLE_INSTRUCTION_END();
530
531 HANDLE_INSTRUCTION_START(GOTO_16) {
532 int16_t offset = inst->VRegA_20t();
533 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200534 if (UNLIKELY(self->TestAllFlags())) {
535 CheckSuspend(self);
536 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200537 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
538 currentHandlersTable = instrumentationHandlersTable;
539 } else {
540 currentHandlersTable = handlersTable;
541 }
542 }
543 ADVANCE(offset);
544 }
545 HANDLE_INSTRUCTION_END();
546
547 HANDLE_INSTRUCTION_START(GOTO_32) {
548 int32_t offset = inst->VRegA_30t();
549 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200550 if (UNLIKELY(self->TestAllFlags())) {
551 CheckSuspend(self);
552 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200553 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
554 currentHandlersTable = instrumentationHandlersTable;
555 } else {
556 currentHandlersTable = handlersTable;
557 }
558 }
559 ADVANCE(offset);
560 }
561 HANDLE_INSTRUCTION_END();
562
563 HANDLE_INSTRUCTION_START(PACKED_SWITCH) {
564 int32_t offset = DoPackedSwitch(inst, shadow_frame);
565 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200566 if (UNLIKELY(self->TestAllFlags())) {
567 CheckSuspend(self);
568 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200569 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
570 currentHandlersTable = instrumentationHandlersTable;
571 } else {
572 currentHandlersTable = handlersTable;
573 }
574 }
575 ADVANCE(offset);
576 }
577 HANDLE_INSTRUCTION_END();
578
579 HANDLE_INSTRUCTION_START(SPARSE_SWITCH) {
580 int32_t offset = DoSparseSwitch(inst, shadow_frame);
581 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200582 if (UNLIKELY(self->TestAllFlags())) {
583 CheckSuspend(self);
584 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200585 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
586 currentHandlersTable = instrumentationHandlersTable;
587 } else {
588 currentHandlersTable = handlersTable;
589 }
590 }
591 ADVANCE(offset);
592 }
593 HANDLE_INSTRUCTION_END();
594
595 HANDLE_INSTRUCTION_START(CMPL_FLOAT) {
596 float val1 = shadow_frame.GetVRegFloat(inst->VRegB_23x());
597 float val2 = shadow_frame.GetVRegFloat(inst->VRegC_23x());
598 int32_t result;
599 if (val1 > val2) {
600 result = 1;
601 } else if (val1 == val2) {
602 result = 0;
603 } else {
604 result = -1;
605 }
606 shadow_frame.SetVReg(inst->VRegA_23x(), result);
607 ADVANCE(2);
608 }
609 HANDLE_INSTRUCTION_END();
610
611 HANDLE_INSTRUCTION_START(CMPG_FLOAT) {
612 float val1 = shadow_frame.GetVRegFloat(inst->VRegB_23x());
613 float val2 = shadow_frame.GetVRegFloat(inst->VRegC_23x());
614 int32_t result;
615 if (val1 < val2) {
616 result = -1;
617 } else if (val1 == val2) {
618 result = 0;
619 } else {
620 result = 1;
621 }
622 shadow_frame.SetVReg(inst->VRegA_23x(), result);
623 ADVANCE(2);
624 }
625 HANDLE_INSTRUCTION_END();
626
627 HANDLE_INSTRUCTION_START(CMPL_DOUBLE) {
628 double val1 = shadow_frame.GetVRegDouble(inst->VRegB_23x());
629 double val2 = shadow_frame.GetVRegDouble(inst->VRegC_23x());
630 int32_t result;
631 if (val1 > val2) {
632 result = 1;
633 } else if (val1 == val2) {
634 result = 0;
635 } else {
636 result = -1;
637 }
638 shadow_frame.SetVReg(inst->VRegA_23x(), result);
639 ADVANCE(2);
640 }
641 HANDLE_INSTRUCTION_END();
642
643 HANDLE_INSTRUCTION_START(CMPG_DOUBLE) {
644 double val1 = shadow_frame.GetVRegDouble(inst->VRegB_23x());
645 double val2 = shadow_frame.GetVRegDouble(inst->VRegC_23x());
646 int32_t result;
647 if (val1 < val2) {
648 result = -1;
649 } else if (val1 == val2) {
650 result = 0;
651 } else {
652 result = 1;
653 }
654 shadow_frame.SetVReg(inst->VRegA_23x(), result);
655 ADVANCE(2);
656 }
657 HANDLE_INSTRUCTION_END();
658
659 HANDLE_INSTRUCTION_START(CMP_LONG) {
660 int64_t val1 = shadow_frame.GetVRegLong(inst->VRegB_23x());
661 int64_t val2 = shadow_frame.GetVRegLong(inst->VRegC_23x());
662 int32_t result;
663 if (val1 > val2) {
664 result = 1;
665 } else if (val1 == val2) {
666 result = 0;
667 } else {
668 result = -1;
669 }
670 shadow_frame.SetVReg(inst->VRegA_23x(), result);
671 ADVANCE(2);
672 }
673 HANDLE_INSTRUCTION_END();
674
675 HANDLE_INSTRUCTION_START(IF_EQ) {
676 if (shadow_frame.GetVReg(inst->VRegA_22t()) == shadow_frame.GetVReg(inst->VRegB_22t())) {
677 int16_t offset = inst->VRegC_22t();
678 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200679 if (UNLIKELY(self->TestAllFlags())) {
680 CheckSuspend(self);
681 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200682 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
683 currentHandlersTable = instrumentationHandlersTable;
684 } else {
685 currentHandlersTable = handlersTable;
686 }
687 }
688 ADVANCE(offset);
689 } else {
690 ADVANCE(2);
691 }
692 }
693 HANDLE_INSTRUCTION_END();
694
695 HANDLE_INSTRUCTION_START(IF_NE) {
696 if (shadow_frame.GetVReg(inst->VRegA_22t()) != shadow_frame.GetVReg(inst->VRegB_22t())) {
697 int16_t offset = inst->VRegC_22t();
698 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200699 if (UNLIKELY(self->TestAllFlags())) {
700 CheckSuspend(self);
701 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200702 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
703 currentHandlersTable = instrumentationHandlersTable;
704 } else {
705 currentHandlersTable = handlersTable;
706 }
707 }
708 ADVANCE(offset);
709 } else {
710 ADVANCE(2);
711 }
712 }
713 HANDLE_INSTRUCTION_END();
714
715 HANDLE_INSTRUCTION_START(IF_LT) {
716 if (shadow_frame.GetVReg(inst->VRegA_22t()) < shadow_frame.GetVReg(inst->VRegB_22t())) {
717 int16_t offset = inst->VRegC_22t();
718 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200719 if (UNLIKELY(self->TestAllFlags())) {
720 CheckSuspend(self);
721 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200722 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
723 currentHandlersTable = instrumentationHandlersTable;
724 } else {
725 currentHandlersTable = handlersTable;
726 }
727 }
728 ADVANCE(offset);
729 } else {
730 ADVANCE(2);
731 }
732 }
733 HANDLE_INSTRUCTION_END();
734
735 HANDLE_INSTRUCTION_START(IF_GE) {
736 if (shadow_frame.GetVReg(inst->VRegA_22t()) >= shadow_frame.GetVReg(inst->VRegB_22t())) {
737 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);
741 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200742 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
743 currentHandlersTable = instrumentationHandlersTable;
744 } else {
745 currentHandlersTable = handlersTable;
746 }
747 }
748 ADVANCE(offset);
749 } else {
750 ADVANCE(2);
751 }
752 }
753 HANDLE_INSTRUCTION_END();
754
755 HANDLE_INSTRUCTION_START(IF_GT) {
756 if (shadow_frame.GetVReg(inst->VRegA_22t()) > shadow_frame.GetVReg(inst->VRegB_22t())) {
757 int16_t offset = inst->VRegC_22t();
758 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200759 if (UNLIKELY(self->TestAllFlags())) {
760 CheckSuspend(self);
761 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200762 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
763 currentHandlersTable = instrumentationHandlersTable;
764 } else {
765 currentHandlersTable = handlersTable;
766 }
767 }
768 ADVANCE(offset);
769 } else {
770 ADVANCE(2);
771 }
772 }
773 HANDLE_INSTRUCTION_END();
774
775 HANDLE_INSTRUCTION_START(IF_LE) {
776 if (shadow_frame.GetVReg(inst->VRegA_22t()) <= shadow_frame.GetVReg(inst->VRegB_22t())) {
777 int16_t offset = inst->VRegC_22t();
778 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200779 if (UNLIKELY(self->TestAllFlags())) {
780 CheckSuspend(self);
781 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200782 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
783 currentHandlersTable = instrumentationHandlersTable;
784 } else {
785 currentHandlersTable = handlersTable;
786 }
787 }
788 ADVANCE(offset);
789 } else {
790 ADVANCE(2);
791 }
792 }
793 HANDLE_INSTRUCTION_END();
794
795 HANDLE_INSTRUCTION_START(IF_EQZ) {
796 if (shadow_frame.GetVReg(inst->VRegA_21t()) == 0) {
797 int16_t offset = inst->VRegB_21t();
798 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200799 if (UNLIKELY(self->TestAllFlags())) {
800 CheckSuspend(self);
801 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200802 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
803 currentHandlersTable = instrumentationHandlersTable;
804 } else {
805 currentHandlersTable = handlersTable;
806 }
807 }
808 ADVANCE(offset);
809 } else {
810 ADVANCE(2);
811 }
812 }
813 HANDLE_INSTRUCTION_END();
814
815 HANDLE_INSTRUCTION_START(IF_NEZ) {
816 if (shadow_frame.GetVReg(inst->VRegA_21t()) != 0) {
817 int16_t offset = inst->VRegB_21t();
818 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200819 if (UNLIKELY(self->TestAllFlags())) {
820 CheckSuspend(self);
821 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200822 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
823 currentHandlersTable = instrumentationHandlersTable;
824 } else {
825 currentHandlersTable = handlersTable;
826 }
827 }
828 ADVANCE(offset);
829 } else {
830 ADVANCE(2);
831 }
832 }
833 HANDLE_INSTRUCTION_END();
834
835 HANDLE_INSTRUCTION_START(IF_LTZ) {
836 if (shadow_frame.GetVReg(inst->VRegA_21t()) < 0) {
837 int16_t offset = inst->VRegB_21t();
838 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200839 if (UNLIKELY(self->TestAllFlags())) {
840 CheckSuspend(self);
841 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200842 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
843 currentHandlersTable = instrumentationHandlersTable;
844 } else {
845 currentHandlersTable = handlersTable;
846 }
847 }
848 ADVANCE(offset);
849 } else {
850 ADVANCE(2);
851 }
852 }
853 HANDLE_INSTRUCTION_END();
854
855 HANDLE_INSTRUCTION_START(IF_GEZ) {
856 if (shadow_frame.GetVReg(inst->VRegA_21t()) >= 0) {
857 int16_t offset = inst->VRegB_21t();
858 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200859 if (UNLIKELY(self->TestAllFlags())) {
860 CheckSuspend(self);
861 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200862 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
863 currentHandlersTable = instrumentationHandlersTable;
864 } else {
865 currentHandlersTable = handlersTable;
866 }
867 }
868 ADVANCE(offset);
869 } else {
870 ADVANCE(2);
871 }
872 }
873 HANDLE_INSTRUCTION_END();
874
875 HANDLE_INSTRUCTION_START(IF_GTZ) {
876 if (shadow_frame.GetVReg(inst->VRegA_21t()) > 0) {
877 int16_t offset = inst->VRegB_21t();
878 if (IsBackwardBranch(offset)) {
Sebastien Hertz1eda2262013-09-09 16:53:14 +0200879 if (UNLIKELY(self->TestAllFlags())) {
880 CheckSuspend(self);
881 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200882 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
883 currentHandlersTable = instrumentationHandlersTable;
884 } else {
885 currentHandlersTable = handlersTable;
886 }
887 }
888 ADVANCE(offset);
889 } else {
890 ADVANCE(2);
891 }
892 }
893 HANDLE_INSTRUCTION_END();
894
895 HANDLE_INSTRUCTION_START(IF_LEZ) {
896 if (shadow_frame.GetVReg(inst->VRegA_21t()) <= 0) {
897 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);
901 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +0200902 if (UNLIKELY(instrumentation->HasDexPcListeners())) {
903 currentHandlersTable = instrumentationHandlersTable;
904 } else {
905 currentHandlersTable = handlersTable;
906 }
907 }
908 ADVANCE(offset);
909 } else {
910 ADVANCE(2);
911 }
912 }
913 HANDLE_INSTRUCTION_END();
914
915 HANDLE_INSTRUCTION_START(AGET_BOOLEAN) {
916 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
917 if (UNLIKELY(a == NULL)) {
918 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
919 HANDLE_PENDING_EXCEPTION();
920 } else {
921 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
922 BooleanArray* array = a->AsBooleanArray();
923 if (LIKELY(array->IsValidIndex(index))) {
924 shadow_frame.SetVReg(inst->VRegA_23x(), array->GetData()[index]);
925 ADVANCE(2);
926 } else {
927 HANDLE_PENDING_EXCEPTION();
928 }
929 }
930 }
931 HANDLE_INSTRUCTION_END();
932
933 HANDLE_INSTRUCTION_START(AGET_BYTE) {
934 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
935 if (UNLIKELY(a == NULL)) {
936 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
937 HANDLE_PENDING_EXCEPTION();
938 } else {
939 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
940 ByteArray* array = a->AsByteArray();
941 if (LIKELY(array->IsValidIndex(index))) {
942 shadow_frame.SetVReg(inst->VRegA_23x(), array->GetData()[index]);
943 ADVANCE(2);
944 } else {
945 HANDLE_PENDING_EXCEPTION();
946 }
947 }
948 }
949 HANDLE_INSTRUCTION_END();
950
951 HANDLE_INSTRUCTION_START(AGET_CHAR) {
952 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
953 if (UNLIKELY(a == NULL)) {
954 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
955 HANDLE_PENDING_EXCEPTION();
956 } else {
957 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
958 CharArray* array = a->AsCharArray();
959 if (LIKELY(array->IsValidIndex(index))) {
960 shadow_frame.SetVReg(inst->VRegA_23x(), array->GetData()[index]);
961 ADVANCE(2);
962 } else {
963 HANDLE_PENDING_EXCEPTION();
964 }
965 }
966 }
967 HANDLE_INSTRUCTION_END();
968
969 HANDLE_INSTRUCTION_START(AGET_SHORT) {
970 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
971 if (UNLIKELY(a == NULL)) {
972 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
973 HANDLE_PENDING_EXCEPTION();
974 } else {
975 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
976 ShortArray* array = a->AsShortArray();
977 if (LIKELY(array->IsValidIndex(index))) {
978 shadow_frame.SetVReg(inst->VRegA_23x(), array->GetData()[index]);
979 ADVANCE(2);
980 } else {
981 HANDLE_PENDING_EXCEPTION();
982 }
983 }
984 }
985 HANDLE_INSTRUCTION_END();
986
987 HANDLE_INSTRUCTION_START(AGET) {
988 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
989 if (UNLIKELY(a == NULL)) {
990 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
991 HANDLE_PENDING_EXCEPTION();
992 } else {
993 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
994 IntArray* array = a->AsIntArray();
995 if (LIKELY(array->IsValidIndex(index))) {
996 shadow_frame.SetVReg(inst->VRegA_23x(), array->GetData()[index]);
997 ADVANCE(2);
998 } else {
999 HANDLE_PENDING_EXCEPTION();
1000 }
1001 }
1002 }
1003 HANDLE_INSTRUCTION_END();
1004
1005 HANDLE_INSTRUCTION_START(AGET_WIDE) {
1006 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1007 if (UNLIKELY(a == NULL)) {
1008 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1009 HANDLE_PENDING_EXCEPTION();
1010 } else {
1011 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1012 LongArray* array = a->AsLongArray();
1013 if (LIKELY(array->IsValidIndex(index))) {
1014 shadow_frame.SetVRegLong(inst->VRegA_23x(), array->GetData()[index]);
1015 ADVANCE(2);
1016 } else {
1017 HANDLE_PENDING_EXCEPTION();
1018 }
1019 }
1020 }
1021 HANDLE_INSTRUCTION_END();
1022
1023 HANDLE_INSTRUCTION_START(AGET_OBJECT) {
1024 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1025 if (UNLIKELY(a == NULL)) {
1026 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1027 HANDLE_PENDING_EXCEPTION();
1028 } else {
1029 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1030 ObjectArray<Object>* array = a->AsObjectArray<Object>();
1031 if (LIKELY(array->IsValidIndex(index))) {
1032 shadow_frame.SetVRegReference(inst->VRegA_23x(), array->GetWithoutChecks(index));
1033 ADVANCE(2);
1034 } else {
1035 HANDLE_PENDING_EXCEPTION();
1036 }
1037 }
1038 }
1039 HANDLE_INSTRUCTION_END();
1040
1041 HANDLE_INSTRUCTION_START(APUT_BOOLEAN) {
1042 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1043 if (UNLIKELY(a == NULL)) {
1044 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1045 HANDLE_PENDING_EXCEPTION();
1046 } else {
1047 uint8_t val = shadow_frame.GetVReg(inst->VRegA_23x());
1048 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1049 BooleanArray* array = a->AsBooleanArray();
1050 if (LIKELY(array->IsValidIndex(index))) {
1051 array->GetData()[index] = val;
1052 ADVANCE(2);
1053 } else {
1054 HANDLE_PENDING_EXCEPTION();
1055 }
1056 }
1057 }
1058 HANDLE_INSTRUCTION_END();
1059
1060 HANDLE_INSTRUCTION_START(APUT_BYTE) {
1061 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1062 if (UNLIKELY(a == NULL)) {
1063 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1064 HANDLE_PENDING_EXCEPTION();
1065 } else {
1066 int8_t val = shadow_frame.GetVReg(inst->VRegA_23x());
1067 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1068 ByteArray* array = a->AsByteArray();
1069 if (LIKELY(array->IsValidIndex(index))) {
1070 array->GetData()[index] = val;
1071 ADVANCE(2);
1072 } else {
1073 HANDLE_PENDING_EXCEPTION();
1074 }
1075 }
1076 }
1077 HANDLE_INSTRUCTION_END();
1078
1079 HANDLE_INSTRUCTION_START(APUT_CHAR) {
1080 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1081 if (UNLIKELY(a == NULL)) {
1082 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1083 HANDLE_PENDING_EXCEPTION();
1084 } else {
1085 uint16_t val = shadow_frame.GetVReg(inst->VRegA_23x());
1086 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1087 CharArray* array = a->AsCharArray();
1088 if (LIKELY(array->IsValidIndex(index))) {
1089 array->GetData()[index] = val;
1090 ADVANCE(2);
1091 } else {
1092 HANDLE_PENDING_EXCEPTION();
1093 }
1094 }
1095 }
1096 HANDLE_INSTRUCTION_END();
1097
1098 HANDLE_INSTRUCTION_START(APUT_SHORT) {
1099 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1100 if (UNLIKELY(a == NULL)) {
1101 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1102 HANDLE_PENDING_EXCEPTION();
1103 } else {
1104 int16_t val = shadow_frame.GetVReg(inst->VRegA_23x());
1105 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1106 ShortArray* array = a->AsShortArray();
1107 if (LIKELY(array->IsValidIndex(index))) {
1108 array->GetData()[index] = val;
1109 ADVANCE(2);
1110 } else {
1111 HANDLE_PENDING_EXCEPTION();
1112 }
1113 }
1114 }
1115 HANDLE_INSTRUCTION_END();
1116
1117 HANDLE_INSTRUCTION_START(APUT) {
1118 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1119 if (UNLIKELY(a == NULL)) {
1120 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1121 HANDLE_PENDING_EXCEPTION();
1122 } else {
1123 int32_t val = shadow_frame.GetVReg(inst->VRegA_23x());
1124 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1125 IntArray* array = a->AsIntArray();
1126 if (LIKELY(array->IsValidIndex(index))) {
1127 array->GetData()[index] = val;
1128 ADVANCE(2);
1129 } else {
1130 HANDLE_PENDING_EXCEPTION();
1131 }
1132 }
1133 }
1134 HANDLE_INSTRUCTION_END();
1135
1136 HANDLE_INSTRUCTION_START(APUT_WIDE) {
1137 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1138 if (UNLIKELY(a == NULL)) {
1139 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1140 HANDLE_PENDING_EXCEPTION();
1141 } else {
1142 int64_t val = shadow_frame.GetVRegLong(inst->VRegA_23x());
1143 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1144 LongArray* array = a->AsLongArray();
1145 if (LIKELY(array->IsValidIndex(index))) {
1146 array->GetData()[index] = val;
1147 ADVANCE(2);
1148 } else {
1149 HANDLE_PENDING_EXCEPTION();
1150 }
1151 }
1152 }
1153 HANDLE_INSTRUCTION_END();
1154
1155 HANDLE_INSTRUCTION_START(APUT_OBJECT) {
1156 Object* a = shadow_frame.GetVRegReference(inst->VRegB_23x());
1157 if (UNLIKELY(a == NULL)) {
1158 ThrowNullPointerExceptionFromDexPC(shadow_frame.GetCurrentLocationForThrow());
1159 HANDLE_PENDING_EXCEPTION();
1160 } else {
1161 int32_t index = shadow_frame.GetVReg(inst->VRegC_23x());
1162 Object* val = shadow_frame.GetVRegReference(inst->VRegA_23x());
1163 ObjectArray<Object>* array = a->AsObjectArray<Object>();
1164 if (LIKELY(array->IsValidIndex(index) && array->CheckAssignable(val))) {
1165 array->SetWithoutChecks(index, val);
1166 ADVANCE(2);
1167 } else {
1168 HANDLE_PENDING_EXCEPTION();
1169 }
1170 }
1171 }
1172 HANDLE_INSTRUCTION_END();
1173
1174 HANDLE_INSTRUCTION_START(IGET_BOOLEAN) {
1175 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst);
1176 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1177 }
1178 HANDLE_INSTRUCTION_END();
1179
1180 HANDLE_INSTRUCTION_START(IGET_BYTE) {
1181 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst);
1182 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1183 }
1184 HANDLE_INSTRUCTION_END();
1185
1186 HANDLE_INSTRUCTION_START(IGET_CHAR) {
1187 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst);
1188 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1189 }
1190 HANDLE_INSTRUCTION_END();
1191
1192 HANDLE_INSTRUCTION_START(IGET_SHORT) {
1193 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst);
1194 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1195 }
1196 HANDLE_INSTRUCTION_END();
1197
1198 HANDLE_INSTRUCTION_START(IGET) {
1199 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst);
1200 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1201 }
1202 HANDLE_INSTRUCTION_END();
1203
1204 HANDLE_INSTRUCTION_START(IGET_WIDE) {
1205 bool success = DoFieldGet<InstancePrimitiveRead, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst);
1206 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1207 }
1208 HANDLE_INSTRUCTION_END();
1209
1210 HANDLE_INSTRUCTION_START(IGET_OBJECT) {
1211 bool success = DoFieldGet<InstanceObjectRead, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst);
1212 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1213 }
1214 HANDLE_INSTRUCTION_END();
1215
1216 HANDLE_INSTRUCTION_START(IGET_QUICK) {
1217 bool success = DoIGetQuick<Primitive::kPrimInt>(self, shadow_frame, inst);
1218 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1219 }
1220 HANDLE_INSTRUCTION_END();
1221
1222 HANDLE_INSTRUCTION_START(IGET_WIDE_QUICK) {
1223 bool success = DoIGetQuick<Primitive::kPrimLong>(self, shadow_frame, inst);
1224 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1225 }
1226 HANDLE_INSTRUCTION_END();
1227
1228 HANDLE_INSTRUCTION_START(IGET_OBJECT_QUICK) {
1229 bool success = DoIGetQuick<Primitive::kPrimNot>(self, shadow_frame, inst);
1230 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1231 }
1232 HANDLE_INSTRUCTION_END();
1233
1234 HANDLE_INSTRUCTION_START(SGET_BOOLEAN) {
1235 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst);
1236 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1237 }
1238 HANDLE_INSTRUCTION_END();
1239
1240 HANDLE_INSTRUCTION_START(SGET_BYTE) {
1241 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst);
1242 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1243 }
1244 HANDLE_INSTRUCTION_END();
1245
1246 HANDLE_INSTRUCTION_START(SGET_CHAR) {
1247 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst);
1248 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1249 }
1250 HANDLE_INSTRUCTION_END();
1251
1252 HANDLE_INSTRUCTION_START(SGET_SHORT) {
1253 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst);
1254 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1255 }
1256 HANDLE_INSTRUCTION_END();
1257
1258 HANDLE_INSTRUCTION_START(SGET) {
1259 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst);
1260 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1261 }
1262 HANDLE_INSTRUCTION_END();
1263
1264 HANDLE_INSTRUCTION_START(SGET_WIDE) {
1265 bool success = DoFieldGet<StaticPrimitiveRead, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst);
1266 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1267 }
1268 HANDLE_INSTRUCTION_END();
1269
1270 HANDLE_INSTRUCTION_START(SGET_OBJECT) {
1271 bool success = DoFieldGet<StaticObjectRead, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst);
1272 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1273 }
1274 HANDLE_INSTRUCTION_END();
1275
1276 HANDLE_INSTRUCTION_START(IPUT_BOOLEAN) {
1277 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst);
1278 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1279 }
1280 HANDLE_INSTRUCTION_END();
1281
1282 HANDLE_INSTRUCTION_START(IPUT_BYTE) {
1283 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst);
1284 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1285 }
1286 HANDLE_INSTRUCTION_END();
1287
1288 HANDLE_INSTRUCTION_START(IPUT_CHAR) {
1289 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst);
1290 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1291 }
1292 HANDLE_INSTRUCTION_END();
1293
1294 HANDLE_INSTRUCTION_START(IPUT_SHORT) {
1295 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst);
1296 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1297 }
1298 HANDLE_INSTRUCTION_END();
1299
1300 HANDLE_INSTRUCTION_START(IPUT) {
1301 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst);
1302 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1303 }
1304 HANDLE_INSTRUCTION_END();
1305
1306 HANDLE_INSTRUCTION_START(IPUT_WIDE) {
1307 bool success = DoFieldPut<InstancePrimitiveWrite, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst);
1308 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1309 }
1310 HANDLE_INSTRUCTION_END();
1311
1312 HANDLE_INSTRUCTION_START(IPUT_OBJECT) {
1313 bool success = DoFieldPut<InstanceObjectWrite, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst);
1314 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1315 }
1316 HANDLE_INSTRUCTION_END();
1317
1318 HANDLE_INSTRUCTION_START(IPUT_QUICK) {
1319 bool success = DoIPutQuick<Primitive::kPrimInt>(self, shadow_frame, inst);
1320 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1321 }
1322 HANDLE_INSTRUCTION_END();
1323
1324 HANDLE_INSTRUCTION_START(IPUT_WIDE_QUICK) {
1325 bool success = DoIPutQuick<Primitive::kPrimLong>(self, shadow_frame, inst);
1326 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1327 }
1328 HANDLE_INSTRUCTION_END();
1329
1330 HANDLE_INSTRUCTION_START(IPUT_OBJECT_QUICK) {
1331 bool success = DoIPutQuick<Primitive::kPrimNot>(self, shadow_frame, inst);
1332 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1333 }
1334 HANDLE_INSTRUCTION_END();
1335
1336 HANDLE_INSTRUCTION_START(SPUT_BOOLEAN) {
1337 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimBoolean, do_access_check>(self, shadow_frame, inst);
1338 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1339 }
1340 HANDLE_INSTRUCTION_END();
1341
1342 HANDLE_INSTRUCTION_START(SPUT_BYTE) {
1343 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimByte, do_access_check>(self, shadow_frame, inst);
1344 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1345 }
1346 HANDLE_INSTRUCTION_END();
1347
1348 HANDLE_INSTRUCTION_START(SPUT_CHAR) {
1349 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimChar, do_access_check>(self, shadow_frame, inst);
1350 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1351 }
1352 HANDLE_INSTRUCTION_END();
1353
1354 HANDLE_INSTRUCTION_START(SPUT_SHORT) {
1355 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimShort, do_access_check>(self, shadow_frame, inst);
1356 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1357 }
1358 HANDLE_INSTRUCTION_END();
1359
1360 HANDLE_INSTRUCTION_START(SPUT) {
1361 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimInt, do_access_check>(self, shadow_frame, inst);
1362 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1363 }
1364 HANDLE_INSTRUCTION_END();
1365
1366 HANDLE_INSTRUCTION_START(SPUT_WIDE) {
1367 bool success = DoFieldPut<StaticPrimitiveWrite, Primitive::kPrimLong, do_access_check>(self, shadow_frame, inst);
1368 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1369 }
1370 HANDLE_INSTRUCTION_END();
1371
1372 HANDLE_INSTRUCTION_START(SPUT_OBJECT) {
1373 bool success = DoFieldPut<StaticObjectWrite, Primitive::kPrimNot, do_access_check>(self, shadow_frame, inst);
1374 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1375 }
1376 HANDLE_INSTRUCTION_END();
1377
1378 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL) {
1379 bool success = DoInvoke<kVirtual, false, do_access_check>(self, shadow_frame, inst, &result_register);
1380 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1381 }
1382 HANDLE_INSTRUCTION_END();
1383
1384 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL_RANGE) {
1385 bool success = DoInvoke<kVirtual, true, do_access_check>(self, shadow_frame, inst, &result_register);
1386 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1387 }
1388 HANDLE_INSTRUCTION_END();
1389
1390 HANDLE_INSTRUCTION_START(INVOKE_SUPER) {
1391 bool success = DoInvoke<kSuper, false, do_access_check>(self, shadow_frame, inst, &result_register);
1392 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1393 }
1394 HANDLE_INSTRUCTION_END();
1395
1396 HANDLE_INSTRUCTION_START(INVOKE_SUPER_RANGE) {
1397 bool success = DoInvoke<kSuper, true, do_access_check>(self, shadow_frame, inst, &result_register);
1398 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1399 }
1400 HANDLE_INSTRUCTION_END();
1401
1402 HANDLE_INSTRUCTION_START(INVOKE_DIRECT) {
1403 bool success = DoInvoke<kDirect, false, do_access_check>(self, shadow_frame, inst, &result_register);
1404 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1405 }
1406 HANDLE_INSTRUCTION_END();
1407
1408 HANDLE_INSTRUCTION_START(INVOKE_DIRECT_RANGE) {
1409 bool success = DoInvoke<kDirect, true, do_access_check>(self, shadow_frame, inst, &result_register);
1410 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1411 }
1412 HANDLE_INSTRUCTION_END();
1413
1414 HANDLE_INSTRUCTION_START(INVOKE_INTERFACE) {
1415 bool success = DoInvoke<kInterface, false, do_access_check>(self, shadow_frame, inst, &result_register);
1416 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1417 }
1418 HANDLE_INSTRUCTION_END();
1419
1420 HANDLE_INSTRUCTION_START(INVOKE_INTERFACE_RANGE) {
1421 bool success = DoInvoke<kInterface, true, do_access_check>(self, shadow_frame, inst, &result_register);
1422 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1423 }
1424 HANDLE_INSTRUCTION_END();
1425
1426 HANDLE_INSTRUCTION_START(INVOKE_STATIC) {
1427 bool success = DoInvoke<kStatic, false, do_access_check>(self, shadow_frame, inst, &result_register);
1428 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1429 }
1430 HANDLE_INSTRUCTION_END();
1431
1432 HANDLE_INSTRUCTION_START(INVOKE_STATIC_RANGE) {
1433 bool success = DoInvoke<kStatic, true, do_access_check>(self, shadow_frame, inst, &result_register);
1434 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1435 }
1436 HANDLE_INSTRUCTION_END();
1437
1438 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL_QUICK) {
1439 bool success = DoInvokeVirtualQuick<false>(self, shadow_frame, inst, &result_register);
1440 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1441 }
1442 HANDLE_INSTRUCTION_END();
1443
1444 HANDLE_INSTRUCTION_START(INVOKE_VIRTUAL_RANGE_QUICK) {
1445 bool success = DoInvokeVirtualQuick<true>(self, shadow_frame, inst, &result_register);
1446 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 3);
1447 }
1448 HANDLE_INSTRUCTION_END();
1449
1450 HANDLE_INSTRUCTION_START(NEG_INT)
1451 shadow_frame.SetVReg(inst->VRegA_12x(), -shadow_frame.GetVReg(inst->VRegB_12x()));
1452 ADVANCE(1);
1453 HANDLE_INSTRUCTION_END();
1454
1455 HANDLE_INSTRUCTION_START(NOT_INT)
1456 shadow_frame.SetVReg(inst->VRegA_12x(), ~shadow_frame.GetVReg(inst->VRegB_12x()));
1457 ADVANCE(1);
1458 HANDLE_INSTRUCTION_END();
1459
1460 HANDLE_INSTRUCTION_START(NEG_LONG)
1461 shadow_frame.SetVRegLong(inst->VRegA_12x(), -shadow_frame.GetVRegLong(inst->VRegB_12x()));
1462 ADVANCE(1);
1463 HANDLE_INSTRUCTION_END();
1464
1465 HANDLE_INSTRUCTION_START(NOT_LONG)
1466 shadow_frame.SetVRegLong(inst->VRegA_12x(), ~shadow_frame.GetVRegLong(inst->VRegB_12x()));
1467 ADVANCE(1);
1468 HANDLE_INSTRUCTION_END();
1469
1470 HANDLE_INSTRUCTION_START(NEG_FLOAT)
1471 shadow_frame.SetVRegFloat(inst->VRegA_12x(), -shadow_frame.GetVRegFloat(inst->VRegB_12x()));
1472 ADVANCE(1);
1473 HANDLE_INSTRUCTION_END();
1474
1475 HANDLE_INSTRUCTION_START(NEG_DOUBLE)
1476 shadow_frame.SetVRegDouble(inst->VRegA_12x(), -shadow_frame.GetVRegDouble(inst->VRegB_12x()));
1477 ADVANCE(1);
1478 HANDLE_INSTRUCTION_END();
1479
1480 HANDLE_INSTRUCTION_START(INT_TO_LONG)
1481 shadow_frame.SetVRegLong(inst->VRegA_12x(), shadow_frame.GetVReg(inst->VRegB_12x()));
1482 ADVANCE(1);
1483 HANDLE_INSTRUCTION_END();
1484
1485 HANDLE_INSTRUCTION_START(INT_TO_FLOAT)
1486 shadow_frame.SetVRegFloat(inst->VRegA_12x(), shadow_frame.GetVReg(inst->VRegB_12x()));
1487 ADVANCE(1);
1488 HANDLE_INSTRUCTION_END();
1489
1490 HANDLE_INSTRUCTION_START(INT_TO_DOUBLE)
1491 shadow_frame.SetVRegDouble(inst->VRegA_12x(), shadow_frame.GetVReg(inst->VRegB_12x()));
1492 ADVANCE(1);
1493 HANDLE_INSTRUCTION_END();
1494
1495 HANDLE_INSTRUCTION_START(LONG_TO_INT)
1496 shadow_frame.SetVReg(inst->VRegA_12x(), shadow_frame.GetVRegLong(inst->VRegB_12x()));
1497 ADVANCE(1);
1498 HANDLE_INSTRUCTION_END();
1499
1500 HANDLE_INSTRUCTION_START(LONG_TO_FLOAT)
1501 shadow_frame.SetVRegFloat(inst->VRegA_12x(), shadow_frame.GetVRegLong(inst->VRegB_12x()));
1502 ADVANCE(1);
1503 HANDLE_INSTRUCTION_END();
1504
1505 HANDLE_INSTRUCTION_START(LONG_TO_DOUBLE)
1506 shadow_frame.SetVRegDouble(inst->VRegA_12x(), shadow_frame.GetVRegLong(inst->VRegB_12x()));
1507 ADVANCE(1);
1508 HANDLE_INSTRUCTION_END();
1509
1510 HANDLE_INSTRUCTION_START(FLOAT_TO_INT) {
1511 float val = shadow_frame.GetVRegFloat(inst->VRegB_12x());
1512 int32_t result;
1513 if (val != val) {
1514 result = 0;
1515 } else if (val > static_cast<float>(kMaxInt)) {
1516 result = kMaxInt;
1517 } else if (val < static_cast<float>(kMinInt)) {
1518 result = kMinInt;
1519 } else {
1520 result = val;
1521 }
1522 shadow_frame.SetVReg(inst->VRegA_12x(), result);
1523 ADVANCE(1);
1524 }
1525 HANDLE_INSTRUCTION_END();
1526
1527 HANDLE_INSTRUCTION_START(FLOAT_TO_LONG) {
1528 float val = shadow_frame.GetVRegFloat(inst->VRegB_12x());
1529 int64_t result;
1530 if (val != val) {
1531 result = 0;
1532 } else if (val > static_cast<float>(kMaxLong)) {
1533 result = kMaxLong;
1534 } else if (val < static_cast<float>(kMinLong)) {
1535 result = kMinLong;
1536 } else {
1537 result = val;
1538 }
1539 shadow_frame.SetVRegLong(inst->VRegA_12x(), result);
1540 ADVANCE(1);
1541 }
1542 HANDLE_INSTRUCTION_END();
1543
1544 HANDLE_INSTRUCTION_START(FLOAT_TO_DOUBLE)
1545 shadow_frame.SetVRegDouble(inst->VRegA_12x(), shadow_frame.GetVRegFloat(inst->VRegB_12x()));
1546 ADVANCE(1);
1547 HANDLE_INSTRUCTION_END();
1548
1549 HANDLE_INSTRUCTION_START(DOUBLE_TO_INT) {
1550 double val = shadow_frame.GetVRegDouble(inst->VRegB_12x());
1551 int32_t result;
1552 if (val != val) {
1553 result = 0;
1554 } else if (val > static_cast<double>(kMaxInt)) {
1555 result = kMaxInt;
1556 } else if (val < static_cast<double>(kMinInt)) {
1557 result = kMinInt;
1558 } else {
1559 result = val;
1560 }
1561 shadow_frame.SetVReg(inst->VRegA_12x(), result);
1562 ADVANCE(1);
1563 }
1564 HANDLE_INSTRUCTION_END();
1565
1566 HANDLE_INSTRUCTION_START(DOUBLE_TO_LONG) {
1567 double val = shadow_frame.GetVRegDouble(inst->VRegB_12x());
1568 int64_t result;
1569 if (val != val) {
1570 result = 0;
1571 } else if (val > static_cast<double>(kMaxLong)) {
1572 result = kMaxLong;
1573 } else if (val < static_cast<double>(kMinLong)) {
1574 result = kMinLong;
1575 } else {
1576 result = val;
1577 }
1578 shadow_frame.SetVRegLong(inst->VRegA_12x(), result);
1579 ADVANCE(1);
1580 }
1581 HANDLE_INSTRUCTION_END();
1582
1583 HANDLE_INSTRUCTION_START(DOUBLE_TO_FLOAT)
1584 shadow_frame.SetVRegFloat(inst->VRegA_12x(), shadow_frame.GetVRegDouble(inst->VRegB_12x()));
1585 ADVANCE(1);
1586 HANDLE_INSTRUCTION_END();
1587
1588 HANDLE_INSTRUCTION_START(INT_TO_BYTE)
1589 shadow_frame.SetVReg(inst->VRegA_12x(),
1590 static_cast<int8_t>(shadow_frame.GetVReg(inst->VRegB_12x())));
1591 ADVANCE(1);
1592 HANDLE_INSTRUCTION_END();
1593
1594 HANDLE_INSTRUCTION_START(INT_TO_CHAR)
1595 shadow_frame.SetVReg(inst->VRegA_12x(),
1596 static_cast<uint16_t>(shadow_frame.GetVReg(inst->VRegB_12x())));
1597 ADVANCE(1);
1598 HANDLE_INSTRUCTION_END();
1599
1600 HANDLE_INSTRUCTION_START(INT_TO_SHORT)
1601 shadow_frame.SetVReg(inst->VRegA_12x(),
1602 static_cast<int16_t>(shadow_frame.GetVReg(inst->VRegB_12x())));
1603 ADVANCE(1);
1604 HANDLE_INSTRUCTION_END();
1605
1606 HANDLE_INSTRUCTION_START(ADD_INT)
1607 shadow_frame.SetVReg(inst->VRegA_23x(),
1608 shadow_frame.GetVReg(inst->VRegB_23x()) +
1609 shadow_frame.GetVReg(inst->VRegC_23x()));
1610 ADVANCE(2);
1611 HANDLE_INSTRUCTION_END();
1612
1613 HANDLE_INSTRUCTION_START(SUB_INT)
1614 shadow_frame.SetVReg(inst->VRegA_23x(),
1615 shadow_frame.GetVReg(inst->VRegB_23x()) -
1616 shadow_frame.GetVReg(inst->VRegC_23x()));
1617 ADVANCE(2);
1618 HANDLE_INSTRUCTION_END();
1619
1620 HANDLE_INSTRUCTION_START(MUL_INT)
1621 shadow_frame.SetVReg(inst->VRegA_23x(),
1622 shadow_frame.GetVReg(inst->VRegB_23x()) *
1623 shadow_frame.GetVReg(inst->VRegC_23x()));
1624 ADVANCE(2);
1625 HANDLE_INSTRUCTION_END();
1626
1627 HANDLE_INSTRUCTION_START(DIV_INT) {
1628 bool success = DoIntDivide(shadow_frame, inst->VRegA_23x(),
1629 shadow_frame.GetVReg(inst->VRegB_23x()),
1630 shadow_frame.GetVReg(inst->VRegC_23x()));
1631 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1632 }
1633 HANDLE_INSTRUCTION_END();
1634
1635 HANDLE_INSTRUCTION_START(REM_INT) {
1636 bool success = DoIntRemainder(shadow_frame, inst->VRegA_23x(),
1637 shadow_frame.GetVReg(inst->VRegB_23x()),
1638 shadow_frame.GetVReg(inst->VRegC_23x()));
1639 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1640 }
1641 HANDLE_INSTRUCTION_END();
1642
1643 HANDLE_INSTRUCTION_START(SHL_INT)
1644 shadow_frame.SetVReg(inst->VRegA_23x(),
1645 shadow_frame.GetVReg(inst->VRegB_23x()) <<
1646 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x1f));
1647 ADVANCE(2);
1648 HANDLE_INSTRUCTION_END();
1649
1650 HANDLE_INSTRUCTION_START(SHR_INT)
1651 shadow_frame.SetVReg(inst->VRegA_23x(),
1652 shadow_frame.GetVReg(inst->VRegB_23x()) >>
1653 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x1f));
1654 ADVANCE(2);
1655 HANDLE_INSTRUCTION_END();
1656
1657 HANDLE_INSTRUCTION_START(USHR_INT)
1658 shadow_frame.SetVReg(inst->VRegA_23x(),
1659 static_cast<uint32_t>(shadow_frame.GetVReg(inst->VRegB_23x())) >>
1660 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x1f));
1661 ADVANCE(2);
1662 HANDLE_INSTRUCTION_END();
1663
1664 HANDLE_INSTRUCTION_START(AND_INT)
1665 shadow_frame.SetVReg(inst->VRegA_23x(),
1666 shadow_frame.GetVReg(inst->VRegB_23x()) &
1667 shadow_frame.GetVReg(inst->VRegC_23x()));
1668 ADVANCE(2);
1669 HANDLE_INSTRUCTION_END();
1670
1671 HANDLE_INSTRUCTION_START(OR_INT)
1672 shadow_frame.SetVReg(inst->VRegA_23x(),
1673 shadow_frame.GetVReg(inst->VRegB_23x()) |
1674 shadow_frame.GetVReg(inst->VRegC_23x()));
1675 ADVANCE(2);
1676 HANDLE_INSTRUCTION_END();
1677
1678 HANDLE_INSTRUCTION_START(XOR_INT)
1679 shadow_frame.SetVReg(inst->VRegA_23x(),
1680 shadow_frame.GetVReg(inst->VRegB_23x()) ^
1681 shadow_frame.GetVReg(inst->VRegC_23x()));
1682 ADVANCE(2);
1683 HANDLE_INSTRUCTION_END();
1684
1685 HANDLE_INSTRUCTION_START(ADD_LONG)
1686 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1687 shadow_frame.GetVRegLong(inst->VRegB_23x()) +
1688 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1689 ADVANCE(2);
1690 HANDLE_INSTRUCTION_END();
1691
1692 HANDLE_INSTRUCTION_START(SUB_LONG)
1693 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1694 shadow_frame.GetVRegLong(inst->VRegB_23x()) -
1695 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1696 ADVANCE(2);
1697 HANDLE_INSTRUCTION_END();
1698
1699 HANDLE_INSTRUCTION_START(MUL_LONG)
1700 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1701 shadow_frame.GetVRegLong(inst->VRegB_23x()) *
1702 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1703 ADVANCE(2);
1704 HANDLE_INSTRUCTION_END();
1705
1706 HANDLE_INSTRUCTION_START(DIV_LONG) {
1707 bool success = DoLongDivide(shadow_frame, inst->VRegA_23x(),
1708 shadow_frame.GetVRegLong(inst->VRegB_23x()),
1709 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1710 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1711 }
1712 HANDLE_INSTRUCTION_END();
1713
1714 HANDLE_INSTRUCTION_START(REM_LONG) {
1715 bool success = DoLongRemainder(shadow_frame, inst->VRegA_23x(),
1716 shadow_frame.GetVRegLong(inst->VRegB_23x()),
1717 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1718 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
1719 }
1720 HANDLE_INSTRUCTION_END();
1721
1722 HANDLE_INSTRUCTION_START(AND_LONG)
1723 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1724 shadow_frame.GetVRegLong(inst->VRegB_23x()) &
1725 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1726 ADVANCE(2);
1727 HANDLE_INSTRUCTION_END();
1728
1729 HANDLE_INSTRUCTION_START(OR_LONG)
1730 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1731 shadow_frame.GetVRegLong(inst->VRegB_23x()) |
1732 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1733 ADVANCE(2);
1734 HANDLE_INSTRUCTION_END();
1735
1736 HANDLE_INSTRUCTION_START(XOR_LONG)
1737 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1738 shadow_frame.GetVRegLong(inst->VRegB_23x()) ^
1739 shadow_frame.GetVRegLong(inst->VRegC_23x()));
1740 ADVANCE(2);
1741 HANDLE_INSTRUCTION_END();
1742
1743 HANDLE_INSTRUCTION_START(SHL_LONG)
1744 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1745 shadow_frame.GetVRegLong(inst->VRegB_23x()) <<
1746 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x3f));
1747 ADVANCE(2);
1748 HANDLE_INSTRUCTION_END();
1749
1750 HANDLE_INSTRUCTION_START(SHR_LONG)
1751 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1752 shadow_frame.GetVRegLong(inst->VRegB_23x()) >>
1753 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x3f));
1754 ADVANCE(2);
1755 HANDLE_INSTRUCTION_END();
1756
1757 HANDLE_INSTRUCTION_START(USHR_LONG)
1758 shadow_frame.SetVRegLong(inst->VRegA_23x(),
1759 static_cast<uint64_t>(shadow_frame.GetVRegLong(inst->VRegB_23x())) >>
1760 (shadow_frame.GetVReg(inst->VRegC_23x()) & 0x3f));
1761 ADVANCE(2);
1762 HANDLE_INSTRUCTION_END();
1763
1764 HANDLE_INSTRUCTION_START(ADD_FLOAT)
1765 shadow_frame.SetVRegFloat(inst->VRegA_23x(),
1766 shadow_frame.GetVRegFloat(inst->VRegB_23x()) +
1767 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1768 ADVANCE(2);
1769 HANDLE_INSTRUCTION_END();
1770
1771 HANDLE_INSTRUCTION_START(SUB_FLOAT)
1772 shadow_frame.SetVRegFloat(inst->VRegA_23x(),
1773 shadow_frame.GetVRegFloat(inst->VRegB_23x()) -
1774 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1775 ADVANCE(2);
1776 HANDLE_INSTRUCTION_END();
1777
1778 HANDLE_INSTRUCTION_START(MUL_FLOAT)
1779 shadow_frame.SetVRegFloat(inst->VRegA_23x(),
1780 shadow_frame.GetVRegFloat(inst->VRegB_23x()) *
1781 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1782 ADVANCE(2);
1783 HANDLE_INSTRUCTION_END();
1784
1785 HANDLE_INSTRUCTION_START(DIV_FLOAT)
1786 shadow_frame.SetVRegFloat(inst->VRegA_23x(),
1787 shadow_frame.GetVRegFloat(inst->VRegB_23x()) /
1788 shadow_frame.GetVRegFloat(inst->VRegC_23x()));
1789 ADVANCE(2);
1790 HANDLE_INSTRUCTION_END();
1791
1792 HANDLE_INSTRUCTION_START(REM_FLOAT)
1793 shadow_frame.SetVRegFloat(inst->VRegA_23x(),
1794 fmodf(shadow_frame.GetVRegFloat(inst->VRegB_23x()),
1795 shadow_frame.GetVRegFloat(inst->VRegC_23x())));
1796 ADVANCE(2);
1797 HANDLE_INSTRUCTION_END();
1798
1799 HANDLE_INSTRUCTION_START(ADD_DOUBLE)
1800 shadow_frame.SetVRegDouble(inst->VRegA_23x(),
1801 shadow_frame.GetVRegDouble(inst->VRegB_23x()) +
1802 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1803 ADVANCE(2);
1804 HANDLE_INSTRUCTION_END();
1805
1806 HANDLE_INSTRUCTION_START(SUB_DOUBLE)
1807 shadow_frame.SetVRegDouble(inst->VRegA_23x(),
1808 shadow_frame.GetVRegDouble(inst->VRegB_23x()) -
1809 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1810 ADVANCE(2);
1811 HANDLE_INSTRUCTION_END();
1812
1813 HANDLE_INSTRUCTION_START(MUL_DOUBLE)
1814 shadow_frame.SetVRegDouble(inst->VRegA_23x(),
1815 shadow_frame.GetVRegDouble(inst->VRegB_23x()) *
1816 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1817 ADVANCE(2);
1818 HANDLE_INSTRUCTION_END();
1819
1820 HANDLE_INSTRUCTION_START(DIV_DOUBLE)
1821 shadow_frame.SetVRegDouble(inst->VRegA_23x(),
1822 shadow_frame.GetVRegDouble(inst->VRegB_23x()) /
1823 shadow_frame.GetVRegDouble(inst->VRegC_23x()));
1824 ADVANCE(2);
1825 HANDLE_INSTRUCTION_END();
1826
1827 HANDLE_INSTRUCTION_START(REM_DOUBLE)
1828 shadow_frame.SetVRegDouble(inst->VRegA_23x(),
1829 fmod(shadow_frame.GetVRegDouble(inst->VRegB_23x()),
1830 shadow_frame.GetVRegDouble(inst->VRegC_23x())));
1831 ADVANCE(2);
1832 HANDLE_INSTRUCTION_END();
1833
1834 HANDLE_INSTRUCTION_START(ADD_INT_2ADDR) {
1835 uint32_t vregA = inst->VRegA_12x();
1836 shadow_frame.SetVReg(vregA,
1837 shadow_frame.GetVReg(vregA) +
1838 shadow_frame.GetVReg(inst->VRegB_12x()));
1839 ADVANCE(1);
1840 }
1841 HANDLE_INSTRUCTION_END();
1842
1843 HANDLE_INSTRUCTION_START(SUB_INT_2ADDR) {
1844 uint32_t vregA = inst->VRegA_12x();
1845 shadow_frame.SetVReg(vregA,
1846 shadow_frame.GetVReg(vregA) -
1847 shadow_frame.GetVReg(inst->VRegB_12x()));
1848 ADVANCE(1);
1849 }
1850 HANDLE_INSTRUCTION_END();
1851
1852 HANDLE_INSTRUCTION_START(MUL_INT_2ADDR) {
1853 uint32_t vregA = inst->VRegA_12x();
1854 shadow_frame.SetVReg(vregA,
1855 shadow_frame.GetVReg(vregA) *
1856 shadow_frame.GetVReg(inst->VRegB_12x()));
1857 ADVANCE(1);
1858 }
1859 HANDLE_INSTRUCTION_END();
1860
1861 HANDLE_INSTRUCTION_START(DIV_INT_2ADDR) {
1862 uint32_t vregA = inst->VRegA_12x();
1863 bool success = DoIntDivide(shadow_frame, vregA, shadow_frame.GetVReg(vregA),
1864 shadow_frame.GetVReg(inst->VRegB_12x()));
1865 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1866 }
1867 HANDLE_INSTRUCTION_END();
1868
1869 HANDLE_INSTRUCTION_START(REM_INT_2ADDR) {
1870 uint32_t vregA = inst->VRegA_12x();
1871 bool success = DoIntRemainder(shadow_frame, vregA, shadow_frame.GetVReg(vregA),
1872 shadow_frame.GetVReg(inst->VRegB_12x()));
1873 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1874 }
1875 HANDLE_INSTRUCTION_END();
1876
1877 HANDLE_INSTRUCTION_START(SHL_INT_2ADDR) {
1878 uint32_t vregA = inst->VRegA_12x();
1879 shadow_frame.SetVReg(vregA,
1880 shadow_frame.GetVReg(vregA) <<
1881 (shadow_frame.GetVReg(inst->VRegB_12x()) & 0x1f));
1882 ADVANCE(1);
1883 }
1884 HANDLE_INSTRUCTION_END();
1885
1886 HANDLE_INSTRUCTION_START(SHR_INT_2ADDR) {
1887 uint32_t vregA = inst->VRegA_12x();
1888 shadow_frame.SetVReg(vregA,
1889 shadow_frame.GetVReg(vregA) >>
1890 (shadow_frame.GetVReg(inst->VRegB_12x()) & 0x1f));
1891 ADVANCE(1);
1892 }
1893 HANDLE_INSTRUCTION_END();
1894
1895 HANDLE_INSTRUCTION_START(USHR_INT_2ADDR) {
1896 uint32_t vregA = inst->VRegA_12x();
1897 shadow_frame.SetVReg(vregA,
1898 static_cast<uint32_t>(shadow_frame.GetVReg(vregA)) >>
1899 (shadow_frame.GetVReg(inst->VRegB_12x()) & 0x1f));
1900 ADVANCE(1);
1901 }
1902 HANDLE_INSTRUCTION_END();
1903
1904 HANDLE_INSTRUCTION_START(AND_INT_2ADDR) {
1905 uint32_t vregA = inst->VRegA_12x();
1906 shadow_frame.SetVReg(vregA,
1907 shadow_frame.GetVReg(vregA) &
1908 shadow_frame.GetVReg(inst->VRegB_12x()));
1909 ADVANCE(1);
1910 }
1911 HANDLE_INSTRUCTION_END();
1912
1913 HANDLE_INSTRUCTION_START(OR_INT_2ADDR) {
1914 uint32_t vregA = inst->VRegA_12x();
1915 shadow_frame.SetVReg(vregA,
1916 shadow_frame.GetVReg(vregA) |
1917 shadow_frame.GetVReg(inst->VRegB_12x()));
1918 ADVANCE(1);
1919 }
1920 HANDLE_INSTRUCTION_END();
1921
1922 HANDLE_INSTRUCTION_START(XOR_INT_2ADDR) {
1923 uint32_t vregA = inst->VRegA_12x();
1924 shadow_frame.SetVReg(vregA,
1925 shadow_frame.GetVReg(vregA) ^
1926 shadow_frame.GetVReg(inst->VRegB_12x()));
1927 ADVANCE(1);
1928 }
1929 HANDLE_INSTRUCTION_END();
1930
1931 HANDLE_INSTRUCTION_START(ADD_LONG_2ADDR) {
1932 uint32_t vregA = inst->VRegA_12x();
1933 shadow_frame.SetVRegLong(vregA,
1934 shadow_frame.GetVRegLong(vregA) +
1935 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1936 ADVANCE(1);
1937 }
1938 HANDLE_INSTRUCTION_END();
1939
1940 HANDLE_INSTRUCTION_START(SUB_LONG_2ADDR) {
1941 uint32_t vregA = inst->VRegA_12x();
1942 shadow_frame.SetVRegLong(vregA,
1943 shadow_frame.GetVRegLong(vregA) -
1944 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1945 ADVANCE(1);
1946 }
1947 HANDLE_INSTRUCTION_END();
1948
1949 HANDLE_INSTRUCTION_START(MUL_LONG_2ADDR) {
1950 uint32_t vregA = inst->VRegA_12x();
1951 shadow_frame.SetVRegLong(vregA,
1952 shadow_frame.GetVRegLong(vregA) *
1953 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1954 ADVANCE(1);
1955 }
1956 HANDLE_INSTRUCTION_END();
1957
1958 HANDLE_INSTRUCTION_START(DIV_LONG_2ADDR) {
1959 uint32_t vregA = inst->VRegA_12x();
1960 bool success = DoLongDivide(shadow_frame, vregA, shadow_frame.GetVRegLong(vregA),
1961 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1962 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1963 }
1964 HANDLE_INSTRUCTION_END();
1965
1966 HANDLE_INSTRUCTION_START(REM_LONG_2ADDR) {
1967 uint32_t vregA = inst->VRegA_12x();
1968 bool success = DoLongRemainder(shadow_frame, vregA, shadow_frame.GetVRegLong(vregA),
1969 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1970 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 1);
1971 }
1972 HANDLE_INSTRUCTION_END();
1973
1974 HANDLE_INSTRUCTION_START(AND_LONG_2ADDR) {
1975 uint32_t vregA = inst->VRegA_12x();
1976 shadow_frame.SetVRegLong(vregA,
1977 shadow_frame.GetVRegLong(vregA) &
1978 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1979 ADVANCE(1);
1980 }
1981 HANDLE_INSTRUCTION_END();
1982
1983 HANDLE_INSTRUCTION_START(OR_LONG_2ADDR) {
1984 uint32_t vregA = inst->VRegA_12x();
1985 shadow_frame.SetVRegLong(vregA,
1986 shadow_frame.GetVRegLong(vregA) |
1987 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1988 ADVANCE(1);
1989 }
1990 HANDLE_INSTRUCTION_END();
1991
1992 HANDLE_INSTRUCTION_START(XOR_LONG_2ADDR) {
1993 uint32_t vregA = inst->VRegA_12x();
1994 shadow_frame.SetVRegLong(vregA,
1995 shadow_frame.GetVRegLong(vregA) ^
1996 shadow_frame.GetVRegLong(inst->VRegB_12x()));
1997 ADVANCE(1);
1998 }
1999 HANDLE_INSTRUCTION_END();
2000
2001 HANDLE_INSTRUCTION_START(SHL_LONG_2ADDR) {
2002 uint32_t vregA = inst->VRegA_12x();
2003 shadow_frame.SetVRegLong(vregA,
2004 shadow_frame.GetVRegLong(vregA) <<
2005 (shadow_frame.GetVReg(inst->VRegB_12x()) & 0x3f));
2006 ADVANCE(1);
2007 }
2008 HANDLE_INSTRUCTION_END();
2009
2010 HANDLE_INSTRUCTION_START(SHR_LONG_2ADDR) {
2011 uint32_t vregA = inst->VRegA_12x();
2012 shadow_frame.SetVRegLong(vregA,
2013 shadow_frame.GetVRegLong(vregA) >>
2014 (shadow_frame.GetVReg(inst->VRegB_12x()) & 0x3f));
2015 ADVANCE(1);
2016 }
2017 HANDLE_INSTRUCTION_END();
2018
2019 HANDLE_INSTRUCTION_START(USHR_LONG_2ADDR) {
2020 uint32_t vregA = inst->VRegA_12x();
2021 shadow_frame.SetVRegLong(vregA,
2022 static_cast<uint64_t>(shadow_frame.GetVRegLong(vregA)) >>
2023 (shadow_frame.GetVReg(inst->VRegB_12x()) & 0x3f));
2024 ADVANCE(1);
2025 }
2026 HANDLE_INSTRUCTION_END();
2027
2028 HANDLE_INSTRUCTION_START(ADD_FLOAT_2ADDR) {
2029 uint32_t vregA = inst->VRegA_12x();
2030 shadow_frame.SetVRegFloat(vregA,
2031 shadow_frame.GetVRegFloat(vregA) +
2032 shadow_frame.GetVRegFloat(inst->VRegB_12x()));
2033 ADVANCE(1);
2034 }
2035 HANDLE_INSTRUCTION_END();
2036
2037 HANDLE_INSTRUCTION_START(SUB_FLOAT_2ADDR) {
2038 uint32_t vregA = inst->VRegA_12x();
2039 shadow_frame.SetVRegFloat(vregA,
2040 shadow_frame.GetVRegFloat(vregA) -
2041 shadow_frame.GetVRegFloat(inst->VRegB_12x()));
2042 ADVANCE(1);
2043 }
2044 HANDLE_INSTRUCTION_END();
2045
2046 HANDLE_INSTRUCTION_START(MUL_FLOAT_2ADDR) {
2047 uint32_t vregA = inst->VRegA_12x();
2048 shadow_frame.SetVRegFloat(vregA,
2049 shadow_frame.GetVRegFloat(vregA) *
2050 shadow_frame.GetVRegFloat(inst->VRegB_12x()));
2051 ADVANCE(1);
2052 }
2053 HANDLE_INSTRUCTION_END();
2054
2055 HANDLE_INSTRUCTION_START(DIV_FLOAT_2ADDR) {
2056 uint32_t vregA = inst->VRegA_12x();
2057 shadow_frame.SetVRegFloat(vregA,
2058 shadow_frame.GetVRegFloat(vregA) /
2059 shadow_frame.GetVRegFloat(inst->VRegB_12x()));
2060 ADVANCE(1);
2061 }
2062 HANDLE_INSTRUCTION_END();
2063
2064 HANDLE_INSTRUCTION_START(REM_FLOAT_2ADDR) {
2065 uint32_t vregA = inst->VRegA_12x();
2066 shadow_frame.SetVRegFloat(vregA,
2067 fmodf(shadow_frame.GetVRegFloat(vregA),
2068 shadow_frame.GetVRegFloat(inst->VRegB_12x())));
2069 ADVANCE(1);
2070 }
2071 HANDLE_INSTRUCTION_END();
2072
2073 HANDLE_INSTRUCTION_START(ADD_DOUBLE_2ADDR) {
2074 uint32_t vregA = inst->VRegA_12x();
2075 shadow_frame.SetVRegDouble(vregA,
2076 shadow_frame.GetVRegDouble(vregA) +
2077 shadow_frame.GetVRegDouble(inst->VRegB_12x()));
2078 ADVANCE(1);
2079 }
2080 HANDLE_INSTRUCTION_END();
2081
2082 HANDLE_INSTRUCTION_START(SUB_DOUBLE_2ADDR) {
2083 uint32_t vregA = inst->VRegA_12x();
2084 shadow_frame.SetVRegDouble(vregA,
2085 shadow_frame.GetVRegDouble(vregA) -
2086 shadow_frame.GetVRegDouble(inst->VRegB_12x()));
2087 ADVANCE(1);
2088 }
2089 HANDLE_INSTRUCTION_END();
2090
2091 HANDLE_INSTRUCTION_START(MUL_DOUBLE_2ADDR) {
2092 uint32_t vregA = inst->VRegA_12x();
2093 shadow_frame.SetVRegDouble(vregA,
2094 shadow_frame.GetVRegDouble(vregA) *
2095 shadow_frame.GetVRegDouble(inst->VRegB_12x()));
2096 ADVANCE(1);
2097 }
2098 HANDLE_INSTRUCTION_END();
2099
2100 HANDLE_INSTRUCTION_START(DIV_DOUBLE_2ADDR) {
2101 uint32_t vregA = inst->VRegA_12x();
2102 shadow_frame.SetVRegDouble(vregA,
2103 shadow_frame.GetVRegDouble(vregA) /
2104 shadow_frame.GetVRegDouble(inst->VRegB_12x()));
2105 ADVANCE(1);
2106 }
2107 HANDLE_INSTRUCTION_END();
2108
2109 HANDLE_INSTRUCTION_START(REM_DOUBLE_2ADDR) {
2110 uint32_t vregA = inst->VRegA_12x();
2111 shadow_frame.SetVRegDouble(vregA,
2112 fmod(shadow_frame.GetVRegDouble(vregA),
2113 shadow_frame.GetVRegDouble(inst->VRegB_12x())));
2114 ADVANCE(1);
2115 }
2116 HANDLE_INSTRUCTION_END();
2117
2118 HANDLE_INSTRUCTION_START(ADD_INT_LIT16)
2119 shadow_frame.SetVReg(inst->VRegA_22s(),
2120 shadow_frame.GetVReg(inst->VRegB_22s()) +
2121 inst->VRegC_22s());
2122 ADVANCE(2);
2123 HANDLE_INSTRUCTION_END();
2124
2125 HANDLE_INSTRUCTION_START(RSUB_INT)
2126 shadow_frame.SetVReg(inst->VRegA_22s(),
2127 inst->VRegC_22s() -
2128 shadow_frame.GetVReg(inst->VRegB_22s()));
2129 ADVANCE(2);
2130 HANDLE_INSTRUCTION_END();
2131
2132 HANDLE_INSTRUCTION_START(MUL_INT_LIT16)
2133 shadow_frame.SetVReg(inst->VRegA_22s(),
2134 shadow_frame.GetVReg(inst->VRegB_22s()) *
2135 inst->VRegC_22s());
2136 ADVANCE(2);
2137 HANDLE_INSTRUCTION_END();
2138
2139 HANDLE_INSTRUCTION_START(DIV_INT_LIT16) {
2140 bool success = DoIntDivide(shadow_frame, inst->VRegA_22s(),
2141 shadow_frame.GetVReg(inst->VRegB_22s()), inst->VRegC_22s());
2142 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2143 }
2144 HANDLE_INSTRUCTION_END();
2145
2146 HANDLE_INSTRUCTION_START(REM_INT_LIT16) {
2147 bool success = DoIntRemainder(shadow_frame, inst->VRegA_22s(),
2148 shadow_frame.GetVReg(inst->VRegB_22s()), inst->VRegC_22s());
2149 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2150 }
2151 HANDLE_INSTRUCTION_END();
2152
2153 HANDLE_INSTRUCTION_START(AND_INT_LIT16)
2154 shadow_frame.SetVReg(inst->VRegA_22s(),
2155 shadow_frame.GetVReg(inst->VRegB_22s()) &
2156 inst->VRegC_22s());
2157 ADVANCE(2);
2158 HANDLE_INSTRUCTION_END();
2159
2160 HANDLE_INSTRUCTION_START(OR_INT_LIT16)
2161 shadow_frame.SetVReg(inst->VRegA_22s(),
2162 shadow_frame.GetVReg(inst->VRegB_22s()) |
2163 inst->VRegC_22s());
2164 ADVANCE(2);
2165 HANDLE_INSTRUCTION_END();
2166
2167 HANDLE_INSTRUCTION_START(XOR_INT_LIT16)
2168 shadow_frame.SetVReg(inst->VRegA_22s(),
2169 shadow_frame.GetVReg(inst->VRegB_22s()) ^
2170 inst->VRegC_22s());
2171 ADVANCE(2);
2172 HANDLE_INSTRUCTION_END();
2173
2174 HANDLE_INSTRUCTION_START(ADD_INT_LIT8)
2175 shadow_frame.SetVReg(inst->VRegA_22b(),
2176 shadow_frame.GetVReg(inst->VRegB_22b()) +
2177 inst->VRegC_22b());
2178 ADVANCE(2);
2179 HANDLE_INSTRUCTION_END();
2180
2181 HANDLE_INSTRUCTION_START(RSUB_INT_LIT8)
2182 shadow_frame.SetVReg(inst->VRegA_22b(),
2183 inst->VRegC_22b() -
2184 shadow_frame.GetVReg(inst->VRegB_22b()));
2185 ADVANCE(2);
2186 HANDLE_INSTRUCTION_END();
2187
2188 HANDLE_INSTRUCTION_START(MUL_INT_LIT8)
2189 shadow_frame.SetVReg(inst->VRegA_22b(),
2190 shadow_frame.GetVReg(inst->VRegB_22b()) *
2191 inst->VRegC_22b());
2192 ADVANCE(2);
2193 HANDLE_INSTRUCTION_END();
2194
2195 HANDLE_INSTRUCTION_START(DIV_INT_LIT8) {
2196 bool success = DoIntDivide(shadow_frame, inst->VRegA_22b(),
2197 shadow_frame.GetVReg(inst->VRegB_22b()), inst->VRegC_22b());
2198 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2199 }
2200 HANDLE_INSTRUCTION_END();
2201
2202 HANDLE_INSTRUCTION_START(REM_INT_LIT8) {
2203 bool success = DoIntRemainder(shadow_frame, inst->VRegA_22b(),
2204 shadow_frame.GetVReg(inst->VRegB_22b()), inst->VRegC_22b());
2205 POSSIBLY_HANDLE_PENDING_EXCEPTION(!success, 2);
2206 }
2207 HANDLE_INSTRUCTION_END();
2208
2209 HANDLE_INSTRUCTION_START(AND_INT_LIT8)
2210 shadow_frame.SetVReg(inst->VRegA_22b(),
2211 shadow_frame.GetVReg(inst->VRegB_22b()) &
2212 inst->VRegC_22b());
2213 ADVANCE(2);
2214 HANDLE_INSTRUCTION_END();
2215
2216 HANDLE_INSTRUCTION_START(OR_INT_LIT8)
2217 shadow_frame.SetVReg(inst->VRegA_22b(),
2218 shadow_frame.GetVReg(inst->VRegB_22b()) |
2219 inst->VRegC_22b());
2220 ADVANCE(2);
2221 HANDLE_INSTRUCTION_END();
2222
2223 HANDLE_INSTRUCTION_START(XOR_INT_LIT8)
2224 shadow_frame.SetVReg(inst->VRegA_22b(),
2225 shadow_frame.GetVReg(inst->VRegB_22b()) ^
2226 inst->VRegC_22b());
2227 ADVANCE(2);
2228 HANDLE_INSTRUCTION_END();
2229
2230 HANDLE_INSTRUCTION_START(SHL_INT_LIT8)
2231 shadow_frame.SetVReg(inst->VRegA_22b(),
2232 shadow_frame.GetVReg(inst->VRegB_22b()) <<
2233 (inst->VRegC_22b() & 0x1f));
2234 ADVANCE(2);
2235 HANDLE_INSTRUCTION_END();
2236
2237 HANDLE_INSTRUCTION_START(SHR_INT_LIT8)
2238 shadow_frame.SetVReg(inst->VRegA_22b(),
2239 shadow_frame.GetVReg(inst->VRegB_22b()) >>
2240 (inst->VRegC_22b() & 0x1f));
2241 ADVANCE(2);
2242 HANDLE_INSTRUCTION_END();
2243
2244 HANDLE_INSTRUCTION_START(USHR_INT_LIT8)
2245 shadow_frame.SetVReg(inst->VRegA_22b(),
2246 static_cast<uint32_t>(shadow_frame.GetVReg(inst->VRegB_22b())) >>
2247 (inst->VRegC_22b() & 0x1f));
2248 ADVANCE(2);
2249 HANDLE_INSTRUCTION_END();
2250
2251 HANDLE_INSTRUCTION_START(UNUSED_3E)
2252 UnexpectedOpcode(inst, mh);
2253 HANDLE_INSTRUCTION_END();
2254
2255 HANDLE_INSTRUCTION_START(UNUSED_3F)
2256 UnexpectedOpcode(inst, mh);
2257 HANDLE_INSTRUCTION_END();
2258
2259 HANDLE_INSTRUCTION_START(UNUSED_40)
2260 UnexpectedOpcode(inst, mh);
2261 HANDLE_INSTRUCTION_END();
2262
2263 HANDLE_INSTRUCTION_START(UNUSED_41)
2264 UnexpectedOpcode(inst, mh);
2265 HANDLE_INSTRUCTION_END();
2266
2267 HANDLE_INSTRUCTION_START(UNUSED_42)
2268 UnexpectedOpcode(inst, mh);
2269 HANDLE_INSTRUCTION_END();
2270
2271 HANDLE_INSTRUCTION_START(UNUSED_43)
2272 UnexpectedOpcode(inst, mh);
2273 HANDLE_INSTRUCTION_END();
2274
2275 HANDLE_INSTRUCTION_START(UNUSED_79)
2276 UnexpectedOpcode(inst, mh);
2277 HANDLE_INSTRUCTION_END();
2278
2279 HANDLE_INSTRUCTION_START(UNUSED_7A)
2280 UnexpectedOpcode(inst, mh);
2281 HANDLE_INSTRUCTION_END();
2282
2283 HANDLE_INSTRUCTION_START(UNUSED_EB)
2284 UnexpectedOpcode(inst, mh);
2285 HANDLE_INSTRUCTION_END();
2286
2287 HANDLE_INSTRUCTION_START(UNUSED_EC)
2288 UnexpectedOpcode(inst, mh);
2289 HANDLE_INSTRUCTION_END();
2290
2291 HANDLE_INSTRUCTION_START(UNUSED_ED)
2292 UnexpectedOpcode(inst, mh);
2293 HANDLE_INSTRUCTION_END();
2294
2295 HANDLE_INSTRUCTION_START(UNUSED_EE)
2296 UnexpectedOpcode(inst, mh);
2297 HANDLE_INSTRUCTION_END();
2298
2299 HANDLE_INSTRUCTION_START(UNUSED_EF)
2300 UnexpectedOpcode(inst, mh);
2301 HANDLE_INSTRUCTION_END();
2302
2303 HANDLE_INSTRUCTION_START(UNUSED_F0)
2304 UnexpectedOpcode(inst, mh);
2305 HANDLE_INSTRUCTION_END();
2306
2307 HANDLE_INSTRUCTION_START(UNUSED_F1)
2308 UnexpectedOpcode(inst, mh);
2309 HANDLE_INSTRUCTION_END();
2310
2311 HANDLE_INSTRUCTION_START(UNUSED_F2)
2312 UnexpectedOpcode(inst, mh);
2313 HANDLE_INSTRUCTION_END();
2314
2315 HANDLE_INSTRUCTION_START(UNUSED_F3)
2316 UnexpectedOpcode(inst, mh);
2317 HANDLE_INSTRUCTION_END();
2318
2319 HANDLE_INSTRUCTION_START(UNUSED_F4)
2320 UnexpectedOpcode(inst, mh);
2321 HANDLE_INSTRUCTION_END();
2322
2323 HANDLE_INSTRUCTION_START(UNUSED_F5)
2324 UnexpectedOpcode(inst, mh);
2325 HANDLE_INSTRUCTION_END();
2326
2327 HANDLE_INSTRUCTION_START(UNUSED_F6)
2328 UnexpectedOpcode(inst, mh);
2329 HANDLE_INSTRUCTION_END();
2330
2331 HANDLE_INSTRUCTION_START(UNUSED_F7)
2332 UnexpectedOpcode(inst, mh);
2333 HANDLE_INSTRUCTION_END();
2334
2335 HANDLE_INSTRUCTION_START(UNUSED_F8)
2336 UnexpectedOpcode(inst, mh);
2337 HANDLE_INSTRUCTION_END();
2338
2339 HANDLE_INSTRUCTION_START(UNUSED_F9)
2340 UnexpectedOpcode(inst, mh);
2341 HANDLE_INSTRUCTION_END();
2342
2343 HANDLE_INSTRUCTION_START(UNUSED_FA)
2344 UnexpectedOpcode(inst, mh);
2345 HANDLE_INSTRUCTION_END();
2346
2347 HANDLE_INSTRUCTION_START(UNUSED_FB)
2348 UnexpectedOpcode(inst, mh);
2349 HANDLE_INSTRUCTION_END();
2350
2351 HANDLE_INSTRUCTION_START(UNUSED_FC)
2352 UnexpectedOpcode(inst, mh);
2353 HANDLE_INSTRUCTION_END();
2354
2355 HANDLE_INSTRUCTION_START(UNUSED_FD)
2356 UnexpectedOpcode(inst, mh);
2357 HANDLE_INSTRUCTION_END();
2358
2359 HANDLE_INSTRUCTION_START(UNUSED_FE)
2360 UnexpectedOpcode(inst, mh);
2361 HANDLE_INSTRUCTION_END();
2362
2363 HANDLE_INSTRUCTION_START(UNUSED_FF)
2364 UnexpectedOpcode(inst, mh);
2365 HANDLE_INSTRUCTION_END();
2366
2367 exception_pending_label: {
2368 CHECK(self->IsExceptionPending());
Sebastien Hertz1eda2262013-09-09 16:53:14 +02002369 if (UNLIKELY(self->TestAllFlags())) {
2370 CheckSuspend(self);
2371 }
Sebastien Hertz8ece0502013-08-07 11:26:41 +02002372 uint32_t found_dex_pc = FindNextInstructionFollowingException(self, shadow_frame, dex_pc,
2373 this_object_ref,
2374 instrumentation);
2375 if (found_dex_pc == DexFile::kDexNoIndex) {
2376 return JValue(); /* Handled in caller. */
2377 } else {
2378 int32_t displacement = static_cast<int32_t>(found_dex_pc) - static_cast<int32_t>(dex_pc);
2379 ADVANCE(displacement);
2380 }
2381 }
2382
2383 // Create alternative instruction handlers dedicated to instrumentation.
2384#define INSTRUMENTATION_INSTRUCTION_HANDLER(o, code, n, f, r, i, a, v) \
2385 instrumentation_op_##code: { \
2386 instrumentation->DexPcMovedEvent(self, this_object_ref.get(), \
2387 shadow_frame.GetMethod(), dex_pc); \
2388 goto *handlersTable[Instruction::code]; \
2389 }
2390#include "dex_instruction_list.h"
2391 DEX_INSTRUCTION_LIST(INSTRUMENTATION_INSTRUCTION_HANDLER)
2392#undef DEX_INSTRUCTION_LIST
2393#undef INSTRUMENTATION_INSTRUCTION_HANDLER
2394} // NOLINT(readability/fn_size)
2395
2396// Explicit definitions of ExecuteGotoImpl.
2397template JValue ExecuteGotoImpl<true>(Thread* self, MethodHelper& mh,
2398 const DexFile::CodeItem* code_item,
2399 ShadowFrame& shadow_frame, JValue result_register);
2400template JValue ExecuteGotoImpl<false>(Thread* self, MethodHelper& mh,
2401 const DexFile::CodeItem* code_item,
2402 ShadowFrame& shadow_frame, JValue result_register);
2403
2404} // namespace interpreter
2405} // namespace art