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