1 /* 2 * Copyright (C) 2016 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 "instruction_builder.h" 18 19 #include "art_method-inl.h" 20 #include "base/arena_bit_vector.h" 21 #include "base/bit_vector-inl.h" 22 #include "base/logging.h" 23 #include "block_builder.h" 24 #include "class_linker-inl.h" 25 #include "code_generator.h" 26 #include "data_type-inl.h" 27 #include "dex/bytecode_utils.h" 28 #include "dex/dex_instruction-inl.h" 29 #include "driver/dex_compilation_unit.h" 30 #include "driver/compiler_options.h" 31 #include "imtable-inl.h" 32 #include "mirror/dex_cache.h" 33 #include "oat_file.h" 34 #include "optimizing_compiler_stats.h" 35 #include "quicken_info.h" 36 #include "scoped_thread_state_change-inl.h" 37 #include "sharpening.h" 38 #include "ssa_builder.h" 39 #include "well_known_classes.h" 40 41 namespace art { 42 43 HInstructionBuilder::HInstructionBuilder(HGraph* graph, 44 HBasicBlockBuilder* block_builder, 45 SsaBuilder* ssa_builder, 46 const DexFile* dex_file, 47 const CodeItemDebugInfoAccessor& accessor, 48 DataType::Type return_type, 49 const DexCompilationUnit* dex_compilation_unit, 50 const DexCompilationUnit* outer_compilation_unit, 51 CodeGenerator* code_generator, 52 ArrayRef<const uint8_t> interpreter_metadata, 53 OptimizingCompilerStats* compiler_stats, 54 VariableSizedHandleScope* handles, 55 ScopedArenaAllocator* local_allocator) 56 : allocator_(graph->GetAllocator()), 57 graph_(graph), 58 handles_(handles), 59 dex_file_(dex_file), 60 code_item_accessor_(accessor), 61 return_type_(return_type), 62 block_builder_(block_builder), 63 ssa_builder_(ssa_builder), 64 code_generator_(code_generator), 65 dex_compilation_unit_(dex_compilation_unit), 66 outer_compilation_unit_(outer_compilation_unit), 67 quicken_info_(interpreter_metadata), 68 compilation_stats_(compiler_stats), 69 local_allocator_(local_allocator), 70 locals_for_(local_allocator->Adapter(kArenaAllocGraphBuilder)), 71 current_block_(nullptr), 72 current_locals_(nullptr), 73 latest_result_(nullptr), 74 current_this_parameter_(nullptr), 75 loop_headers_(local_allocator->Adapter(kArenaAllocGraphBuilder)), 76 class_cache_(std::less<dex::TypeIndex>(), local_allocator->Adapter(kArenaAllocGraphBuilder)) { 77 loop_headers_.reserve(kDefaultNumberOfLoops); 78 } 79 80 HBasicBlock* HInstructionBuilder::FindBlockStartingAt(uint32_t dex_pc) const { 81 return block_builder_->GetBlockAt(dex_pc); 82 } 83 84 inline ScopedArenaVector<HInstruction*>* HInstructionBuilder::GetLocalsFor(HBasicBlock* block) { 85 ScopedArenaVector<HInstruction*>* locals = &locals_for_[block->GetBlockId()]; 86 const size_t vregs = graph_->GetNumberOfVRegs(); 87 if (locals->size() == vregs) { 88 return locals; 89 } 90 return GetLocalsForWithAllocation(block, locals, vregs); 91 } 92 93 ScopedArenaVector<HInstruction*>* HInstructionBuilder::GetLocalsForWithAllocation( 94 HBasicBlock* block, 95 ScopedArenaVector<HInstruction*>* locals, 96 const size_t vregs) { 97 DCHECK_NE(locals->size(), vregs); 98 locals->resize(vregs, nullptr); 99 if (block->IsCatchBlock()) { 100 // We record incoming inputs of catch phis at throwing instructions and 101 // must therefore eagerly create the phis. Phis for undefined vregs will 102 // be deleted when the first throwing instruction with the vreg undefined 103 // is encountered. Unused phis will be removed by dead phi analysis. 104 for (size_t i = 0; i < vregs; ++i) { 105 // No point in creating the catch phi if it is already undefined at 106 // the first throwing instruction. 107 HInstruction* current_local_value = (*current_locals_)[i]; 108 if (current_local_value != nullptr) { 109 HPhi* phi = new (allocator_) HPhi( 110 allocator_, 111 i, 112 0, 113 current_local_value->GetType()); 114 block->AddPhi(phi); 115 (*locals)[i] = phi; 116 } 117 } 118 } 119 return locals; 120 } 121 122 inline HInstruction* HInstructionBuilder::ValueOfLocalAt(HBasicBlock* block, size_t local) { 123 ScopedArenaVector<HInstruction*>* locals = GetLocalsFor(block); 124 return (*locals)[local]; 125 } 126 127 void HInstructionBuilder::InitializeBlockLocals() { 128 current_locals_ = GetLocalsFor(current_block_); 129 130 if (current_block_->IsCatchBlock()) { 131 // Catch phis were already created and inputs collected from throwing sites. 132 if (kIsDebugBuild) { 133 // Make sure there was at least one throwing instruction which initialized 134 // locals (guaranteed by HGraphBuilder) and that all try blocks have been 135 // visited already (from HTryBoundary scoping and reverse post order). 136 bool catch_block_visited = false; 137 for (HBasicBlock* current : graph_->GetReversePostOrder()) { 138 if (current == current_block_) { 139 catch_block_visited = true; 140 } else if (current->IsTryBlock()) { 141 const HTryBoundary& try_entry = current->GetTryCatchInformation()->GetTryEntry(); 142 if (try_entry.HasExceptionHandler(*current_block_)) { 143 DCHECK(!catch_block_visited) << "Catch block visited before its try block."; 144 } 145 } 146 } 147 DCHECK_EQ(current_locals_->size(), graph_->GetNumberOfVRegs()) 148 << "No instructions throwing into a live catch block."; 149 } 150 } else if (current_block_->IsLoopHeader()) { 151 // If the block is a loop header, we know we only have visited the pre header 152 // because we are visiting in reverse post order. We create phis for all initialized 153 // locals from the pre header. Their inputs will be populated at the end of 154 // the analysis. 155 for (size_t local = 0; local < current_locals_->size(); ++local) { 156 HInstruction* incoming = 157 ValueOfLocalAt(current_block_->GetLoopInformation()->GetPreHeader(), local); 158 if (incoming != nullptr) { 159 HPhi* phi = new (allocator_) HPhi( 160 allocator_, 161 local, 162 0, 163 incoming->GetType()); 164 current_block_->AddPhi(phi); 165 (*current_locals_)[local] = phi; 166 } 167 } 168 169 // Save the loop header so that the last phase of the analysis knows which 170 // blocks need to be updated. 171 loop_headers_.push_back(current_block_); 172 } else if (current_block_->GetPredecessors().size() > 0) { 173 // All predecessors have already been visited because we are visiting in reverse post order. 174 // We merge the values of all locals, creating phis if those values differ. 175 for (size_t local = 0; local < current_locals_->size(); ++local) { 176 bool one_predecessor_has_no_value = false; 177 bool is_different = false; 178 HInstruction* value = ValueOfLocalAt(current_block_->GetPredecessors()[0], local); 179 180 for (HBasicBlock* predecessor : current_block_->GetPredecessors()) { 181 HInstruction* current = ValueOfLocalAt(predecessor, local); 182 if (current == nullptr) { 183 one_predecessor_has_no_value = true; 184 break; 185 } else if (current != value) { 186 is_different = true; 187 } 188 } 189 190 if (one_predecessor_has_no_value) { 191 // If one predecessor has no value for this local, we trust the verifier has 192 // successfully checked that there is a store dominating any read after this block. 193 continue; 194 } 195 196 if (is_different) { 197 HInstruction* first_input = ValueOfLocalAt(current_block_->GetPredecessors()[0], local); 198 HPhi* phi = new (allocator_) HPhi( 199 allocator_, 200 local, 201 current_block_->GetPredecessors().size(), 202 first_input->GetType()); 203 for (size_t i = 0; i < current_block_->GetPredecessors().size(); i++) { 204 HInstruction* pred_value = ValueOfLocalAt(current_block_->GetPredecessors()[i], local); 205 phi->SetRawInputAt(i, pred_value); 206 } 207 current_block_->AddPhi(phi); 208 value = phi; 209 } 210 (*current_locals_)[local] = value; 211 } 212 } 213 } 214 215 void HInstructionBuilder::PropagateLocalsToCatchBlocks() { 216 const HTryBoundary& try_entry = current_block_->GetTryCatchInformation()->GetTryEntry(); 217 for (HBasicBlock* catch_block : try_entry.GetExceptionHandlers()) { 218 ScopedArenaVector<HInstruction*>* handler_locals = GetLocalsFor(catch_block); 219 DCHECK_EQ(handler_locals->size(), current_locals_->size()); 220 for (size_t vreg = 0, e = current_locals_->size(); vreg < e; ++vreg) { 221 HInstruction* handler_value = (*handler_locals)[vreg]; 222 if (handler_value == nullptr) { 223 // Vreg was undefined at a previously encountered throwing instruction 224 // and the catch phi was deleted. Do not record the local value. 225 continue; 226 } 227 DCHECK(handler_value->IsPhi()); 228 229 HInstruction* local_value = (*current_locals_)[vreg]; 230 if (local_value == nullptr) { 231 // This is the first instruction throwing into `catch_block` where 232 // `vreg` is undefined. Delete the catch phi. 233 catch_block->RemovePhi(handler_value->AsPhi()); 234 (*handler_locals)[vreg] = nullptr; 235 } else { 236 // Vreg has been defined at all instructions throwing into `catch_block` 237 // encountered so far. Record the local value in the catch phi. 238 handler_value->AsPhi()->AddInput(local_value); 239 } 240 } 241 } 242 } 243 244 void HInstructionBuilder::AppendInstruction(HInstruction* instruction) { 245 current_block_->AddInstruction(instruction); 246 InitializeInstruction(instruction); 247 } 248 249 void HInstructionBuilder::InsertInstructionAtTop(HInstruction* instruction) { 250 if (current_block_->GetInstructions().IsEmpty()) { 251 current_block_->AddInstruction(instruction); 252 } else { 253 current_block_->InsertInstructionBefore(instruction, current_block_->GetFirstInstruction()); 254 } 255 InitializeInstruction(instruction); 256 } 257 258 void HInstructionBuilder::InitializeInstruction(HInstruction* instruction) { 259 if (instruction->NeedsEnvironment()) { 260 HEnvironment* environment = new (allocator_) HEnvironment( 261 allocator_, 262 current_locals_->size(), 263 graph_->GetArtMethod(), 264 instruction->GetDexPc(), 265 instruction); 266 environment->CopyFrom(ArrayRef<HInstruction* const>(*current_locals_)); 267 instruction->SetRawEnvironment(environment); 268 } 269 } 270 271 HInstruction* HInstructionBuilder::LoadNullCheckedLocal(uint32_t register_index, uint32_t dex_pc) { 272 HInstruction* ref = LoadLocal(register_index, DataType::Type::kReference); 273 if (!ref->CanBeNull()) { 274 return ref; 275 } 276 277 HNullCheck* null_check = new (allocator_) HNullCheck(ref, dex_pc); 278 AppendInstruction(null_check); 279 return null_check; 280 } 281 282 void HInstructionBuilder::SetLoopHeaderPhiInputs() { 283 for (size_t i = loop_headers_.size(); i > 0; --i) { 284 HBasicBlock* block = loop_headers_[i - 1]; 285 for (HInstructionIterator it(block->GetPhis()); !it.Done(); it.Advance()) { 286 HPhi* phi = it.Current()->AsPhi(); 287 size_t vreg = phi->GetRegNumber(); 288 for (HBasicBlock* predecessor : block->GetPredecessors()) { 289 HInstruction* value = ValueOfLocalAt(predecessor, vreg); 290 if (value == nullptr) { 291 // Vreg is undefined at this predecessor. Mark it dead and leave with 292 // fewer inputs than predecessors. SsaChecker will fail if not removed. 293 phi->SetDead(); 294 break; 295 } else { 296 phi->AddInput(value); 297 } 298 } 299 } 300 } 301 } 302 303 static bool IsBlockPopulated(HBasicBlock* block) { 304 if (block->IsLoopHeader()) { 305 // Suspend checks were inserted into loop headers during building of dominator tree. 306 DCHECK(block->GetFirstInstruction()->IsSuspendCheck()); 307 return block->GetFirstInstruction() != block->GetLastInstruction(); 308 } else { 309 return !block->GetInstructions().IsEmpty(); 310 } 311 } 312 313 bool HInstructionBuilder::Build() { 314 DCHECK(code_item_accessor_.HasCodeItem()); 315 locals_for_.resize( 316 graph_->GetBlocks().size(), 317 ScopedArenaVector<HInstruction*>(local_allocator_->Adapter(kArenaAllocGraphBuilder))); 318 319 // Find locations where we want to generate extra stackmaps for native debugging. 320 // This allows us to generate the info only at interesting points (for example, 321 // at start of java statement) rather than before every dex instruction. 322 const bool native_debuggable = code_generator_ != nullptr && 323 code_generator_->GetCompilerOptions().GetNativeDebuggable(); 324 ArenaBitVector* native_debug_info_locations = nullptr; 325 if (native_debuggable) { 326 native_debug_info_locations = FindNativeDebugInfoLocations(); 327 } 328 329 for (HBasicBlock* block : graph_->GetReversePostOrder()) { 330 current_block_ = block; 331 uint32_t block_dex_pc = current_block_->GetDexPc(); 332 333 InitializeBlockLocals(); 334 335 if (current_block_->IsEntryBlock()) { 336 InitializeParameters(); 337 AppendInstruction(new (allocator_) HSuspendCheck(0u)); 338 AppendInstruction(new (allocator_) HGoto(0u)); 339 continue; 340 } else if (current_block_->IsExitBlock()) { 341 AppendInstruction(new (allocator_) HExit()); 342 continue; 343 } else if (current_block_->IsLoopHeader()) { 344 HSuspendCheck* suspend_check = new (allocator_) HSuspendCheck(current_block_->GetDexPc()); 345 current_block_->GetLoopInformation()->SetSuspendCheck(suspend_check); 346 // This is slightly odd because the loop header might not be empty (TryBoundary). 347 // But we're still creating the environment with locals from the top of the block. 348 InsertInstructionAtTop(suspend_check); 349 } 350 351 if (block_dex_pc == kNoDexPc || current_block_ != block_builder_->GetBlockAt(block_dex_pc)) { 352 // Synthetic block that does not need to be populated. 353 DCHECK(IsBlockPopulated(current_block_)); 354 continue; 355 } 356 357 DCHECK(!IsBlockPopulated(current_block_)); 358 359 uint32_t quicken_index = 0; 360 if (CanDecodeQuickenedInfo()) { 361 quicken_index = block_builder_->GetQuickenIndex(block_dex_pc); 362 } 363 364 for (const DexInstructionPcPair& pair : code_item_accessor_.InstructionsFrom(block_dex_pc)) { 365 if (current_block_ == nullptr) { 366 // The previous instruction ended this block. 367 break; 368 } 369 370 const uint32_t dex_pc = pair.DexPc(); 371 if (dex_pc != block_dex_pc && FindBlockStartingAt(dex_pc) != nullptr) { 372 // This dex_pc starts a new basic block. 373 break; 374 } 375 376 if (current_block_->IsTryBlock() && IsThrowingDexInstruction(pair.Inst())) { 377 PropagateLocalsToCatchBlocks(); 378 } 379 380 if (native_debuggable && native_debug_info_locations->IsBitSet(dex_pc)) { 381 AppendInstruction(new (allocator_) HNativeDebugInfo(dex_pc)); 382 } 383 384 if (!ProcessDexInstruction(pair.Inst(), dex_pc, quicken_index)) { 385 return false; 386 } 387 388 if (QuickenInfoTable::NeedsIndexForInstruction(&pair.Inst())) { 389 ++quicken_index; 390 } 391 } 392 393 if (current_block_ != nullptr) { 394 // Branching instructions clear current_block, so we know the last 395 // instruction of the current block is not a branching instruction. 396 // We add an unconditional Goto to the next block. 397 DCHECK_EQ(current_block_->GetSuccessors().size(), 1u); 398 AppendInstruction(new (allocator_) HGoto()); 399 } 400 } 401 402 SetLoopHeaderPhiInputs(); 403 404 return true; 405 } 406 407 void HInstructionBuilder::BuildIntrinsic(ArtMethod* method) { 408 DCHECK(!code_item_accessor_.HasCodeItem()); 409 DCHECK(method->IsIntrinsic()); 410 411 locals_for_.resize( 412 graph_->GetBlocks().size(), 413 ScopedArenaVector<HInstruction*>(local_allocator_->Adapter(kArenaAllocGraphBuilder))); 414 415 // Fill the entry block. Do not add suspend check, we do not want a suspend 416 // check in intrinsics; intrinsic methods are supposed to be fast. 417 current_block_ = graph_->GetEntryBlock(); 418 InitializeBlockLocals(); 419 InitializeParameters(); 420 AppendInstruction(new (allocator_) HGoto(0u)); 421 422 // Fill the body. 423 current_block_ = current_block_->GetSingleSuccessor(); 424 InitializeBlockLocals(); 425 DCHECK(!IsBlockPopulated(current_block_)); 426 427 // Add the invoke and return instruction. Use HInvokeStaticOrDirect even 428 // for methods that would normally use an HInvokeVirtual (sharpen the call). 429 size_t in_vregs = graph_->GetNumberOfInVRegs(); 430 size_t number_of_arguments = 431 in_vregs - std::count(current_locals_->end() - in_vregs, current_locals_->end(), nullptr); 432 uint32_t method_idx = dex_compilation_unit_->GetDexMethodIndex(); 433 MethodReference target_method(dex_file_, method_idx); 434 HInvokeStaticOrDirect::DispatchInfo dispatch_info = { 435 HInvokeStaticOrDirect::MethodLoadKind::kRuntimeCall, 436 HInvokeStaticOrDirect::CodePtrLocation::kCallArtMethod, 437 /* method_load_data= */ 0u 438 }; 439 InvokeType invoke_type = dex_compilation_unit_->IsStatic() ? kStatic : kDirect; 440 HInvokeStaticOrDirect* invoke = new (allocator_) HInvokeStaticOrDirect( 441 allocator_, 442 number_of_arguments, 443 return_type_, 444 kNoDexPc, 445 method_idx, 446 method, 447 dispatch_info, 448 invoke_type, 449 target_method, 450 HInvokeStaticOrDirect::ClinitCheckRequirement::kNone); 451 RangeInstructionOperands operands(graph_->GetNumberOfVRegs() - in_vregs, in_vregs); 452 HandleInvoke(invoke, operands, dex_file_->GetMethodShorty(method_idx), /* is_unresolved= */ false); 453 454 // Add the return instruction. 455 if (return_type_ == DataType::Type::kVoid) { 456 AppendInstruction(new (allocator_) HReturnVoid()); 457 } else { 458 AppendInstruction(new (allocator_) HReturn(invoke)); 459 } 460 461 // Fill the exit block. 462 DCHECK_EQ(current_block_->GetSingleSuccessor(), graph_->GetExitBlock()); 463 current_block_ = graph_->GetExitBlock(); 464 InitializeBlockLocals(); 465 AppendInstruction(new (allocator_) HExit()); 466 } 467 468 ArenaBitVector* HInstructionBuilder::FindNativeDebugInfoLocations() { 469 ArenaBitVector* locations = ArenaBitVector::Create(local_allocator_, 470 code_item_accessor_.InsnsSizeInCodeUnits(), 471 /* expandable= */ false, 472 kArenaAllocGraphBuilder); 473 locations->ClearAllBits(); 474 // The visitor gets called when the line number changes. 475 // In other words, it marks the start of new java statement. 476 code_item_accessor_.DecodeDebugPositionInfo([&](const DexFile::PositionInfo& entry) { 477 locations->SetBit(entry.address_); 478 return false; 479 }); 480 // Instruction-specific tweaks. 481 for (const DexInstructionPcPair& inst : code_item_accessor_) { 482 switch (inst->Opcode()) { 483 case Instruction::MOVE_EXCEPTION: { 484 // Stop in native debugger after the exception has been moved. 485 // The compiler also expects the move at the start of basic block so 486 // we do not want to interfere by inserting native-debug-info before it. 487 locations->ClearBit(inst.DexPc()); 488 DexInstructionIterator next = std::next(DexInstructionIterator(inst)); 489 DCHECK(next.DexPc() != inst.DexPc()); 490 if (next != code_item_accessor_.end()) { 491 locations->SetBit(next.DexPc()); 492 } 493 break; 494 } 495 default: 496 break; 497 } 498 } 499 return locations; 500 } 501 502 HInstruction* HInstructionBuilder::LoadLocal(uint32_t reg_number, DataType::Type type) const { 503 HInstruction* value = (*current_locals_)[reg_number]; 504 DCHECK(value != nullptr); 505 506 // If the operation requests a specific type, we make sure its input is of that type. 507 if (type != value->GetType()) { 508 if (DataType::IsFloatingPointType(type)) { 509 value = ssa_builder_->GetFloatOrDoubleEquivalent(value, type); 510 } else if (type == DataType::Type::kReference) { 511 value = ssa_builder_->GetReferenceTypeEquivalent(value); 512 } 513 DCHECK(value != nullptr); 514 } 515 516 return value; 517 } 518 519 void HInstructionBuilder::UpdateLocal(uint32_t reg_number, HInstruction* stored_value) { 520 DataType::Type stored_type = stored_value->GetType(); 521 DCHECK_NE(stored_type, DataType::Type::kVoid); 522 523 // Storing into vreg `reg_number` may implicitly invalidate the surrounding 524 // registers. Consider the following cases: 525 // (1) Storing a wide value must overwrite previous values in both `reg_number` 526 // and `reg_number+1`. We store `nullptr` in `reg_number+1`. 527 // (2) If vreg `reg_number-1` holds a wide value, writing into `reg_number` 528 // must invalidate it. We store `nullptr` in `reg_number-1`. 529 // Consequently, storing a wide value into the high vreg of another wide value 530 // will invalidate both `reg_number-1` and `reg_number+1`. 531 532 if (reg_number != 0) { 533 HInstruction* local_low = (*current_locals_)[reg_number - 1]; 534 if (local_low != nullptr && DataType::Is64BitType(local_low->GetType())) { 535 // The vreg we are storing into was previously the high vreg of a pair. 536 // We need to invalidate its low vreg. 537 DCHECK((*current_locals_)[reg_number] == nullptr); 538 (*current_locals_)[reg_number - 1] = nullptr; 539 } 540 } 541 542 (*current_locals_)[reg_number] = stored_value; 543 if (DataType::Is64BitType(stored_type)) { 544 // We are storing a pair. Invalidate the instruction in the high vreg. 545 (*current_locals_)[reg_number + 1] = nullptr; 546 } 547 } 548 549 void HInstructionBuilder::InitializeParameters() { 550 DCHECK(current_block_->IsEntryBlock()); 551 552 // outer_compilation_unit_ is null only when unit testing. 553 if (outer_compilation_unit_ == nullptr) { 554 return; 555 } 556 557 const char* shorty = dex_compilation_unit_->GetShorty(); 558 uint16_t number_of_parameters = graph_->GetNumberOfInVRegs(); 559 uint16_t locals_index = graph_->GetNumberOfLocalVRegs(); 560 uint16_t parameter_index = 0; 561 562 const dex::MethodId& referrer_method_id = 563 dex_file_->GetMethodId(dex_compilation_unit_->GetDexMethodIndex()); 564 if (!dex_compilation_unit_->IsStatic()) { 565 // Add the implicit 'this' argument, not expressed in the signature. 566 HParameterValue* parameter = new (allocator_) HParameterValue(*dex_file_, 567 referrer_method_id.class_idx_, 568 parameter_index++, 569 DataType::Type::kReference, 570 /* is_this= */ true); 571 AppendInstruction(parameter); 572 UpdateLocal(locals_index++, parameter); 573 number_of_parameters--; 574 current_this_parameter_ = parameter; 575 } else { 576 DCHECK(current_this_parameter_ == nullptr); 577 } 578 579 const dex::ProtoId& proto = dex_file_->GetMethodPrototype(referrer_method_id); 580 const dex::TypeList* arg_types = dex_file_->GetProtoParameters(proto); 581 for (int i = 0, shorty_pos = 1; i < number_of_parameters; i++) { 582 HParameterValue* parameter = new (allocator_) HParameterValue( 583 *dex_file_, 584 arg_types->GetTypeItem(shorty_pos - 1).type_idx_, 585 parameter_index++, 586 DataType::FromShorty(shorty[shorty_pos]), 587 /* is_this= */ false); 588 ++shorty_pos; 589 AppendInstruction(parameter); 590 // Store the parameter value in the local that the dex code will use 591 // to reference that parameter. 592 UpdateLocal(locals_index++, parameter); 593 if (DataType::Is64BitType(parameter->GetType())) { 594 i++; 595 locals_index++; 596 parameter_index++; 597 } 598 } 599 } 600 601 template<typename T> 602 void HInstructionBuilder::If_22t(const Instruction& instruction, uint32_t dex_pc) { 603 HInstruction* first = LoadLocal(instruction.VRegA(), DataType::Type::kInt32); 604 HInstruction* second = LoadLocal(instruction.VRegB(), DataType::Type::kInt32); 605 T* comparison = new (allocator_) T(first, second, dex_pc); 606 AppendInstruction(comparison); 607 AppendInstruction(new (allocator_) HIf(comparison, dex_pc)); 608 current_block_ = nullptr; 609 } 610 611 template<typename T> 612 void HInstructionBuilder::If_21t(const Instruction& instruction, uint32_t dex_pc) { 613 HInstruction* value = LoadLocal(instruction.VRegA(), DataType::Type::kInt32); 614 T* comparison = new (allocator_) T(value, graph_->GetIntConstant(0, dex_pc), dex_pc); 615 AppendInstruction(comparison); 616 AppendInstruction(new (allocator_) HIf(comparison, dex_pc)); 617 current_block_ = nullptr; 618 } 619 620 template<typename T> 621 void HInstructionBuilder::Unop_12x(const Instruction& instruction, 622 DataType::Type type, 623 uint32_t dex_pc) { 624 HInstruction* first = LoadLocal(instruction.VRegB(), type); 625 AppendInstruction(new (allocator_) T(type, first, dex_pc)); 626 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 627 } 628 629 void HInstructionBuilder::Conversion_12x(const Instruction& instruction, 630 DataType::Type input_type, 631 DataType::Type result_type, 632 uint32_t dex_pc) { 633 HInstruction* first = LoadLocal(instruction.VRegB(), input_type); 634 AppendInstruction(new (allocator_) HTypeConversion(result_type, first, dex_pc)); 635 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 636 } 637 638 template<typename T> 639 void HInstructionBuilder::Binop_23x(const Instruction& instruction, 640 DataType::Type type, 641 uint32_t dex_pc) { 642 HInstruction* first = LoadLocal(instruction.VRegB(), type); 643 HInstruction* second = LoadLocal(instruction.VRegC(), type); 644 AppendInstruction(new (allocator_) T(type, first, second, dex_pc)); 645 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 646 } 647 648 template<typename T> 649 void HInstructionBuilder::Binop_23x_shift(const Instruction& instruction, 650 DataType::Type type, 651 uint32_t dex_pc) { 652 HInstruction* first = LoadLocal(instruction.VRegB(), type); 653 HInstruction* second = LoadLocal(instruction.VRegC(), DataType::Type::kInt32); 654 AppendInstruction(new (allocator_) T(type, first, second, dex_pc)); 655 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 656 } 657 658 void HInstructionBuilder::Binop_23x_cmp(const Instruction& instruction, 659 DataType::Type type, 660 ComparisonBias bias, 661 uint32_t dex_pc) { 662 HInstruction* first = LoadLocal(instruction.VRegB(), type); 663 HInstruction* second = LoadLocal(instruction.VRegC(), type); 664 AppendInstruction(new (allocator_) HCompare(type, first, second, bias, dex_pc)); 665 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 666 } 667 668 template<typename T> 669 void HInstructionBuilder::Binop_12x_shift(const Instruction& instruction, 670 DataType::Type type, 671 uint32_t dex_pc) { 672 HInstruction* first = LoadLocal(instruction.VRegA(), type); 673 HInstruction* second = LoadLocal(instruction.VRegB(), DataType::Type::kInt32); 674 AppendInstruction(new (allocator_) T(type, first, second, dex_pc)); 675 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 676 } 677 678 template<typename T> 679 void HInstructionBuilder::Binop_12x(const Instruction& instruction, 680 DataType::Type type, 681 uint32_t dex_pc) { 682 HInstruction* first = LoadLocal(instruction.VRegA(), type); 683 HInstruction* second = LoadLocal(instruction.VRegB(), type); 684 AppendInstruction(new (allocator_) T(type, first, second, dex_pc)); 685 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 686 } 687 688 template<typename T> 689 void HInstructionBuilder::Binop_22s(const Instruction& instruction, bool reverse, uint32_t dex_pc) { 690 HInstruction* first = LoadLocal(instruction.VRegB(), DataType::Type::kInt32); 691 HInstruction* second = graph_->GetIntConstant(instruction.VRegC_22s(), dex_pc); 692 if (reverse) { 693 std::swap(first, second); 694 } 695 AppendInstruction(new (allocator_) T(DataType::Type::kInt32, first, second, dex_pc)); 696 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 697 } 698 699 template<typename T> 700 void HInstructionBuilder::Binop_22b(const Instruction& instruction, bool reverse, uint32_t dex_pc) { 701 HInstruction* first = LoadLocal(instruction.VRegB(), DataType::Type::kInt32); 702 HInstruction* second = graph_->GetIntConstant(instruction.VRegC_22b(), dex_pc); 703 if (reverse) { 704 std::swap(first, second); 705 } 706 AppendInstruction(new (allocator_) T(DataType::Type::kInt32, first, second, dex_pc)); 707 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 708 } 709 710 // Does the method being compiled need any constructor barriers being inserted? 711 // (Always 'false' for methods that aren't <init>.) 712 static bool RequiresConstructorBarrier(const DexCompilationUnit* cu) { 713 // Can be null in unit tests only. 714 if (UNLIKELY(cu == nullptr)) { 715 return false; 716 } 717 718 // Constructor barriers are applicable only for <init> methods. 719 if (LIKELY(!cu->IsConstructor() || cu->IsStatic())) { 720 return false; 721 } 722 723 return cu->RequiresConstructorBarrier(); 724 } 725 726 // Returns true if `block` has only one successor which starts at the next 727 // dex_pc after `instruction` at `dex_pc`. 728 static bool IsFallthroughInstruction(const Instruction& instruction, 729 uint32_t dex_pc, 730 HBasicBlock* block) { 731 uint32_t next_dex_pc = dex_pc + instruction.SizeInCodeUnits(); 732 return block->GetSingleSuccessor()->GetDexPc() == next_dex_pc; 733 } 734 735 void HInstructionBuilder::BuildSwitch(const Instruction& instruction, uint32_t dex_pc) { 736 HInstruction* value = LoadLocal(instruction.VRegA(), DataType::Type::kInt32); 737 DexSwitchTable table(instruction, dex_pc); 738 739 if (table.GetNumEntries() == 0) { 740 // Empty Switch. Code falls through to the next block. 741 DCHECK(IsFallthroughInstruction(instruction, dex_pc, current_block_)); 742 AppendInstruction(new (allocator_) HGoto(dex_pc)); 743 } else if (table.ShouldBuildDecisionTree()) { 744 for (DexSwitchTableIterator it(table); !it.Done(); it.Advance()) { 745 HInstruction* case_value = graph_->GetIntConstant(it.CurrentKey(), dex_pc); 746 HEqual* comparison = new (allocator_) HEqual(value, case_value, dex_pc); 747 AppendInstruction(comparison); 748 AppendInstruction(new (allocator_) HIf(comparison, dex_pc)); 749 750 if (!it.IsLast()) { 751 current_block_ = FindBlockStartingAt(it.GetDexPcForCurrentIndex()); 752 } 753 } 754 } else { 755 AppendInstruction( 756 new (allocator_) HPackedSwitch(table.GetEntryAt(0), table.GetNumEntries(), value, dex_pc)); 757 } 758 759 current_block_ = nullptr; 760 } 761 762 void HInstructionBuilder::BuildReturn(const Instruction& instruction, 763 DataType::Type type, 764 uint32_t dex_pc) { 765 if (type == DataType::Type::kVoid) { 766 // Only <init> (which is a return-void) could possibly have a constructor fence. 767 // This may insert additional redundant constructor fences from the super constructors. 768 // TODO: remove redundant constructor fences (b/36656456). 769 if (RequiresConstructorBarrier(dex_compilation_unit_)) { 770 // Compiling instance constructor. 771 DCHECK_STREQ("<init>", graph_->GetMethodName()); 772 773 HInstruction* fence_target = current_this_parameter_; 774 DCHECK(fence_target != nullptr); 775 776 AppendInstruction(new (allocator_) HConstructorFence(fence_target, dex_pc, allocator_)); 777 MaybeRecordStat( 778 compilation_stats_, 779 MethodCompilationStat::kConstructorFenceGeneratedFinal); 780 } 781 AppendInstruction(new (allocator_) HReturnVoid(dex_pc)); 782 } else { 783 DCHECK(!RequiresConstructorBarrier(dex_compilation_unit_)); 784 HInstruction* value = LoadLocal(instruction.VRegA(), type); 785 AppendInstruction(new (allocator_) HReturn(value, dex_pc)); 786 } 787 current_block_ = nullptr; 788 } 789 790 static InvokeType GetInvokeTypeFromOpCode(Instruction::Code opcode) { 791 switch (opcode) { 792 case Instruction::INVOKE_STATIC: 793 case Instruction::INVOKE_STATIC_RANGE: 794 return kStatic; 795 case Instruction::INVOKE_DIRECT: 796 case Instruction::INVOKE_DIRECT_RANGE: 797 return kDirect; 798 case Instruction::INVOKE_VIRTUAL: 799 case Instruction::INVOKE_VIRTUAL_QUICK: 800 case Instruction::INVOKE_VIRTUAL_RANGE: 801 case Instruction::INVOKE_VIRTUAL_RANGE_QUICK: 802 return kVirtual; 803 case Instruction::INVOKE_INTERFACE: 804 case Instruction::INVOKE_INTERFACE_RANGE: 805 return kInterface; 806 case Instruction::INVOKE_SUPER_RANGE: 807 case Instruction::INVOKE_SUPER: 808 return kSuper; 809 default: 810 LOG(FATAL) << "Unexpected invoke opcode: " << opcode; 811 UNREACHABLE(); 812 } 813 } 814 815 ArtMethod* HInstructionBuilder::ResolveMethod(uint16_t method_idx, InvokeType invoke_type) { 816 ScopedObjectAccess soa(Thread::Current()); 817 818 ClassLinker* class_linker = dex_compilation_unit_->GetClassLinker(); 819 Handle<mirror::ClassLoader> class_loader = dex_compilation_unit_->GetClassLoader(); 820 821 ArtMethod* resolved_method = 822 class_linker->ResolveMethod<ClassLinker::ResolveMode::kCheckICCEAndIAE>( 823 method_idx, 824 dex_compilation_unit_->GetDexCache(), 825 class_loader, 826 graph_->GetArtMethod(), 827 invoke_type); 828 829 if (UNLIKELY(resolved_method == nullptr)) { 830 // Clean up any exception left by type resolution. 831 soa.Self()->ClearException(); 832 return nullptr; 833 } 834 835 // The referrer may be unresolved for AOT if we're compiling a class that cannot be 836 // resolved because, for example, we don't find a superclass in the classpath. 837 if (graph_->GetArtMethod() == nullptr) { 838 // The class linker cannot check access without a referrer, so we have to do it. 839 // Fall back to HInvokeUnresolved if the method isn't public. 840 if (!resolved_method->IsPublic()) { 841 return nullptr; 842 } 843 } 844 845 // We have to special case the invoke-super case, as ClassLinker::ResolveMethod does not. 846 // We need to look at the referrer's super class vtable. We need to do this to know if we need to 847 // make this an invoke-unresolved to handle cross-dex invokes or abstract super methods, both of 848 // which require runtime handling. 849 if (invoke_type == kSuper) { 850 ObjPtr<mirror::Class> compiling_class = dex_compilation_unit_->GetCompilingClass().Get(); 851 if (compiling_class == nullptr) { 852 // We could not determine the method's class we need to wait until runtime. 853 DCHECK(Runtime::Current()->IsAotCompiler()); 854 return nullptr; 855 } 856 ObjPtr<mirror::Class> referenced_class = class_linker->LookupResolvedType( 857 dex_compilation_unit_->GetDexFile()->GetMethodId(method_idx).class_idx_, 858 dex_compilation_unit_->GetDexCache().Get(), 859 class_loader.Get()); 860 DCHECK(referenced_class != nullptr); // We have already resolved a method from this class. 861 if (!referenced_class->IsAssignableFrom(compiling_class)) { 862 // We cannot statically determine the target method. The runtime will throw a 863 // NoSuchMethodError on this one. 864 return nullptr; 865 } 866 ArtMethod* actual_method; 867 if (referenced_class->IsInterface()) { 868 actual_method = referenced_class->FindVirtualMethodForInterfaceSuper( 869 resolved_method, class_linker->GetImagePointerSize()); 870 } else { 871 uint16_t vtable_index = resolved_method->GetMethodIndex(); 872 actual_method = compiling_class->GetSuperClass()->GetVTableEntry( 873 vtable_index, class_linker->GetImagePointerSize()); 874 } 875 if (actual_method != resolved_method && 876 !IsSameDexFile(*actual_method->GetDexFile(), *dex_compilation_unit_->GetDexFile())) { 877 // The back-end code generator relies on this check in order to ensure that it will not 878 // attempt to read the dex_cache with a dex_method_index that is not from the correct 879 // dex_file. If we didn't do this check then the dex_method_index will not be updated in the 880 // builder, which means that the code-generator (and sharpening and inliner, maybe) 881 // might invoke an incorrect method. 882 // TODO: The actual method could still be referenced in the current dex file, so we 883 // could try locating it. 884 // TODO: Remove the dex_file restriction. 885 return nullptr; 886 } 887 if (!actual_method->IsInvokable()) { 888 // Fail if the actual method cannot be invoked. Otherwise, the runtime resolution stub 889 // could resolve the callee to the wrong method. 890 return nullptr; 891 } 892 resolved_method = actual_method; 893 } 894 895 return resolved_method; 896 } 897 898 static bool IsStringConstructor(ArtMethod* method) { 899 ScopedObjectAccess soa(Thread::Current()); 900 return method->GetDeclaringClass()->IsStringClass() && method->IsConstructor(); 901 } 902 903 bool HInstructionBuilder::BuildInvoke(const Instruction& instruction, 904 uint32_t dex_pc, 905 uint32_t method_idx, 906 const InstructionOperands& operands) { 907 InvokeType invoke_type = GetInvokeTypeFromOpCode(instruction.Opcode()); 908 const char* shorty = dex_file_->GetMethodShorty(method_idx); 909 DataType::Type return_type = DataType::FromShorty(shorty[0]); 910 911 // Remove the return type from the 'proto'. 912 size_t number_of_arguments = strlen(shorty) - 1; 913 if (invoke_type != kStatic) { // instance call 914 // One extra argument for 'this'. 915 number_of_arguments++; 916 } 917 918 ArtMethod* resolved_method = ResolveMethod(method_idx, invoke_type); 919 920 if (UNLIKELY(resolved_method == nullptr)) { 921 MaybeRecordStat(compilation_stats_, 922 MethodCompilationStat::kUnresolvedMethod); 923 HInvoke* invoke = new (allocator_) HInvokeUnresolved(allocator_, 924 number_of_arguments, 925 return_type, 926 dex_pc, 927 method_idx, 928 invoke_type); 929 return HandleInvoke(invoke, operands, shorty, /* is_unresolved= */ true); 930 } 931 932 // Replace calls to String.<init> with StringFactory. 933 if (IsStringConstructor(resolved_method)) { 934 uint32_t string_init_entry_point = WellKnownClasses::StringInitToEntryPoint(resolved_method); 935 HInvokeStaticOrDirect::DispatchInfo dispatch_info = { 936 HInvokeStaticOrDirect::MethodLoadKind::kStringInit, 937 HInvokeStaticOrDirect::CodePtrLocation::kCallArtMethod, 938 dchecked_integral_cast<uint64_t>(string_init_entry_point) 939 }; 940 ScopedObjectAccess soa(Thread::Current()); 941 MethodReference target_method(resolved_method->GetDexFile(), 942 resolved_method->GetDexMethodIndex()); 943 // We pass null for the resolved_method to ensure optimizations 944 // don't rely on it. 945 HInvoke* invoke = new (allocator_) HInvokeStaticOrDirect( 946 allocator_, 947 number_of_arguments - 1, 948 /* return_type= */ DataType::Type::kReference, 949 dex_pc, 950 method_idx, 951 /* resolved_method= */ nullptr, 952 dispatch_info, 953 invoke_type, 954 target_method, 955 HInvokeStaticOrDirect::ClinitCheckRequirement::kImplicit); 956 return HandleStringInit(invoke, operands, shorty); 957 } 958 959 // Potential class initialization check, in the case of a static method call. 960 HClinitCheck* clinit_check = nullptr; 961 HInvoke* invoke = nullptr; 962 if (invoke_type == kDirect || invoke_type == kStatic || invoke_type == kSuper) { 963 // By default, consider that the called method implicitly requires 964 // an initialization check of its declaring method. 965 HInvokeStaticOrDirect::ClinitCheckRequirement clinit_check_requirement 966 = HInvokeStaticOrDirect::ClinitCheckRequirement::kImplicit; 967 ScopedObjectAccess soa(Thread::Current()); 968 if (invoke_type == kStatic) { 969 clinit_check = 970 ProcessClinitCheckForInvoke(dex_pc, resolved_method, &clinit_check_requirement); 971 } else if (invoke_type == kSuper) { 972 if (IsSameDexFile(*resolved_method->GetDexFile(), *dex_compilation_unit_->GetDexFile())) { 973 // Update the method index to the one resolved. Note that this may be a no-op if 974 // we resolved to the method referenced by the instruction. 975 method_idx = resolved_method->GetDexMethodIndex(); 976 } 977 } 978 979 HInvokeStaticOrDirect::DispatchInfo dispatch_info = 980 HSharpening::SharpenInvokeStaticOrDirect(resolved_method, code_generator_); 981 MethodReference target_method(resolved_method->GetDexFile(), 982 resolved_method->GetDexMethodIndex()); 983 invoke = new (allocator_) HInvokeStaticOrDirect(allocator_, 984 number_of_arguments, 985 return_type, 986 dex_pc, 987 method_idx, 988 resolved_method, 989 dispatch_info, 990 invoke_type, 991 target_method, 992 clinit_check_requirement); 993 } else if (invoke_type == kVirtual) { 994 ScopedObjectAccess soa(Thread::Current()); // Needed for the method index 995 invoke = new (allocator_) HInvokeVirtual(allocator_, 996 number_of_arguments, 997 return_type, 998 dex_pc, 999 method_idx, 1000 resolved_method, 1001 resolved_method->GetMethodIndex()); 1002 } else { 1003 DCHECK_EQ(invoke_type, kInterface); 1004 ScopedObjectAccess soa(Thread::Current()); // Needed for the IMT index. 1005 invoke = new (allocator_) HInvokeInterface(allocator_, 1006 number_of_arguments, 1007 return_type, 1008 dex_pc, 1009 method_idx, 1010 resolved_method, 1011 ImTable::GetImtIndex(resolved_method)); 1012 } 1013 return HandleInvoke(invoke, operands, shorty, /* is_unresolved= */ false, clinit_check); 1014 } 1015 1016 bool HInstructionBuilder::BuildInvokePolymorphic(uint32_t dex_pc, 1017 uint32_t method_idx, 1018 dex::ProtoIndex proto_idx, 1019 const InstructionOperands& operands) { 1020 const char* shorty = dex_file_->GetShorty(proto_idx); 1021 DCHECK_EQ(1 + ArtMethod::NumArgRegisters(shorty), operands.GetNumberOfOperands()); 1022 DataType::Type return_type = DataType::FromShorty(shorty[0]); 1023 size_t number_of_arguments = strlen(shorty); 1024 HInvoke* invoke = new (allocator_) HInvokePolymorphic(allocator_, 1025 number_of_arguments, 1026 return_type, 1027 dex_pc, 1028 method_idx); 1029 return HandleInvoke(invoke, operands, shorty, /* is_unresolved= */ false); 1030 } 1031 1032 1033 bool HInstructionBuilder::BuildInvokeCustom(uint32_t dex_pc, 1034 uint32_t call_site_idx, 1035 const InstructionOperands& operands) { 1036 dex::ProtoIndex proto_idx = dex_file_->GetProtoIndexForCallSite(call_site_idx); 1037 const char* shorty = dex_file_->GetShorty(proto_idx); 1038 DataType::Type return_type = DataType::FromShorty(shorty[0]); 1039 size_t number_of_arguments = strlen(shorty) - 1; 1040 HInvoke* invoke = new (allocator_) HInvokeCustom(allocator_, 1041 number_of_arguments, 1042 call_site_idx, 1043 return_type, 1044 dex_pc); 1045 return HandleInvoke(invoke, operands, shorty, /* is_unresolved= */ false); 1046 } 1047 1048 HNewInstance* HInstructionBuilder::BuildNewInstance(dex::TypeIndex type_index, uint32_t dex_pc) { 1049 ScopedObjectAccess soa(Thread::Current()); 1050 1051 HLoadClass* load_class = BuildLoadClass(type_index, dex_pc); 1052 1053 HInstruction* cls = load_class; 1054 Handle<mirror::Class> klass = load_class->GetClass(); 1055 1056 if (!IsInitialized(klass)) { 1057 cls = new (allocator_) HClinitCheck(load_class, dex_pc); 1058 AppendInstruction(cls); 1059 } 1060 1061 // Only the access check entrypoint handles the finalizable class case. If we 1062 // need access checks, then we haven't resolved the method and the class may 1063 // again be finalizable. 1064 QuickEntrypointEnum entrypoint = kQuickAllocObjectInitialized; 1065 if (load_class->NeedsAccessCheck() || klass->IsFinalizable() || !klass->IsInstantiable()) { 1066 entrypoint = kQuickAllocObjectWithChecks; 1067 } 1068 // We will always be able to resolve the string class since it is in the BCP. 1069 if (!klass.IsNull() && klass->IsStringClass()) { 1070 entrypoint = kQuickAllocStringObject; 1071 } 1072 1073 // Consider classes we haven't resolved as potentially finalizable. 1074 bool finalizable = (klass == nullptr) || klass->IsFinalizable(); 1075 1076 HNewInstance* new_instance = new (allocator_) HNewInstance( 1077 cls, 1078 dex_pc, 1079 type_index, 1080 *dex_compilation_unit_->GetDexFile(), 1081 finalizable, 1082 entrypoint); 1083 AppendInstruction(new_instance); 1084 1085 return new_instance; 1086 } 1087 1088 void HInstructionBuilder::BuildConstructorFenceForAllocation(HInstruction* allocation) { 1089 DCHECK(allocation != nullptr && 1090 (allocation->IsNewInstance() || 1091 allocation->IsNewArray())); // corresponding to "new" keyword in JLS. 1092 1093 if (allocation->IsNewInstance()) { 1094 // STRING SPECIAL HANDLING: 1095 // ------------------------------- 1096 // Strings have a real HNewInstance node but they end up always having 0 uses. 1097 // All uses of a String HNewInstance are always transformed to replace their input 1098 // of the HNewInstance with an input of the invoke to StringFactory. 1099 // 1100 // Do not emit an HConstructorFence here since it can inhibit some String new-instance 1101 // optimizations (to pass checker tests that rely on those optimizations). 1102 HNewInstance* new_inst = allocation->AsNewInstance(); 1103 HLoadClass* load_class = new_inst->GetLoadClass(); 1104 1105 Thread* self = Thread::Current(); 1106 ScopedObjectAccess soa(self); 1107 StackHandleScope<1> hs(self); 1108 Handle<mirror::Class> klass = load_class->GetClass(); 1109 if (klass != nullptr && klass->IsStringClass()) { 1110 return; 1111 // Note: Do not use allocation->IsStringAlloc which requires 1112 // a valid ReferenceTypeInfo, but that doesn't get made until after reference type 1113 // propagation (and instruction builder is too early). 1114 } 1115 // (In terms of correctness, the StringFactory needs to provide its own 1116 // default initialization barrier, see below.) 1117 } 1118 1119 // JLS 17.4.5 "Happens-before Order" describes: 1120 // 1121 // The default initialization of any object happens-before any other actions (other than 1122 // default-writes) of a program. 1123 // 1124 // In our implementation the default initialization of an object to type T means 1125 // setting all of its initial data (object[0..size)) to 0, and setting the 1126 // object's class header (i.e. object.getClass() == T.class). 1127 // 1128 // In practice this fence ensures that the writes to the object header 1129 // are visible to other threads if this object escapes the current thread. 1130 // (and in theory the 0-initializing, but that happens automatically 1131 // when new memory pages are mapped in by the OS). 1132 HConstructorFence* ctor_fence = 1133 new (allocator_) HConstructorFence(allocation, allocation->GetDexPc(), allocator_); 1134 AppendInstruction(ctor_fence); 1135 MaybeRecordStat( 1136 compilation_stats_, 1137 MethodCompilationStat::kConstructorFenceGeneratedNew); 1138 } 1139 1140 static bool IsInBootImage(ObjPtr<mirror::Class> cls, const CompilerOptions& compiler_options) 1141 REQUIRES_SHARED(Locks::mutator_lock_) { 1142 if (compiler_options.IsBootImage()) { 1143 std::string temp; 1144 const char* descriptor = cls->GetDescriptor(&temp); 1145 return compiler_options.IsImageClass(descriptor); 1146 } else { 1147 return Runtime::Current()->GetHeap()->FindSpaceFromObject(cls, false)->IsImageSpace(); 1148 } 1149 } 1150 1151 static bool IsSubClass(ObjPtr<mirror::Class> to_test, ObjPtr<mirror::Class> super_class) 1152 REQUIRES_SHARED(Locks::mutator_lock_) { 1153 return to_test != nullptr && !to_test->IsInterface() && to_test->IsSubClass(super_class); 1154 } 1155 1156 static bool HasTrivialClinit(ObjPtr<mirror::Class> klass, PointerSize pointer_size) 1157 REQUIRES_SHARED(Locks::mutator_lock_) { 1158 // Check if the class has encoded fields that trigger bytecode execution. 1159 // (Encoded fields are just a different representation of <clinit>.) 1160 if (klass->NumStaticFields() != 0u) { 1161 DCHECK(klass->GetClassDef() != nullptr); 1162 EncodedStaticFieldValueIterator it(klass->GetDexFile(), *klass->GetClassDef()); 1163 for (; it.HasNext(); it.Next()) { 1164 switch (it.GetValueType()) { 1165 case EncodedArrayValueIterator::ValueType::kBoolean: 1166 case EncodedArrayValueIterator::ValueType::kByte: 1167 case EncodedArrayValueIterator::ValueType::kShort: 1168 case EncodedArrayValueIterator::ValueType::kChar: 1169 case EncodedArrayValueIterator::ValueType::kInt: 1170 case EncodedArrayValueIterator::ValueType::kLong: 1171 case EncodedArrayValueIterator::ValueType::kFloat: 1172 case EncodedArrayValueIterator::ValueType::kDouble: 1173 case EncodedArrayValueIterator::ValueType::kNull: 1174 case EncodedArrayValueIterator::ValueType::kString: 1175 // Primitive, null or j.l.String initialization is permitted. 1176 break; 1177 case EncodedArrayValueIterator::ValueType::kType: 1178 // Type initialization can load classes and execute bytecode through a class loader 1179 // which can execute arbitrary bytecode. We do not optimize for known class loaders; 1180 // kType is rarely used (if ever). 1181 return false; 1182 default: 1183 // Other types in the encoded static field list are rejected by the DexFileVerifier. 1184 LOG(FATAL) << "Unexpected type " << it.GetValueType(); 1185 UNREACHABLE(); 1186 } 1187 } 1188 } 1189 // Check if the class has <clinit> that executes arbitrary code. 1190 // Initialization of static fields of the class itself with constants is allowed. 1191 ArtMethod* clinit = klass->FindClassInitializer(pointer_size); 1192 if (clinit != nullptr) { 1193 const DexFile& dex_file = *clinit->GetDexFile(); 1194 CodeItemInstructionAccessor accessor(dex_file, clinit->GetCodeItem()); 1195 for (DexInstructionPcPair it : accessor) { 1196 switch (it->Opcode()) { 1197 case Instruction::CONST_4: 1198 case Instruction::CONST_16: 1199 case Instruction::CONST: 1200 case Instruction::CONST_HIGH16: 1201 case Instruction::CONST_WIDE_16: 1202 case Instruction::CONST_WIDE_32: 1203 case Instruction::CONST_WIDE: 1204 case Instruction::CONST_WIDE_HIGH16: 1205 case Instruction::CONST_STRING: 1206 case Instruction::CONST_STRING_JUMBO: 1207 // Primitive, null or j.l.String initialization is permitted. 1208 break; 1209 case Instruction::RETURN_VOID: 1210 case Instruction::RETURN_VOID_NO_BARRIER: 1211 break; 1212 case Instruction::SPUT: 1213 case Instruction::SPUT_WIDE: 1214 case Instruction::SPUT_OBJECT: 1215 case Instruction::SPUT_BOOLEAN: 1216 case Instruction::SPUT_BYTE: 1217 case Instruction::SPUT_CHAR: 1218 case Instruction::SPUT_SHORT: 1219 // Only initialization of a static field of the same class is permitted. 1220 if (dex_file.GetFieldId(it->VRegB_21c()).class_idx_ != klass->GetDexTypeIndex()) { 1221 return false; 1222 } 1223 break; 1224 case Instruction::NEW_ARRAY: 1225 // Only primitive arrays are permitted. 1226 if (Primitive::GetType(dex_file.GetTypeDescriptor(dex_file.GetTypeId( 1227 dex::TypeIndex(it->VRegC_22c())))[1]) == Primitive::kPrimNot) { 1228 return false; 1229 } 1230 break; 1231 case Instruction::APUT: 1232 case Instruction::APUT_WIDE: 1233 case Instruction::APUT_BOOLEAN: 1234 case Instruction::APUT_BYTE: 1235 case Instruction::APUT_CHAR: 1236 case Instruction::APUT_SHORT: 1237 case Instruction::FILL_ARRAY_DATA: 1238 case Instruction::NOP: 1239 // Allow initialization of primitive arrays (only constants can be stored). 1240 // Note: We expect NOPs used for fill-array-data-payload but accept all NOPs 1241 // (even unreferenced switch payloads if they make it through the verifier). 1242 break; 1243 default: 1244 return false; 1245 } 1246 } 1247 } 1248 return true; 1249 } 1250 1251 static bool HasTrivialInitialization(ObjPtr<mirror::Class> cls, 1252 const CompilerOptions& compiler_options) 1253 REQUIRES_SHARED(Locks::mutator_lock_) { 1254 Runtime* runtime = Runtime::Current(); 1255 PointerSize pointer_size = runtime->GetClassLinker()->GetImagePointerSize(); 1256 1257 // Check the superclass chain. 1258 for (ObjPtr<mirror::Class> klass = cls; klass != nullptr; klass = klass->GetSuperClass()) { 1259 if (klass->IsInitialized() && IsInBootImage(klass, compiler_options)) { 1260 break; // `klass` and its superclasses are already initialized in the boot image. 1261 } 1262 if (!HasTrivialClinit(klass, pointer_size)) { 1263 return false; 1264 } 1265 } 1266 1267 // Also check interfaces with default methods as they need to be initialized as well. 1268 ObjPtr<mirror::IfTable> iftable = cls->GetIfTable(); 1269 DCHECK(iftable != nullptr); 1270 for (int32_t i = 0, count = iftable->Count(); i != count; ++i) { 1271 ObjPtr<mirror::Class> iface = iftable->GetInterface(i); 1272 if (!iface->HasDefaultMethods()) { 1273 continue; // Initializing `cls` does not initialize this interface. 1274 } 1275 if (iface->IsInitialized() && IsInBootImage(iface, compiler_options)) { 1276 continue; // This interface is already initialized in the boot image. 1277 } 1278 if (!HasTrivialClinit(iface, pointer_size)) { 1279 return false; 1280 } 1281 } 1282 return true; 1283 } 1284 1285 bool HInstructionBuilder::IsInitialized(Handle<mirror::Class> cls) const { 1286 if (cls == nullptr) { 1287 return false; 1288 } 1289 1290 // Check if the class will be initialized at runtime. 1291 if (cls->IsInitialized()) { 1292 Runtime* runtime = Runtime::Current(); 1293 if (!runtime->IsAotCompiler()) { 1294 DCHECK(runtime->UseJitCompilation()); 1295 // For JIT, the class cannot revert to an uninitialized state. 1296 return true; 1297 } 1298 // Assume loaded only if klass is in the boot image. App classes cannot be assumed 1299 // loaded because we don't even know what class loader will be used to load them. 1300 if (IsInBootImage(cls.Get(), code_generator_->GetCompilerOptions())) { 1301 return true; 1302 } 1303 } 1304 1305 // We can avoid the class initialization check for `cls` in static methods and constructors 1306 // in the very same class; invoking a static method involves a class initialization check 1307 // and so does the instance allocation that must be executed before invoking a constructor. 1308 // Other instance methods of the same class can run on an escaped instance 1309 // of an erroneous class. Even a superclass may need to be checked as the subclass 1310 // can be completely initialized while the superclass is initializing and the subclass 1311 // remains initialized when the superclass initializer throws afterwards. b/62478025 1312 // Note: The HClinitCheck+HInvokeStaticOrDirect merging can still apply. 1313 auto is_static_method_or_constructor_of_cls = [cls](const DexCompilationUnit& compilation_unit) 1314 REQUIRES_SHARED(Locks::mutator_lock_) { 1315 return (compilation_unit.GetAccessFlags() & (kAccStatic | kAccConstructor)) != 0u && 1316 compilation_unit.GetCompilingClass().Get() == cls.Get(); 1317 }; 1318 if (is_static_method_or_constructor_of_cls(*outer_compilation_unit_) || 1319 // Check also the innermost method. Though excessive copies of ClinitCheck can be 1320 // eliminated by GVN, that happens only after the decision whether to inline the 1321 // graph or not and that may depend on the presence of the ClinitCheck. 1322 // TODO: We should walk over the entire inlined method chain, but we don't pass that 1323 // information to the builder. 1324 is_static_method_or_constructor_of_cls(*dex_compilation_unit_)) { 1325 return true; 1326 } 1327 1328 // Otherwise, we may be able to avoid the check if `cls` is a superclass of a method being 1329 // compiled here (anywhere in the inlining chain) as the `cls` must have started initializing 1330 // before calling any `cls` or subclass methods. Static methods require a clinit check and 1331 // instance methods require an instance which cannot be created before doing a clinit check. 1332 // When a subclass of `cls` starts initializing, it starts initializing its superclass 1333 // chain up to `cls` without running any bytecode, i.e. without any opportunity for circular 1334 // initialization weirdness. 1335 // 1336 // If the initialization of `cls` is trivial (`cls` and its superclasses and superinterfaces 1337 // with default methods initialize only their own static fields using constant values), it must 1338 // complete, either successfully or by throwing and marking `cls` erroneous, without allocating 1339 // any instances of `cls` or subclasses (or any other class) and without calling any methods. 1340 // If it completes by throwing, no instances of `cls` shall be created and no subclass method 1341 // bytecode shall execute (see above), therefore the instruction we're building shall be 1342 // unreachable. By reaching the instruction, we know that `cls` was initialized successfully. 1343 // 1344 // TODO: We should walk over the entire inlined methods chain, but we don't pass that 1345 // information to the builder. (We could also check if we're guaranteed a non-null instance 1346 // of `cls` at this location but that's outside the scope of the instruction builder.) 1347 bool is_subclass = IsSubClass(outer_compilation_unit_->GetCompilingClass().Get(), cls.Get()); 1348 if (dex_compilation_unit_ != outer_compilation_unit_) { 1349 is_subclass = is_subclass || 1350 IsSubClass(dex_compilation_unit_->GetCompilingClass().Get(), cls.Get()); 1351 } 1352 if (is_subclass && HasTrivialInitialization(cls.Get(), code_generator_->GetCompilerOptions())) { 1353 return true; 1354 } 1355 1356 return false; 1357 } 1358 1359 HClinitCheck* HInstructionBuilder::ProcessClinitCheckForInvoke( 1360 uint32_t dex_pc, 1361 ArtMethod* resolved_method, 1362 HInvokeStaticOrDirect::ClinitCheckRequirement* clinit_check_requirement) { 1363 Handle<mirror::Class> klass = handles_->NewHandle(resolved_method->GetDeclaringClass()); 1364 1365 HClinitCheck* clinit_check = nullptr; 1366 if (IsInitialized(klass)) { 1367 *clinit_check_requirement = HInvokeStaticOrDirect::ClinitCheckRequirement::kNone; 1368 } else { 1369 HLoadClass* cls = BuildLoadClass(klass->GetDexTypeIndex(), 1370 klass->GetDexFile(), 1371 klass, 1372 dex_pc, 1373 /* needs_access_check= */ false); 1374 if (cls != nullptr) { 1375 *clinit_check_requirement = HInvokeStaticOrDirect::ClinitCheckRequirement::kExplicit; 1376 clinit_check = new (allocator_) HClinitCheck(cls, dex_pc); 1377 AppendInstruction(clinit_check); 1378 } 1379 } 1380 return clinit_check; 1381 } 1382 1383 bool HInstructionBuilder::SetupInvokeArguments(HInvoke* invoke, 1384 const InstructionOperands& operands, 1385 const char* shorty, 1386 size_t start_index, 1387 size_t* argument_index) { 1388 uint32_t shorty_index = 1; // Skip the return type. 1389 const size_t number_of_operands = operands.GetNumberOfOperands(); 1390 for (size_t i = start_index; 1391 // Make sure we don't go over the expected arguments or over the number of 1392 // dex registers given. If the instruction was seen as dead by the verifier, 1393 // it hasn't been properly checked. 1394 (i < number_of_operands) && (*argument_index < invoke->GetNumberOfArguments()); 1395 i++, (*argument_index)++) { 1396 DataType::Type type = DataType::FromShorty(shorty[shorty_index++]); 1397 bool is_wide = (type == DataType::Type::kInt64) || (type == DataType::Type::kFloat64); 1398 if (is_wide && ((i + 1 == number_of_operands) || 1399 (operands.GetOperand(i) + 1 != operands.GetOperand(i + 1)))) { 1400 // Longs and doubles should be in pairs, that is, sequential registers. The verifier should 1401 // reject any class where this is violated. However, the verifier only does these checks 1402 // on non trivially dead instructions, so we just bailout the compilation. 1403 VLOG(compiler) << "Did not compile " 1404 << dex_file_->PrettyMethod(dex_compilation_unit_->GetDexMethodIndex()) 1405 << " because of non-sequential dex register pair in wide argument"; 1406 MaybeRecordStat(compilation_stats_, 1407 MethodCompilationStat::kNotCompiledMalformedOpcode); 1408 return false; 1409 } 1410 HInstruction* arg = LoadLocal(operands.GetOperand(i), type); 1411 invoke->SetArgumentAt(*argument_index, arg); 1412 if (is_wide) { 1413 i++; 1414 } 1415 } 1416 1417 if (*argument_index != invoke->GetNumberOfArguments()) { 1418 VLOG(compiler) << "Did not compile " 1419 << dex_file_->PrettyMethod(dex_compilation_unit_->GetDexMethodIndex()) 1420 << " because of wrong number of arguments in invoke instruction"; 1421 MaybeRecordStat(compilation_stats_, 1422 MethodCompilationStat::kNotCompiledMalformedOpcode); 1423 return false; 1424 } 1425 1426 if (invoke->IsInvokeStaticOrDirect() && 1427 HInvokeStaticOrDirect::NeedsCurrentMethodInput( 1428 invoke->AsInvokeStaticOrDirect()->GetMethodLoadKind())) { 1429 invoke->SetArgumentAt(*argument_index, graph_->GetCurrentMethod()); 1430 (*argument_index)++; 1431 } 1432 1433 return true; 1434 } 1435 1436 bool HInstructionBuilder::HandleInvoke(HInvoke* invoke, 1437 const InstructionOperands& operands, 1438 const char* shorty, 1439 bool is_unresolved, 1440 HClinitCheck* clinit_check) { 1441 DCHECK(!invoke->IsInvokeStaticOrDirect() || !invoke->AsInvokeStaticOrDirect()->IsStringInit()); 1442 1443 size_t start_index = 0; 1444 size_t argument_index = 0; 1445 if (invoke->GetInvokeType() != InvokeType::kStatic) { // Instance call. 1446 uint32_t obj_reg = operands.GetOperand(0); 1447 HInstruction* arg = is_unresolved 1448 ? LoadLocal(obj_reg, DataType::Type::kReference) 1449 : LoadNullCheckedLocal(obj_reg, invoke->GetDexPc()); 1450 invoke->SetArgumentAt(0, arg); 1451 start_index = 1; 1452 argument_index = 1; 1453 } 1454 1455 if (!SetupInvokeArguments(invoke, operands, shorty, start_index, &argument_index)) { 1456 return false; 1457 } 1458 1459 if (clinit_check != nullptr) { 1460 // Add the class initialization check as last input of `invoke`. 1461 DCHECK(invoke->IsInvokeStaticOrDirect()); 1462 DCHECK(invoke->AsInvokeStaticOrDirect()->GetClinitCheckRequirement() 1463 == HInvokeStaticOrDirect::ClinitCheckRequirement::kExplicit); 1464 invoke->SetArgumentAt(argument_index, clinit_check); 1465 argument_index++; 1466 } 1467 1468 AppendInstruction(invoke); 1469 latest_result_ = invoke; 1470 1471 return true; 1472 } 1473 1474 bool HInstructionBuilder::HandleStringInit(HInvoke* invoke, 1475 const InstructionOperands& operands, 1476 const char* shorty) { 1477 DCHECK(invoke->IsInvokeStaticOrDirect()); 1478 DCHECK(invoke->AsInvokeStaticOrDirect()->IsStringInit()); 1479 1480 size_t start_index = 1; 1481 size_t argument_index = 0; 1482 if (!SetupInvokeArguments(invoke, operands, shorty, start_index, &argument_index)) { 1483 return false; 1484 } 1485 1486 AppendInstruction(invoke); 1487 1488 // This is a StringFactory call, not an actual String constructor. Its result 1489 // replaces the empty String pre-allocated by NewInstance. 1490 uint32_t orig_this_reg = operands.GetOperand(0); 1491 HInstruction* arg_this = LoadLocal(orig_this_reg, DataType::Type::kReference); 1492 1493 // Replacing the NewInstance might render it redundant. Keep a list of these 1494 // to be visited once it is clear whether it has remaining uses. 1495 if (arg_this->IsNewInstance()) { 1496 ssa_builder_->AddUninitializedString(arg_this->AsNewInstance()); 1497 } else { 1498 DCHECK(arg_this->IsPhi()); 1499 // We can get a phi as input of a String.<init> if there is a loop between the 1500 // allocation and the String.<init> call. As we don't know which other phis might alias 1501 // with `arg_this`, we keep a record of those invocations so we can later replace 1502 // the allocation with the invocation. 1503 // Add the actual 'this' input so the analysis knows what is the allocation instruction. 1504 // The input will be removed during the analysis. 1505 invoke->AddInput(arg_this); 1506 ssa_builder_->AddUninitializedStringPhi(invoke); 1507 } 1508 // Walk over all vregs and replace any occurrence of `arg_this` with `invoke`. 1509 for (size_t vreg = 0, e = current_locals_->size(); vreg < e; ++vreg) { 1510 if ((*current_locals_)[vreg] == arg_this) { 1511 (*current_locals_)[vreg] = invoke; 1512 } 1513 } 1514 return true; 1515 } 1516 1517 static DataType::Type GetFieldAccessType(const DexFile& dex_file, uint16_t field_index) { 1518 const dex::FieldId& field_id = dex_file.GetFieldId(field_index); 1519 const char* type = dex_file.GetFieldTypeDescriptor(field_id); 1520 return DataType::FromShorty(type[0]); 1521 } 1522 1523 bool HInstructionBuilder::BuildInstanceFieldAccess(const Instruction& instruction, 1524 uint32_t dex_pc, 1525 bool is_put, 1526 size_t quicken_index) { 1527 uint32_t source_or_dest_reg = instruction.VRegA_22c(); 1528 uint32_t obj_reg = instruction.VRegB_22c(); 1529 uint16_t field_index; 1530 if (instruction.IsQuickened()) { 1531 if (!CanDecodeQuickenedInfo()) { 1532 VLOG(compiler) << "Not compiled: Could not decode quickened instruction " 1533 << instruction.Opcode(); 1534 return false; 1535 } 1536 field_index = LookupQuickenedInfo(quicken_index); 1537 } else { 1538 field_index = instruction.VRegC_22c(); 1539 } 1540 1541 ScopedObjectAccess soa(Thread::Current()); 1542 ArtField* resolved_field = ResolveField(field_index, /* is_static= */ false, is_put); 1543 1544 // Generate an explicit null check on the reference, unless the field access 1545 // is unresolved. In that case, we rely on the runtime to perform various 1546 // checks first, followed by a null check. 1547 HInstruction* object = (resolved_field == nullptr) 1548 ? LoadLocal(obj_reg, DataType::Type::kReference) 1549 : LoadNullCheckedLocal(obj_reg, dex_pc); 1550 1551 DataType::Type field_type = GetFieldAccessType(*dex_file_, field_index); 1552 if (is_put) { 1553 HInstruction* value = LoadLocal(source_or_dest_reg, field_type); 1554 HInstruction* field_set = nullptr; 1555 if (resolved_field == nullptr) { 1556 MaybeRecordStat(compilation_stats_, 1557 MethodCompilationStat::kUnresolvedField); 1558 field_set = new (allocator_) HUnresolvedInstanceFieldSet(object, 1559 value, 1560 field_type, 1561 field_index, 1562 dex_pc); 1563 } else { 1564 uint16_t class_def_index = resolved_field->GetDeclaringClass()->GetDexClassDefIndex(); 1565 field_set = new (allocator_) HInstanceFieldSet(object, 1566 value, 1567 resolved_field, 1568 field_type, 1569 resolved_field->GetOffset(), 1570 resolved_field->IsVolatile(), 1571 field_index, 1572 class_def_index, 1573 *dex_file_, 1574 dex_pc); 1575 } 1576 AppendInstruction(field_set); 1577 } else { 1578 HInstruction* field_get = nullptr; 1579 if (resolved_field == nullptr) { 1580 MaybeRecordStat(compilation_stats_, 1581 MethodCompilationStat::kUnresolvedField); 1582 field_get = new (allocator_) HUnresolvedInstanceFieldGet(object, 1583 field_type, 1584 field_index, 1585 dex_pc); 1586 } else { 1587 uint16_t class_def_index = resolved_field->GetDeclaringClass()->GetDexClassDefIndex(); 1588 field_get = new (allocator_) HInstanceFieldGet(object, 1589 resolved_field, 1590 field_type, 1591 resolved_field->GetOffset(), 1592 resolved_field->IsVolatile(), 1593 field_index, 1594 class_def_index, 1595 *dex_file_, 1596 dex_pc); 1597 } 1598 AppendInstruction(field_get); 1599 UpdateLocal(source_or_dest_reg, field_get); 1600 } 1601 1602 return true; 1603 } 1604 1605 void HInstructionBuilder::BuildUnresolvedStaticFieldAccess(const Instruction& instruction, 1606 uint32_t dex_pc, 1607 bool is_put, 1608 DataType::Type field_type) { 1609 uint32_t source_or_dest_reg = instruction.VRegA_21c(); 1610 uint16_t field_index = instruction.VRegB_21c(); 1611 1612 if (is_put) { 1613 HInstruction* value = LoadLocal(source_or_dest_reg, field_type); 1614 AppendInstruction( 1615 new (allocator_) HUnresolvedStaticFieldSet(value, field_type, field_index, dex_pc)); 1616 } else { 1617 AppendInstruction(new (allocator_) HUnresolvedStaticFieldGet(field_type, field_index, dex_pc)); 1618 UpdateLocal(source_or_dest_reg, current_block_->GetLastInstruction()); 1619 } 1620 } 1621 1622 ArtField* HInstructionBuilder::ResolveField(uint16_t field_idx, bool is_static, bool is_put) { 1623 ScopedObjectAccess soa(Thread::Current()); 1624 1625 ClassLinker* class_linker = dex_compilation_unit_->GetClassLinker(); 1626 Handle<mirror::ClassLoader> class_loader = dex_compilation_unit_->GetClassLoader(); 1627 1628 ArtField* resolved_field = class_linker->ResolveField(field_idx, 1629 dex_compilation_unit_->GetDexCache(), 1630 class_loader, 1631 is_static); 1632 DCHECK_EQ(resolved_field == nullptr, soa.Self()->IsExceptionPending()); 1633 if (UNLIKELY(resolved_field == nullptr)) { 1634 // Clean up any exception left by field resolution. 1635 soa.Self()->ClearException(); 1636 return nullptr; 1637 } 1638 1639 // Check static/instance. The class linker has a fast path for looking into the dex cache 1640 // and does not check static/instance if it hits it. 1641 if (UNLIKELY(resolved_field->IsStatic() != is_static)) { 1642 return nullptr; 1643 } 1644 1645 // Check access. 1646 Handle<mirror::Class> compiling_class = dex_compilation_unit_->GetCompilingClass(); 1647 if (compiling_class == nullptr) { 1648 if (!resolved_field->IsPublic()) { 1649 return nullptr; 1650 } 1651 } else if (!compiling_class->CanAccessResolvedField(resolved_field->GetDeclaringClass(), 1652 resolved_field, 1653 dex_compilation_unit_->GetDexCache().Get(), 1654 field_idx)) { 1655 return nullptr; 1656 } 1657 1658 if (is_put && 1659 resolved_field->IsFinal() && 1660 (compiling_class.Get() != resolved_field->GetDeclaringClass())) { 1661 // Final fields can only be updated within their own class. 1662 // TODO: Only allow it in constructors. b/34966607. 1663 return nullptr; 1664 } 1665 1666 return resolved_field; 1667 } 1668 1669 void HInstructionBuilder::BuildStaticFieldAccess(const Instruction& instruction, 1670 uint32_t dex_pc, 1671 bool is_put) { 1672 uint32_t source_or_dest_reg = instruction.VRegA_21c(); 1673 uint16_t field_index = instruction.VRegB_21c(); 1674 1675 ScopedObjectAccess soa(Thread::Current()); 1676 ArtField* resolved_field = ResolveField(field_index, /* is_static= */ true, is_put); 1677 1678 if (resolved_field == nullptr) { 1679 MaybeRecordStat(compilation_stats_, 1680 MethodCompilationStat::kUnresolvedField); 1681 DataType::Type field_type = GetFieldAccessType(*dex_file_, field_index); 1682 BuildUnresolvedStaticFieldAccess(instruction, dex_pc, is_put, field_type); 1683 return; 1684 } 1685 1686 DataType::Type field_type = GetFieldAccessType(*dex_file_, field_index); 1687 1688 Handle<mirror::Class> klass = handles_->NewHandle(resolved_field->GetDeclaringClass()); 1689 HLoadClass* constant = BuildLoadClass(klass->GetDexTypeIndex(), 1690 klass->GetDexFile(), 1691 klass, 1692 dex_pc, 1693 /* needs_access_check= */ false); 1694 1695 if (constant == nullptr) { 1696 // The class cannot be referenced from this compiled code. Generate 1697 // an unresolved access. 1698 MaybeRecordStat(compilation_stats_, 1699 MethodCompilationStat::kUnresolvedFieldNotAFastAccess); 1700 BuildUnresolvedStaticFieldAccess(instruction, dex_pc, is_put, field_type); 1701 return; 1702 } 1703 1704 HInstruction* cls = constant; 1705 if (!IsInitialized(klass)) { 1706 cls = new (allocator_) HClinitCheck(constant, dex_pc); 1707 AppendInstruction(cls); 1708 } 1709 1710 uint16_t class_def_index = klass->GetDexClassDefIndex(); 1711 if (is_put) { 1712 // We need to keep the class alive before loading the value. 1713 HInstruction* value = LoadLocal(source_or_dest_reg, field_type); 1714 DCHECK_EQ(HPhi::ToPhiType(value->GetType()), HPhi::ToPhiType(field_type)); 1715 AppendInstruction(new (allocator_) HStaticFieldSet(cls, 1716 value, 1717 resolved_field, 1718 field_type, 1719 resolved_field->GetOffset(), 1720 resolved_field->IsVolatile(), 1721 field_index, 1722 class_def_index, 1723 *dex_file_, 1724 dex_pc)); 1725 } else { 1726 AppendInstruction(new (allocator_) HStaticFieldGet(cls, 1727 resolved_field, 1728 field_type, 1729 resolved_field->GetOffset(), 1730 resolved_field->IsVolatile(), 1731 field_index, 1732 class_def_index, 1733 *dex_file_, 1734 dex_pc)); 1735 UpdateLocal(source_or_dest_reg, current_block_->GetLastInstruction()); 1736 } 1737 } 1738 1739 void HInstructionBuilder::BuildCheckedDivRem(uint16_t out_vreg, 1740 uint16_t first_vreg, 1741 int64_t second_vreg_or_constant, 1742 uint32_t dex_pc, 1743 DataType::Type type, 1744 bool second_is_constant, 1745 bool isDiv) { 1746 DCHECK(type == DataType::Type::kInt32 || type == DataType::Type::kInt64); 1747 1748 HInstruction* first = LoadLocal(first_vreg, type); 1749 HInstruction* second = nullptr; 1750 if (second_is_constant) { 1751 if (type == DataType::Type::kInt32) { 1752 second = graph_->GetIntConstant(second_vreg_or_constant, dex_pc); 1753 } else { 1754 second = graph_->GetLongConstant(second_vreg_or_constant, dex_pc); 1755 } 1756 } else { 1757 second = LoadLocal(second_vreg_or_constant, type); 1758 } 1759 1760 if (!second_is_constant 1761 || (type == DataType::Type::kInt32 && second->AsIntConstant()->GetValue() == 0) 1762 || (type == DataType::Type::kInt64 && second->AsLongConstant()->GetValue() == 0)) { 1763 second = new (allocator_) HDivZeroCheck(second, dex_pc); 1764 AppendInstruction(second); 1765 } 1766 1767 if (isDiv) { 1768 AppendInstruction(new (allocator_) HDiv(type, first, second, dex_pc)); 1769 } else { 1770 AppendInstruction(new (allocator_) HRem(type, first, second, dex_pc)); 1771 } 1772 UpdateLocal(out_vreg, current_block_->GetLastInstruction()); 1773 } 1774 1775 void HInstructionBuilder::BuildArrayAccess(const Instruction& instruction, 1776 uint32_t dex_pc, 1777 bool is_put, 1778 DataType::Type anticipated_type) { 1779 uint8_t source_or_dest_reg = instruction.VRegA_23x(); 1780 uint8_t array_reg = instruction.VRegB_23x(); 1781 uint8_t index_reg = instruction.VRegC_23x(); 1782 1783 HInstruction* object = LoadNullCheckedLocal(array_reg, dex_pc); 1784 HInstruction* length = new (allocator_) HArrayLength(object, dex_pc); 1785 AppendInstruction(length); 1786 HInstruction* index = LoadLocal(index_reg, DataType::Type::kInt32); 1787 index = new (allocator_) HBoundsCheck(index, length, dex_pc); 1788 AppendInstruction(index); 1789 if (is_put) { 1790 HInstruction* value = LoadLocal(source_or_dest_reg, anticipated_type); 1791 // TODO: Insert a type check node if the type is Object. 1792 HArraySet* aset = new (allocator_) HArraySet(object, index, value, anticipated_type, dex_pc); 1793 ssa_builder_->MaybeAddAmbiguousArraySet(aset); 1794 AppendInstruction(aset); 1795 } else { 1796 HArrayGet* aget = new (allocator_) HArrayGet(object, index, anticipated_type, dex_pc); 1797 ssa_builder_->MaybeAddAmbiguousArrayGet(aget); 1798 AppendInstruction(aget); 1799 UpdateLocal(source_or_dest_reg, current_block_->GetLastInstruction()); 1800 } 1801 graph_->SetHasBoundsChecks(true); 1802 } 1803 1804 HNewArray* HInstructionBuilder::BuildNewArray(uint32_t dex_pc, 1805 dex::TypeIndex type_index, 1806 HInstruction* length) { 1807 HLoadClass* cls = BuildLoadClass(type_index, dex_pc); 1808 1809 const char* descriptor = dex_file_->GetTypeDescriptor(dex_file_->GetTypeId(type_index)); 1810 DCHECK_EQ(descriptor[0], '['); 1811 size_t component_type_shift = Primitive::ComponentSizeShift(Primitive::GetType(descriptor[1])); 1812 1813 HNewArray* new_array = new (allocator_) HNewArray(cls, length, dex_pc, component_type_shift); 1814 AppendInstruction(new_array); 1815 return new_array; 1816 } 1817 1818 HNewArray* HInstructionBuilder::BuildFilledNewArray(uint32_t dex_pc, 1819 dex::TypeIndex type_index, 1820 const InstructionOperands& operands) { 1821 const size_t number_of_operands = operands.GetNumberOfOperands(); 1822 HInstruction* length = graph_->GetIntConstant(number_of_operands, dex_pc); 1823 1824 HNewArray* new_array = BuildNewArray(dex_pc, type_index, length); 1825 const char* descriptor = dex_file_->StringByTypeIdx(type_index); 1826 DCHECK_EQ(descriptor[0], '[') << descriptor; 1827 char primitive = descriptor[1]; 1828 DCHECK(primitive == 'I' 1829 || primitive == 'L' 1830 || primitive == '[') << descriptor; 1831 bool is_reference_array = (primitive == 'L') || (primitive == '['); 1832 DataType::Type type = is_reference_array ? DataType::Type::kReference : DataType::Type::kInt32; 1833 1834 for (size_t i = 0; i < number_of_operands; ++i) { 1835 HInstruction* value = LoadLocal(operands.GetOperand(i), type); 1836 HInstruction* index = graph_->GetIntConstant(i, dex_pc); 1837 HArraySet* aset = new (allocator_) HArraySet(new_array, index, value, type, dex_pc); 1838 ssa_builder_->MaybeAddAmbiguousArraySet(aset); 1839 AppendInstruction(aset); 1840 } 1841 latest_result_ = new_array; 1842 1843 return new_array; 1844 } 1845 1846 template <typename T> 1847 void HInstructionBuilder::BuildFillArrayData(HInstruction* object, 1848 const T* data, 1849 uint32_t element_count, 1850 DataType::Type anticipated_type, 1851 uint32_t dex_pc) { 1852 for (uint32_t i = 0; i < element_count; ++i) { 1853 HInstruction* index = graph_->GetIntConstant(i, dex_pc); 1854 HInstruction* value = graph_->GetIntConstant(data[i], dex_pc); 1855 HArraySet* aset = new (allocator_) HArraySet(object, index, value, anticipated_type, dex_pc); 1856 ssa_builder_->MaybeAddAmbiguousArraySet(aset); 1857 AppendInstruction(aset); 1858 } 1859 } 1860 1861 void HInstructionBuilder::BuildFillArrayData(const Instruction& instruction, uint32_t dex_pc) { 1862 HInstruction* array = LoadNullCheckedLocal(instruction.VRegA_31t(), dex_pc); 1863 1864 int32_t payload_offset = instruction.VRegB_31t() + dex_pc; 1865 const Instruction::ArrayDataPayload* payload = 1866 reinterpret_cast<const Instruction::ArrayDataPayload*>( 1867 code_item_accessor_.Insns() + payload_offset); 1868 const uint8_t* data = payload->data; 1869 uint32_t element_count = payload->element_count; 1870 1871 if (element_count == 0u) { 1872 // For empty payload we emit only the null check above. 1873 return; 1874 } 1875 1876 HInstruction* length = new (allocator_) HArrayLength(array, dex_pc); 1877 AppendInstruction(length); 1878 1879 // Implementation of this DEX instruction seems to be that the bounds check is 1880 // done before doing any stores. 1881 HInstruction* last_index = graph_->GetIntConstant(payload->element_count - 1, dex_pc); 1882 AppendInstruction(new (allocator_) HBoundsCheck(last_index, length, dex_pc)); 1883 1884 switch (payload->element_width) { 1885 case 1: 1886 BuildFillArrayData(array, 1887 reinterpret_cast<const int8_t*>(data), 1888 element_count, 1889 DataType::Type::kInt8, 1890 dex_pc); 1891 break; 1892 case 2: 1893 BuildFillArrayData(array, 1894 reinterpret_cast<const int16_t*>(data), 1895 element_count, 1896 DataType::Type::kInt16, 1897 dex_pc); 1898 break; 1899 case 4: 1900 BuildFillArrayData(array, 1901 reinterpret_cast<const int32_t*>(data), 1902 element_count, 1903 DataType::Type::kInt32, 1904 dex_pc); 1905 break; 1906 case 8: 1907 BuildFillWideArrayData(array, 1908 reinterpret_cast<const int64_t*>(data), 1909 element_count, 1910 dex_pc); 1911 break; 1912 default: 1913 LOG(FATAL) << "Unknown element width for " << payload->element_width; 1914 } 1915 graph_->SetHasBoundsChecks(true); 1916 } 1917 1918 void HInstructionBuilder::BuildFillWideArrayData(HInstruction* object, 1919 const int64_t* data, 1920 uint32_t element_count, 1921 uint32_t dex_pc) { 1922 for (uint32_t i = 0; i < element_count; ++i) { 1923 HInstruction* index = graph_->GetIntConstant(i, dex_pc); 1924 HInstruction* value = graph_->GetLongConstant(data[i], dex_pc); 1925 HArraySet* aset = 1926 new (allocator_) HArraySet(object, index, value, DataType::Type::kInt64, dex_pc); 1927 ssa_builder_->MaybeAddAmbiguousArraySet(aset); 1928 AppendInstruction(aset); 1929 } 1930 } 1931 1932 void HInstructionBuilder::BuildLoadString(dex::StringIndex string_index, uint32_t dex_pc) { 1933 HLoadString* load_string = 1934 new (allocator_) HLoadString(graph_->GetCurrentMethod(), string_index, *dex_file_, dex_pc); 1935 HSharpening::ProcessLoadString(load_string, 1936 code_generator_, 1937 *dex_compilation_unit_, 1938 handles_); 1939 AppendInstruction(load_string); 1940 } 1941 1942 HLoadClass* HInstructionBuilder::BuildLoadClass(dex::TypeIndex type_index, uint32_t dex_pc) { 1943 ScopedObjectAccess soa(Thread::Current()); 1944 const DexFile& dex_file = *dex_compilation_unit_->GetDexFile(); 1945 Handle<mirror::Class> klass = ResolveClass(soa, type_index); 1946 bool needs_access_check = LoadClassNeedsAccessCheck(klass); 1947 return BuildLoadClass(type_index, dex_file, klass, dex_pc, needs_access_check); 1948 } 1949 1950 HLoadClass* HInstructionBuilder::BuildLoadClass(dex::TypeIndex type_index, 1951 const DexFile& dex_file, 1952 Handle<mirror::Class> klass, 1953 uint32_t dex_pc, 1954 bool needs_access_check) { 1955 // Try to find a reference in the compiling dex file. 1956 const DexFile* actual_dex_file = &dex_file; 1957 if (!IsSameDexFile(dex_file, *dex_compilation_unit_->GetDexFile())) { 1958 dex::TypeIndex local_type_index = 1959 klass->FindTypeIndexInOtherDexFile(*dex_compilation_unit_->GetDexFile()); 1960 if (local_type_index.IsValid()) { 1961 type_index = local_type_index; 1962 actual_dex_file = dex_compilation_unit_->GetDexFile(); 1963 } 1964 } 1965 1966 // Note: `klass` must be from `handles_`. 1967 bool is_referrers_class = 1968 (klass != nullptr) && (outer_compilation_unit_->GetCompilingClass().Get() == klass.Get()); 1969 HLoadClass* load_class = new (allocator_) HLoadClass( 1970 graph_->GetCurrentMethod(), 1971 type_index, 1972 *actual_dex_file, 1973 klass, 1974 is_referrers_class, 1975 dex_pc, 1976 needs_access_check); 1977 1978 HLoadClass::LoadKind load_kind = HSharpening::ComputeLoadClassKind(load_class, 1979 code_generator_, 1980 *dex_compilation_unit_); 1981 1982 if (load_kind == HLoadClass::LoadKind::kInvalid) { 1983 // We actually cannot reference this class, we're forced to bail. 1984 return nullptr; 1985 } 1986 // Load kind must be set before inserting the instruction into the graph. 1987 load_class->SetLoadKind(load_kind); 1988 AppendInstruction(load_class); 1989 return load_class; 1990 } 1991 1992 Handle<mirror::Class> HInstructionBuilder::ResolveClass(ScopedObjectAccess& soa, 1993 dex::TypeIndex type_index) { 1994 auto it = class_cache_.find(type_index); 1995 if (it != class_cache_.end()) { 1996 return it->second; 1997 } 1998 1999 ObjPtr<mirror::Class> klass = dex_compilation_unit_->GetClassLinker()->ResolveType( 2000 type_index, dex_compilation_unit_->GetDexCache(), dex_compilation_unit_->GetClassLoader()); 2001 DCHECK_EQ(klass == nullptr, soa.Self()->IsExceptionPending()); 2002 soa.Self()->ClearException(); // Clean up the exception left by type resolution if any. 2003 2004 Handle<mirror::Class> h_klass = handles_->NewHandle(klass); 2005 class_cache_.Put(type_index, h_klass); 2006 return h_klass; 2007 } 2008 2009 bool HInstructionBuilder::LoadClassNeedsAccessCheck(Handle<mirror::Class> klass) { 2010 if (klass == nullptr) { 2011 return true; 2012 } else if (klass->IsPublic()) { 2013 return false; 2014 } else { 2015 ObjPtr<mirror::Class> compiling_class = dex_compilation_unit_->GetCompilingClass().Get(); 2016 return compiling_class == nullptr || !compiling_class->CanAccess(klass.Get()); 2017 } 2018 } 2019 2020 void HInstructionBuilder::BuildLoadMethodHandle(uint16_t method_handle_index, uint32_t dex_pc) { 2021 const DexFile& dex_file = *dex_compilation_unit_->GetDexFile(); 2022 HLoadMethodHandle* load_method_handle = new (allocator_) HLoadMethodHandle( 2023 graph_->GetCurrentMethod(), method_handle_index, dex_file, dex_pc); 2024 AppendInstruction(load_method_handle); 2025 } 2026 2027 void HInstructionBuilder::BuildLoadMethodType(dex::ProtoIndex proto_index, uint32_t dex_pc) { 2028 const DexFile& dex_file = *dex_compilation_unit_->GetDexFile(); 2029 HLoadMethodType* load_method_type = 2030 new (allocator_) HLoadMethodType(graph_->GetCurrentMethod(), proto_index, dex_file, dex_pc); 2031 AppendInstruction(load_method_type); 2032 } 2033 2034 void HInstructionBuilder::BuildTypeCheck(const Instruction& instruction, 2035 uint8_t destination, 2036 uint8_t reference, 2037 dex::TypeIndex type_index, 2038 uint32_t dex_pc) { 2039 HInstruction* object = LoadLocal(reference, DataType::Type::kReference); 2040 2041 ScopedObjectAccess soa(Thread::Current()); 2042 const DexFile& dex_file = *dex_compilation_unit_->GetDexFile(); 2043 Handle<mirror::Class> klass = ResolveClass(soa, type_index); 2044 bool needs_access_check = LoadClassNeedsAccessCheck(klass); 2045 TypeCheckKind check_kind = HSharpening::ComputeTypeCheckKind( 2046 klass.Get(), code_generator_, needs_access_check); 2047 2048 HInstruction* class_or_null = nullptr; 2049 HIntConstant* bitstring_path_to_root = nullptr; 2050 HIntConstant* bitstring_mask = nullptr; 2051 if (check_kind == TypeCheckKind::kBitstringCheck) { 2052 // TODO: Allow using the bitstring check also if we need an access check. 2053 DCHECK(!needs_access_check); 2054 class_or_null = graph_->GetNullConstant(dex_pc); 2055 MutexLock subtype_check_lock(Thread::Current(), *Locks::subtype_check_lock_); 2056 uint32_t path_to_root = 2057 SubtypeCheck<ObjPtr<mirror::Class>>::GetEncodedPathToRootForTarget(klass.Get()); 2058 uint32_t mask = SubtypeCheck<ObjPtr<mirror::Class>>::GetEncodedPathToRootMask(klass.Get()); 2059 bitstring_path_to_root = graph_->GetIntConstant(static_cast<int32_t>(path_to_root), dex_pc); 2060 bitstring_mask = graph_->GetIntConstant(static_cast<int32_t>(mask), dex_pc); 2061 } else { 2062 class_or_null = BuildLoadClass(type_index, dex_file, klass, dex_pc, needs_access_check); 2063 } 2064 DCHECK(class_or_null != nullptr); 2065 2066 if (instruction.Opcode() == Instruction::INSTANCE_OF) { 2067 AppendInstruction(new (allocator_) HInstanceOf(object, 2068 class_or_null, 2069 check_kind, 2070 klass, 2071 dex_pc, 2072 allocator_, 2073 bitstring_path_to_root, 2074 bitstring_mask)); 2075 UpdateLocal(destination, current_block_->GetLastInstruction()); 2076 } else { 2077 DCHECK_EQ(instruction.Opcode(), Instruction::CHECK_CAST); 2078 // We emit a CheckCast followed by a BoundType. CheckCast is a statement 2079 // which may throw. If it succeeds BoundType sets the new type of `object` 2080 // for all subsequent uses. 2081 AppendInstruction( 2082 new (allocator_) HCheckCast(object, 2083 class_or_null, 2084 check_kind, 2085 klass, 2086 dex_pc, 2087 allocator_, 2088 bitstring_path_to_root, 2089 bitstring_mask)); 2090 AppendInstruction(new (allocator_) HBoundType(object, dex_pc)); 2091 UpdateLocal(reference, current_block_->GetLastInstruction()); 2092 } 2093 } 2094 2095 bool HInstructionBuilder::CanDecodeQuickenedInfo() const { 2096 return !quicken_info_.IsNull(); 2097 } 2098 2099 uint16_t HInstructionBuilder::LookupQuickenedInfo(uint32_t quicken_index) { 2100 DCHECK(CanDecodeQuickenedInfo()); 2101 return quicken_info_.GetData(quicken_index); 2102 } 2103 2104 bool HInstructionBuilder::ProcessDexInstruction(const Instruction& instruction, 2105 uint32_t dex_pc, 2106 size_t quicken_index) { 2107 switch (instruction.Opcode()) { 2108 case Instruction::CONST_4: { 2109 int32_t register_index = instruction.VRegA(); 2110 HIntConstant* constant = graph_->GetIntConstant(instruction.VRegB_11n(), dex_pc); 2111 UpdateLocal(register_index, constant); 2112 break; 2113 } 2114 2115 case Instruction::CONST_16: { 2116 int32_t register_index = instruction.VRegA(); 2117 HIntConstant* constant = graph_->GetIntConstant(instruction.VRegB_21s(), dex_pc); 2118 UpdateLocal(register_index, constant); 2119 break; 2120 } 2121 2122 case Instruction::CONST: { 2123 int32_t register_index = instruction.VRegA(); 2124 HIntConstant* constant = graph_->GetIntConstant(instruction.VRegB_31i(), dex_pc); 2125 UpdateLocal(register_index, constant); 2126 break; 2127 } 2128 2129 case Instruction::CONST_HIGH16: { 2130 int32_t register_index = instruction.VRegA(); 2131 HIntConstant* constant = graph_->GetIntConstant(instruction.VRegB_21h() << 16, dex_pc); 2132 UpdateLocal(register_index, constant); 2133 break; 2134 } 2135 2136 case Instruction::CONST_WIDE_16: { 2137 int32_t register_index = instruction.VRegA(); 2138 // Get 16 bits of constant value, sign extended to 64 bits. 2139 int64_t value = instruction.VRegB_21s(); 2140 value <<= 48; 2141 value >>= 48; 2142 HLongConstant* constant = graph_->GetLongConstant(value, dex_pc); 2143 UpdateLocal(register_index, constant); 2144 break; 2145 } 2146 2147 case Instruction::CONST_WIDE_32: { 2148 int32_t register_index = instruction.VRegA(); 2149 // Get 32 bits of constant value, sign extended to 64 bits. 2150 int64_t value = instruction.VRegB_31i(); 2151 value <<= 32; 2152 value >>= 32; 2153 HLongConstant* constant = graph_->GetLongConstant(value, dex_pc); 2154 UpdateLocal(register_index, constant); 2155 break; 2156 } 2157 2158 case Instruction::CONST_WIDE: { 2159 int32_t register_index = instruction.VRegA(); 2160 HLongConstant* constant = graph_->GetLongConstant(instruction.VRegB_51l(), dex_pc); 2161 UpdateLocal(register_index, constant); 2162 break; 2163 } 2164 2165 case Instruction::CONST_WIDE_HIGH16: { 2166 int32_t register_index = instruction.VRegA(); 2167 int64_t value = static_cast<int64_t>(instruction.VRegB_21h()) << 48; 2168 HLongConstant* constant = graph_->GetLongConstant(value, dex_pc); 2169 UpdateLocal(register_index, constant); 2170 break; 2171 } 2172 2173 // Note that the SSA building will refine the types. 2174 case Instruction::MOVE: 2175 case Instruction::MOVE_FROM16: 2176 case Instruction::MOVE_16: { 2177 HInstruction* value = LoadLocal(instruction.VRegB(), DataType::Type::kInt32); 2178 UpdateLocal(instruction.VRegA(), value); 2179 break; 2180 } 2181 2182 // Note that the SSA building will refine the types. 2183 case Instruction::MOVE_WIDE: 2184 case Instruction::MOVE_WIDE_FROM16: 2185 case Instruction::MOVE_WIDE_16: { 2186 HInstruction* value = LoadLocal(instruction.VRegB(), DataType::Type::kInt64); 2187 UpdateLocal(instruction.VRegA(), value); 2188 break; 2189 } 2190 2191 case Instruction::MOVE_OBJECT: 2192 case Instruction::MOVE_OBJECT_16: 2193 case Instruction::MOVE_OBJECT_FROM16: { 2194 // The verifier has no notion of a null type, so a move-object of constant 0 2195 // will lead to the same constant 0 in the destination register. To mimic 2196 // this behavior, we just pretend we haven't seen a type change (int to reference) 2197 // for the 0 constant and phis. We rely on our type propagation to eventually get the 2198 // types correct. 2199 uint32_t reg_number = instruction.VRegB(); 2200 HInstruction* value = (*current_locals_)[reg_number]; 2201 if (value->IsIntConstant()) { 2202 DCHECK_EQ(value->AsIntConstant()->GetValue(), 0); 2203 } else if (value->IsPhi()) { 2204 DCHECK(value->GetType() == DataType::Type::kInt32 || 2205 value->GetType() == DataType::Type::kReference); 2206 } else { 2207 value = LoadLocal(reg_number, DataType::Type::kReference); 2208 } 2209 UpdateLocal(instruction.VRegA(), value); 2210 break; 2211 } 2212 2213 case Instruction::RETURN_VOID_NO_BARRIER: 2214 case Instruction::RETURN_VOID: { 2215 BuildReturn(instruction, DataType::Type::kVoid, dex_pc); 2216 break; 2217 } 2218 2219 #define IF_XX(comparison, cond) \ 2220 case Instruction::IF_##cond: If_22t<comparison>(instruction, dex_pc); break; \ 2221 case Instruction::IF_##cond##Z: If_21t<comparison>(instruction, dex_pc); break 2222 2223 IF_XX(HEqual, EQ); 2224 IF_XX(HNotEqual, NE); 2225 IF_XX(HLessThan, LT); 2226 IF_XX(HLessThanOrEqual, LE); 2227 IF_XX(HGreaterThan, GT); 2228 IF_XX(HGreaterThanOrEqual, GE); 2229 2230 case Instruction::GOTO: 2231 case Instruction::GOTO_16: 2232 case Instruction::GOTO_32: { 2233 AppendInstruction(new (allocator_) HGoto(dex_pc)); 2234 current_block_ = nullptr; 2235 break; 2236 } 2237 2238 case Instruction::RETURN: { 2239 BuildReturn(instruction, return_type_, dex_pc); 2240 break; 2241 } 2242 2243 case Instruction::RETURN_OBJECT: { 2244 BuildReturn(instruction, return_type_, dex_pc); 2245 break; 2246 } 2247 2248 case Instruction::RETURN_WIDE: { 2249 BuildReturn(instruction, return_type_, dex_pc); 2250 break; 2251 } 2252 2253 case Instruction::INVOKE_DIRECT: 2254 case Instruction::INVOKE_INTERFACE: 2255 case Instruction::INVOKE_STATIC: 2256 case Instruction::INVOKE_SUPER: 2257 case Instruction::INVOKE_VIRTUAL: 2258 case Instruction::INVOKE_VIRTUAL_QUICK: { 2259 uint16_t method_idx; 2260 if (instruction.Opcode() == Instruction::INVOKE_VIRTUAL_QUICK) { 2261 if (!CanDecodeQuickenedInfo()) { 2262 VLOG(compiler) << "Not compiled: Could not decode quickened instruction " 2263 << instruction.Opcode(); 2264 return false; 2265 } 2266 method_idx = LookupQuickenedInfo(quicken_index); 2267 } else { 2268 method_idx = instruction.VRegB_35c(); 2269 } 2270 uint32_t args[5]; 2271 uint32_t number_of_vreg_arguments = instruction.GetVarArgs(args); 2272 VarArgsInstructionOperands operands(args, number_of_vreg_arguments); 2273 if (!BuildInvoke(instruction, dex_pc, method_idx, operands)) { 2274 return false; 2275 } 2276 break; 2277 } 2278 2279 case Instruction::INVOKE_DIRECT_RANGE: 2280 case Instruction::INVOKE_INTERFACE_RANGE: 2281 case Instruction::INVOKE_STATIC_RANGE: 2282 case Instruction::INVOKE_SUPER_RANGE: 2283 case Instruction::INVOKE_VIRTUAL_RANGE: 2284 case Instruction::INVOKE_VIRTUAL_RANGE_QUICK: { 2285 uint16_t method_idx; 2286 if (instruction.Opcode() == Instruction::INVOKE_VIRTUAL_RANGE_QUICK) { 2287 if (!CanDecodeQuickenedInfo()) { 2288 VLOG(compiler) << "Not compiled: Could not decode quickened instruction " 2289 << instruction.Opcode(); 2290 return false; 2291 } 2292 method_idx = LookupQuickenedInfo(quicken_index); 2293 } else { 2294 method_idx = instruction.VRegB_3rc(); 2295 } 2296 RangeInstructionOperands operands(instruction.VRegC(), instruction.VRegA_3rc()); 2297 if (!BuildInvoke(instruction, dex_pc, method_idx, operands)) { 2298 return false; 2299 } 2300 break; 2301 } 2302 2303 case Instruction::INVOKE_POLYMORPHIC: { 2304 uint16_t method_idx = instruction.VRegB_45cc(); 2305 dex::ProtoIndex proto_idx(instruction.VRegH_45cc()); 2306 uint32_t args[5]; 2307 uint32_t number_of_vreg_arguments = instruction.GetVarArgs(args); 2308 VarArgsInstructionOperands operands(args, number_of_vreg_arguments); 2309 return BuildInvokePolymorphic(dex_pc, method_idx, proto_idx, operands); 2310 } 2311 2312 case Instruction::INVOKE_POLYMORPHIC_RANGE: { 2313 uint16_t method_idx = instruction.VRegB_4rcc(); 2314 dex::ProtoIndex proto_idx(instruction.VRegH_4rcc()); 2315 RangeInstructionOperands operands(instruction.VRegC_4rcc(), instruction.VRegA_4rcc()); 2316 return BuildInvokePolymorphic(dex_pc, method_idx, proto_idx, operands); 2317 } 2318 2319 case Instruction::INVOKE_CUSTOM: { 2320 uint16_t call_site_idx = instruction.VRegB_35c(); 2321 uint32_t args[5]; 2322 uint32_t number_of_vreg_arguments = instruction.GetVarArgs(args); 2323 VarArgsInstructionOperands operands(args, number_of_vreg_arguments); 2324 return BuildInvokeCustom(dex_pc, call_site_idx, operands); 2325 } 2326 2327 case Instruction::INVOKE_CUSTOM_RANGE: { 2328 uint16_t call_site_idx = instruction.VRegB_3rc(); 2329 RangeInstructionOperands operands(instruction.VRegC_3rc(), instruction.VRegA_3rc()); 2330 return BuildInvokeCustom(dex_pc, call_site_idx, operands); 2331 } 2332 2333 case Instruction::NEG_INT: { 2334 Unop_12x<HNeg>(instruction, DataType::Type::kInt32, dex_pc); 2335 break; 2336 } 2337 2338 case Instruction::NEG_LONG: { 2339 Unop_12x<HNeg>(instruction, DataType::Type::kInt64, dex_pc); 2340 break; 2341 } 2342 2343 case Instruction::NEG_FLOAT: { 2344 Unop_12x<HNeg>(instruction, DataType::Type::kFloat32, dex_pc); 2345 break; 2346 } 2347 2348 case Instruction::NEG_DOUBLE: { 2349 Unop_12x<HNeg>(instruction, DataType::Type::kFloat64, dex_pc); 2350 break; 2351 } 2352 2353 case Instruction::NOT_INT: { 2354 Unop_12x<HNot>(instruction, DataType::Type::kInt32, dex_pc); 2355 break; 2356 } 2357 2358 case Instruction::NOT_LONG: { 2359 Unop_12x<HNot>(instruction, DataType::Type::kInt64, dex_pc); 2360 break; 2361 } 2362 2363 case Instruction::INT_TO_LONG: { 2364 Conversion_12x(instruction, DataType::Type::kInt32, DataType::Type::kInt64, dex_pc); 2365 break; 2366 } 2367 2368 case Instruction::INT_TO_FLOAT: { 2369 Conversion_12x(instruction, DataType::Type::kInt32, DataType::Type::kFloat32, dex_pc); 2370 break; 2371 } 2372 2373 case Instruction::INT_TO_DOUBLE: { 2374 Conversion_12x(instruction, DataType::Type::kInt32, DataType::Type::kFloat64, dex_pc); 2375 break; 2376 } 2377 2378 case Instruction::LONG_TO_INT: { 2379 Conversion_12x(instruction, DataType::Type::kInt64, DataType::Type::kInt32, dex_pc); 2380 break; 2381 } 2382 2383 case Instruction::LONG_TO_FLOAT: { 2384 Conversion_12x(instruction, DataType::Type::kInt64, DataType::Type::kFloat32, dex_pc); 2385 break; 2386 } 2387 2388 case Instruction::LONG_TO_DOUBLE: { 2389 Conversion_12x(instruction, DataType::Type::kInt64, DataType::Type::kFloat64, dex_pc); 2390 break; 2391 } 2392 2393 case Instruction::FLOAT_TO_INT: { 2394 Conversion_12x(instruction, DataType::Type::kFloat32, DataType::Type::kInt32, dex_pc); 2395 break; 2396 } 2397 2398 case Instruction::FLOAT_TO_LONG: { 2399 Conversion_12x(instruction, DataType::Type::kFloat32, DataType::Type::kInt64, dex_pc); 2400 break; 2401 } 2402 2403 case Instruction::FLOAT_TO_DOUBLE: { 2404 Conversion_12x(instruction, DataType::Type::kFloat32, DataType::Type::kFloat64, dex_pc); 2405 break; 2406 } 2407 2408 case Instruction::DOUBLE_TO_INT: { 2409 Conversion_12x(instruction, DataType::Type::kFloat64, DataType::Type::kInt32, dex_pc); 2410 break; 2411 } 2412 2413 case Instruction::DOUBLE_TO_LONG: { 2414 Conversion_12x(instruction, DataType::Type::kFloat64, DataType::Type::kInt64, dex_pc); 2415 break; 2416 } 2417 2418 case Instruction::DOUBLE_TO_FLOAT: { 2419 Conversion_12x(instruction, DataType::Type::kFloat64, DataType::Type::kFloat32, dex_pc); 2420 break; 2421 } 2422 2423 case Instruction::INT_TO_BYTE: { 2424 Conversion_12x(instruction, DataType::Type::kInt32, DataType::Type::kInt8, dex_pc); 2425 break; 2426 } 2427 2428 case Instruction::INT_TO_SHORT: { 2429 Conversion_12x(instruction, DataType::Type::kInt32, DataType::Type::kInt16, dex_pc); 2430 break; 2431 } 2432 2433 case Instruction::INT_TO_CHAR: { 2434 Conversion_12x(instruction, DataType::Type::kInt32, DataType::Type::kUint16, dex_pc); 2435 break; 2436 } 2437 2438 case Instruction::ADD_INT: { 2439 Binop_23x<HAdd>(instruction, DataType::Type::kInt32, dex_pc); 2440 break; 2441 } 2442 2443 case Instruction::ADD_LONG: { 2444 Binop_23x<HAdd>(instruction, DataType::Type::kInt64, dex_pc); 2445 break; 2446 } 2447 2448 case Instruction::ADD_DOUBLE: { 2449 Binop_23x<HAdd>(instruction, DataType::Type::kFloat64, dex_pc); 2450 break; 2451 } 2452 2453 case Instruction::ADD_FLOAT: { 2454 Binop_23x<HAdd>(instruction, DataType::Type::kFloat32, dex_pc); 2455 break; 2456 } 2457 2458 case Instruction::SUB_INT: { 2459 Binop_23x<HSub>(instruction, DataType::Type::kInt32, dex_pc); 2460 break; 2461 } 2462 2463 case Instruction::SUB_LONG: { 2464 Binop_23x<HSub>(instruction, DataType::Type::kInt64, dex_pc); 2465 break; 2466 } 2467 2468 case Instruction::SUB_FLOAT: { 2469 Binop_23x<HSub>(instruction, DataType::Type::kFloat32, dex_pc); 2470 break; 2471 } 2472 2473 case Instruction::SUB_DOUBLE: { 2474 Binop_23x<HSub>(instruction, DataType::Type::kFloat64, dex_pc); 2475 break; 2476 } 2477 2478 case Instruction::ADD_INT_2ADDR: { 2479 Binop_12x<HAdd>(instruction, DataType::Type::kInt32, dex_pc); 2480 break; 2481 } 2482 2483 case Instruction::MUL_INT: { 2484 Binop_23x<HMul>(instruction, DataType::Type::kInt32, dex_pc); 2485 break; 2486 } 2487 2488 case Instruction::MUL_LONG: { 2489 Binop_23x<HMul>(instruction, DataType::Type::kInt64, dex_pc); 2490 break; 2491 } 2492 2493 case Instruction::MUL_FLOAT: { 2494 Binop_23x<HMul>(instruction, DataType::Type::kFloat32, dex_pc); 2495 break; 2496 } 2497 2498 case Instruction::MUL_DOUBLE: { 2499 Binop_23x<HMul>(instruction, DataType::Type::kFloat64, dex_pc); 2500 break; 2501 } 2502 2503 case Instruction::DIV_INT: { 2504 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegB(), instruction.VRegC(), 2505 dex_pc, DataType::Type::kInt32, false, true); 2506 break; 2507 } 2508 2509 case Instruction::DIV_LONG: { 2510 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegB(), instruction.VRegC(), 2511 dex_pc, DataType::Type::kInt64, false, true); 2512 break; 2513 } 2514 2515 case Instruction::DIV_FLOAT: { 2516 Binop_23x<HDiv>(instruction, DataType::Type::kFloat32, dex_pc); 2517 break; 2518 } 2519 2520 case Instruction::DIV_DOUBLE: { 2521 Binop_23x<HDiv>(instruction, DataType::Type::kFloat64, dex_pc); 2522 break; 2523 } 2524 2525 case Instruction::REM_INT: { 2526 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegB(), instruction.VRegC(), 2527 dex_pc, DataType::Type::kInt32, false, false); 2528 break; 2529 } 2530 2531 case Instruction::REM_LONG: { 2532 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegB(), instruction.VRegC(), 2533 dex_pc, DataType::Type::kInt64, false, false); 2534 break; 2535 } 2536 2537 case Instruction::REM_FLOAT: { 2538 Binop_23x<HRem>(instruction, DataType::Type::kFloat32, dex_pc); 2539 break; 2540 } 2541 2542 case Instruction::REM_DOUBLE: { 2543 Binop_23x<HRem>(instruction, DataType::Type::kFloat64, dex_pc); 2544 break; 2545 } 2546 2547 case Instruction::AND_INT: { 2548 Binop_23x<HAnd>(instruction, DataType::Type::kInt32, dex_pc); 2549 break; 2550 } 2551 2552 case Instruction::AND_LONG: { 2553 Binop_23x<HAnd>(instruction, DataType::Type::kInt64, dex_pc); 2554 break; 2555 } 2556 2557 case Instruction::SHL_INT: { 2558 Binop_23x_shift<HShl>(instruction, DataType::Type::kInt32, dex_pc); 2559 break; 2560 } 2561 2562 case Instruction::SHL_LONG: { 2563 Binop_23x_shift<HShl>(instruction, DataType::Type::kInt64, dex_pc); 2564 break; 2565 } 2566 2567 case Instruction::SHR_INT: { 2568 Binop_23x_shift<HShr>(instruction, DataType::Type::kInt32, dex_pc); 2569 break; 2570 } 2571 2572 case Instruction::SHR_LONG: { 2573 Binop_23x_shift<HShr>(instruction, DataType::Type::kInt64, dex_pc); 2574 break; 2575 } 2576 2577 case Instruction::USHR_INT: { 2578 Binop_23x_shift<HUShr>(instruction, DataType::Type::kInt32, dex_pc); 2579 break; 2580 } 2581 2582 case Instruction::USHR_LONG: { 2583 Binop_23x_shift<HUShr>(instruction, DataType::Type::kInt64, dex_pc); 2584 break; 2585 } 2586 2587 case Instruction::OR_INT: { 2588 Binop_23x<HOr>(instruction, DataType::Type::kInt32, dex_pc); 2589 break; 2590 } 2591 2592 case Instruction::OR_LONG: { 2593 Binop_23x<HOr>(instruction, DataType::Type::kInt64, dex_pc); 2594 break; 2595 } 2596 2597 case Instruction::XOR_INT: { 2598 Binop_23x<HXor>(instruction, DataType::Type::kInt32, dex_pc); 2599 break; 2600 } 2601 2602 case Instruction::XOR_LONG: { 2603 Binop_23x<HXor>(instruction, DataType::Type::kInt64, dex_pc); 2604 break; 2605 } 2606 2607 case Instruction::ADD_LONG_2ADDR: { 2608 Binop_12x<HAdd>(instruction, DataType::Type::kInt64, dex_pc); 2609 break; 2610 } 2611 2612 case Instruction::ADD_DOUBLE_2ADDR: { 2613 Binop_12x<HAdd>(instruction, DataType::Type::kFloat64, dex_pc); 2614 break; 2615 } 2616 2617 case Instruction::ADD_FLOAT_2ADDR: { 2618 Binop_12x<HAdd>(instruction, DataType::Type::kFloat32, dex_pc); 2619 break; 2620 } 2621 2622 case Instruction::SUB_INT_2ADDR: { 2623 Binop_12x<HSub>(instruction, DataType::Type::kInt32, dex_pc); 2624 break; 2625 } 2626 2627 case Instruction::SUB_LONG_2ADDR: { 2628 Binop_12x<HSub>(instruction, DataType::Type::kInt64, dex_pc); 2629 break; 2630 } 2631 2632 case Instruction::SUB_FLOAT_2ADDR: { 2633 Binop_12x<HSub>(instruction, DataType::Type::kFloat32, dex_pc); 2634 break; 2635 } 2636 2637 case Instruction::SUB_DOUBLE_2ADDR: { 2638 Binop_12x<HSub>(instruction, DataType::Type::kFloat64, dex_pc); 2639 break; 2640 } 2641 2642 case Instruction::MUL_INT_2ADDR: { 2643 Binop_12x<HMul>(instruction, DataType::Type::kInt32, dex_pc); 2644 break; 2645 } 2646 2647 case Instruction::MUL_LONG_2ADDR: { 2648 Binop_12x<HMul>(instruction, DataType::Type::kInt64, dex_pc); 2649 break; 2650 } 2651 2652 case Instruction::MUL_FLOAT_2ADDR: { 2653 Binop_12x<HMul>(instruction, DataType::Type::kFloat32, dex_pc); 2654 break; 2655 } 2656 2657 case Instruction::MUL_DOUBLE_2ADDR: { 2658 Binop_12x<HMul>(instruction, DataType::Type::kFloat64, dex_pc); 2659 break; 2660 } 2661 2662 case Instruction::DIV_INT_2ADDR: { 2663 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegA(), instruction.VRegB(), 2664 dex_pc, DataType::Type::kInt32, false, true); 2665 break; 2666 } 2667 2668 case Instruction::DIV_LONG_2ADDR: { 2669 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegA(), instruction.VRegB(), 2670 dex_pc, DataType::Type::kInt64, false, true); 2671 break; 2672 } 2673 2674 case Instruction::REM_INT_2ADDR: { 2675 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegA(), instruction.VRegB(), 2676 dex_pc, DataType::Type::kInt32, false, false); 2677 break; 2678 } 2679 2680 case Instruction::REM_LONG_2ADDR: { 2681 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegA(), instruction.VRegB(), 2682 dex_pc, DataType::Type::kInt64, false, false); 2683 break; 2684 } 2685 2686 case Instruction::REM_FLOAT_2ADDR: { 2687 Binop_12x<HRem>(instruction, DataType::Type::kFloat32, dex_pc); 2688 break; 2689 } 2690 2691 case Instruction::REM_DOUBLE_2ADDR: { 2692 Binop_12x<HRem>(instruction, DataType::Type::kFloat64, dex_pc); 2693 break; 2694 } 2695 2696 case Instruction::SHL_INT_2ADDR: { 2697 Binop_12x_shift<HShl>(instruction, DataType::Type::kInt32, dex_pc); 2698 break; 2699 } 2700 2701 case Instruction::SHL_LONG_2ADDR: { 2702 Binop_12x_shift<HShl>(instruction, DataType::Type::kInt64, dex_pc); 2703 break; 2704 } 2705 2706 case Instruction::SHR_INT_2ADDR: { 2707 Binop_12x_shift<HShr>(instruction, DataType::Type::kInt32, dex_pc); 2708 break; 2709 } 2710 2711 case Instruction::SHR_LONG_2ADDR: { 2712 Binop_12x_shift<HShr>(instruction, DataType::Type::kInt64, dex_pc); 2713 break; 2714 } 2715 2716 case Instruction::USHR_INT_2ADDR: { 2717 Binop_12x_shift<HUShr>(instruction, DataType::Type::kInt32, dex_pc); 2718 break; 2719 } 2720 2721 case Instruction::USHR_LONG_2ADDR: { 2722 Binop_12x_shift<HUShr>(instruction, DataType::Type::kInt64, dex_pc); 2723 break; 2724 } 2725 2726 case Instruction::DIV_FLOAT_2ADDR: { 2727 Binop_12x<HDiv>(instruction, DataType::Type::kFloat32, dex_pc); 2728 break; 2729 } 2730 2731 case Instruction::DIV_DOUBLE_2ADDR: { 2732 Binop_12x<HDiv>(instruction, DataType::Type::kFloat64, dex_pc); 2733 break; 2734 } 2735 2736 case Instruction::AND_INT_2ADDR: { 2737 Binop_12x<HAnd>(instruction, DataType::Type::kInt32, dex_pc); 2738 break; 2739 } 2740 2741 case Instruction::AND_LONG_2ADDR: { 2742 Binop_12x<HAnd>(instruction, DataType::Type::kInt64, dex_pc); 2743 break; 2744 } 2745 2746 case Instruction::OR_INT_2ADDR: { 2747 Binop_12x<HOr>(instruction, DataType::Type::kInt32, dex_pc); 2748 break; 2749 } 2750 2751 case Instruction::OR_LONG_2ADDR: { 2752 Binop_12x<HOr>(instruction, DataType::Type::kInt64, dex_pc); 2753 break; 2754 } 2755 2756 case Instruction::XOR_INT_2ADDR: { 2757 Binop_12x<HXor>(instruction, DataType::Type::kInt32, dex_pc); 2758 break; 2759 } 2760 2761 case Instruction::XOR_LONG_2ADDR: { 2762 Binop_12x<HXor>(instruction, DataType::Type::kInt64, dex_pc); 2763 break; 2764 } 2765 2766 case Instruction::ADD_INT_LIT16: { 2767 Binop_22s<HAdd>(instruction, false, dex_pc); 2768 break; 2769 } 2770 2771 case Instruction::AND_INT_LIT16: { 2772 Binop_22s<HAnd>(instruction, false, dex_pc); 2773 break; 2774 } 2775 2776 case Instruction::OR_INT_LIT16: { 2777 Binop_22s<HOr>(instruction, false, dex_pc); 2778 break; 2779 } 2780 2781 case Instruction::XOR_INT_LIT16: { 2782 Binop_22s<HXor>(instruction, false, dex_pc); 2783 break; 2784 } 2785 2786 case Instruction::RSUB_INT: { 2787 Binop_22s<HSub>(instruction, true, dex_pc); 2788 break; 2789 } 2790 2791 case Instruction::MUL_INT_LIT16: { 2792 Binop_22s<HMul>(instruction, false, dex_pc); 2793 break; 2794 } 2795 2796 case Instruction::ADD_INT_LIT8: { 2797 Binop_22b<HAdd>(instruction, false, dex_pc); 2798 break; 2799 } 2800 2801 case Instruction::AND_INT_LIT8: { 2802 Binop_22b<HAnd>(instruction, false, dex_pc); 2803 break; 2804 } 2805 2806 case Instruction::OR_INT_LIT8: { 2807 Binop_22b<HOr>(instruction, false, dex_pc); 2808 break; 2809 } 2810 2811 case Instruction::XOR_INT_LIT8: { 2812 Binop_22b<HXor>(instruction, false, dex_pc); 2813 break; 2814 } 2815 2816 case Instruction::RSUB_INT_LIT8: { 2817 Binop_22b<HSub>(instruction, true, dex_pc); 2818 break; 2819 } 2820 2821 case Instruction::MUL_INT_LIT8: { 2822 Binop_22b<HMul>(instruction, false, dex_pc); 2823 break; 2824 } 2825 2826 case Instruction::DIV_INT_LIT16: 2827 case Instruction::DIV_INT_LIT8: { 2828 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegB(), instruction.VRegC(), 2829 dex_pc, DataType::Type::kInt32, true, true); 2830 break; 2831 } 2832 2833 case Instruction::REM_INT_LIT16: 2834 case Instruction::REM_INT_LIT8: { 2835 BuildCheckedDivRem(instruction.VRegA(), instruction.VRegB(), instruction.VRegC(), 2836 dex_pc, DataType::Type::kInt32, true, false); 2837 break; 2838 } 2839 2840 case Instruction::SHL_INT_LIT8: { 2841 Binop_22b<HShl>(instruction, false, dex_pc); 2842 break; 2843 } 2844 2845 case Instruction::SHR_INT_LIT8: { 2846 Binop_22b<HShr>(instruction, false, dex_pc); 2847 break; 2848 } 2849 2850 case Instruction::USHR_INT_LIT8: { 2851 Binop_22b<HUShr>(instruction, false, dex_pc); 2852 break; 2853 } 2854 2855 case Instruction::NEW_INSTANCE: { 2856 HNewInstance* new_instance = 2857 BuildNewInstance(dex::TypeIndex(instruction.VRegB_21c()), dex_pc); 2858 DCHECK(new_instance != nullptr); 2859 2860 UpdateLocal(instruction.VRegA(), current_block_->GetLastInstruction()); 2861 BuildConstructorFenceForAllocation(new_instance); 2862 break; 2863 } 2864 2865 case Instruction::NEW_ARRAY: { 2866 dex::TypeIndex type_index(instruction.VRegC_22c()); 2867 HInstruction* length = LoadLocal(instruction.VRegB_22c(), DataType::Type::kInt32); 2868 HNewArray* new_array = BuildNewArray(dex_pc, type_index, length); 2869 2870 UpdateLocal(instruction.VRegA_22c(), current_block_->GetLastInstruction()); 2871 BuildConstructorFenceForAllocation(new_array); 2872 break; 2873 } 2874 2875 case Instruction::FILLED_NEW_ARRAY: { 2876 dex::TypeIndex type_index(instruction.VRegB_35c()); 2877 uint32_t args[5]; 2878 uint32_t number_of_vreg_arguments = instruction.GetVarArgs(args); 2879 VarArgsInstructionOperands operands(args, number_of_vreg_arguments); 2880 HNewArray* new_array = BuildFilledNewArray(dex_pc, type_index, operands); 2881 BuildConstructorFenceForAllocation(new_array); 2882 break; 2883 } 2884 2885 case Instruction::FILLED_NEW_ARRAY_RANGE: { 2886 dex::TypeIndex type_index(instruction.VRegB_3rc()); 2887 RangeInstructionOperands operands(instruction.VRegC_3rc(), instruction.VRegA_3rc()); 2888 HNewArray* new_array = BuildFilledNewArray(dex_pc, type_index, operands); 2889 BuildConstructorFenceForAllocation(new_array); 2890 break; 2891 } 2892 2893 case Instruction::FILL_ARRAY_DATA: { 2894 BuildFillArrayData(instruction, dex_pc); 2895 break; 2896 } 2897 2898 case Instruction::MOVE_RESULT: 2899 case Instruction::MOVE_RESULT_WIDE: 2900 case Instruction::MOVE_RESULT_OBJECT: { 2901 DCHECK(latest_result_ != nullptr); 2902 UpdateLocal(instruction.VRegA(), latest_result_); 2903 latest_result_ = nullptr; 2904 break; 2905 } 2906 2907 case Instruction::CMP_LONG: { 2908 Binop_23x_cmp(instruction, DataType::Type::kInt64, ComparisonBias::kNoBias, dex_pc); 2909 break; 2910 } 2911 2912 case Instruction::CMPG_FLOAT: { 2913 Binop_23x_cmp(instruction, DataType::Type::kFloat32, ComparisonBias::kGtBias, dex_pc); 2914 break; 2915 } 2916 2917 case Instruction::CMPG_DOUBLE: { 2918 Binop_23x_cmp(instruction, DataType::Type::kFloat64, ComparisonBias::kGtBias, dex_pc); 2919 break; 2920 } 2921 2922 case Instruction::CMPL_FLOAT: { 2923 Binop_23x_cmp(instruction, DataType::Type::kFloat32, ComparisonBias::kLtBias, dex_pc); 2924 break; 2925 } 2926 2927 case Instruction::CMPL_DOUBLE: { 2928 Binop_23x_cmp(instruction, DataType::Type::kFloat64, ComparisonBias::kLtBias, dex_pc); 2929 break; 2930 } 2931 2932 case Instruction::NOP: 2933 break; 2934 2935 case Instruction::IGET: 2936 case Instruction::IGET_QUICK: 2937 case Instruction::IGET_WIDE: 2938 case Instruction::IGET_WIDE_QUICK: 2939 case Instruction::IGET_OBJECT: 2940 case Instruction::IGET_OBJECT_QUICK: 2941 case Instruction::IGET_BOOLEAN: 2942 case Instruction::IGET_BOOLEAN_QUICK: 2943 case Instruction::IGET_BYTE: 2944 case Instruction::IGET_BYTE_QUICK: 2945 case Instruction::IGET_CHAR: 2946 case Instruction::IGET_CHAR_QUICK: 2947 case Instruction::IGET_SHORT: 2948 case Instruction::IGET_SHORT_QUICK: { 2949 if (!BuildInstanceFieldAccess(instruction, dex_pc, /* is_put= */ false, quicken_index)) { 2950 return false; 2951 } 2952 break; 2953 } 2954 2955 case Instruction::IPUT: 2956 case Instruction::IPUT_QUICK: 2957 case Instruction::IPUT_WIDE: 2958 case Instruction::IPUT_WIDE_QUICK: 2959 case Instruction::IPUT_OBJECT: 2960 case Instruction::IPUT_OBJECT_QUICK: 2961 case Instruction::IPUT_BOOLEAN: 2962 case Instruction::IPUT_BOOLEAN_QUICK: 2963 case Instruction::IPUT_BYTE: 2964 case Instruction::IPUT_BYTE_QUICK: 2965 case Instruction::IPUT_CHAR: 2966 case Instruction::IPUT_CHAR_QUICK: 2967 case Instruction::IPUT_SHORT: 2968 case Instruction::IPUT_SHORT_QUICK: { 2969 if (!BuildInstanceFieldAccess(instruction, dex_pc, /* is_put= */ true, quicken_index)) { 2970 return false; 2971 } 2972 break; 2973 } 2974 2975 case Instruction::SGET: 2976 case Instruction::SGET_WIDE: 2977 case Instruction::SGET_OBJECT: 2978 case Instruction::SGET_BOOLEAN: 2979 case Instruction::SGET_BYTE: 2980 case Instruction::SGET_CHAR: 2981 case Instruction::SGET_SHORT: { 2982 BuildStaticFieldAccess(instruction, dex_pc, /* is_put= */ false); 2983 break; 2984 } 2985 2986 case Instruction::SPUT: 2987 case Instruction::SPUT_WIDE: 2988 case Instruction::SPUT_OBJECT: 2989 case Instruction::SPUT_BOOLEAN: 2990 case Instruction::SPUT_BYTE: 2991 case Instruction::SPUT_CHAR: 2992 case Instruction::SPUT_SHORT: { 2993 BuildStaticFieldAccess(instruction, dex_pc, /* is_put= */ true); 2994 break; 2995 } 2996 2997 #define ARRAY_XX(kind, anticipated_type) \ 2998 case Instruction::AGET##kind: { \ 2999 BuildArrayAccess(instruction, dex_pc, false, anticipated_type); \ 3000 break; \ 3001 } \ 3002 case Instruction::APUT##kind: { \ 3003 BuildArrayAccess(instruction, dex_pc, true, anticipated_type); \ 3004 break; \ 3005 } 3006 3007 ARRAY_XX(, DataType::Type::kInt32); 3008 ARRAY_XX(_WIDE, DataType::Type::kInt64); 3009 ARRAY_XX(_OBJECT, DataType::Type::kReference); 3010 ARRAY_XX(_BOOLEAN, DataType::Type::kBool); 3011 ARRAY_XX(_BYTE, DataType::Type::kInt8); 3012 ARRAY_XX(_CHAR, DataType::Type::kUint16); 3013 ARRAY_XX(_SHORT, DataType::Type::kInt16); 3014 3015 case Instruction::ARRAY_LENGTH: { 3016 HInstruction* object = LoadNullCheckedLocal(instruction.VRegB_12x(), dex_pc); 3017 AppendInstruction(new (allocator_) HArrayLength(object, dex_pc)); 3018 UpdateLocal(instruction.VRegA_12x(), current_block_->GetLastInstruction()); 3019 break; 3020 } 3021 3022 case Instruction::CONST_STRING: { 3023 dex::StringIndex string_index(instruction.VRegB_21c()); 3024 BuildLoadString(string_index, dex_pc); 3025 UpdateLocal(instruction.VRegA_21c(), current_block_->GetLastInstruction()); 3026 break; 3027 } 3028 3029 case Instruction::CONST_STRING_JUMBO: { 3030 dex::StringIndex string_index(instruction.VRegB_31c()); 3031 BuildLoadString(string_index, dex_pc); 3032 UpdateLocal(instruction.VRegA_31c(), current_block_->GetLastInstruction()); 3033 break; 3034 } 3035 3036 case Instruction::CONST_CLASS: { 3037 dex::TypeIndex type_index(instruction.VRegB_21c()); 3038 BuildLoadClass(type_index, dex_pc); 3039 UpdateLocal(instruction.VRegA_21c(), current_block_->GetLastInstruction()); 3040 break; 3041 } 3042 3043 case Instruction::CONST_METHOD_HANDLE: { 3044 uint16_t method_handle_idx = instruction.VRegB_21c(); 3045 BuildLoadMethodHandle(method_handle_idx, dex_pc); 3046 UpdateLocal(instruction.VRegA_21c(), current_block_->GetLastInstruction()); 3047 break; 3048 } 3049 3050 case Instruction::CONST_METHOD_TYPE: { 3051 dex::ProtoIndex proto_idx(instruction.VRegB_21c()); 3052 BuildLoadMethodType(proto_idx, dex_pc); 3053 UpdateLocal(instruction.VRegA_21c(), current_block_->GetLastInstruction()); 3054 break; 3055 } 3056 3057 case Instruction::MOVE_EXCEPTION: { 3058 AppendInstruction(new (allocator_) HLoadException(dex_pc)); 3059 UpdateLocal(instruction.VRegA_11x(), current_block_->GetLastInstruction()); 3060 AppendInstruction(new (allocator_) HClearException(dex_pc)); 3061 break; 3062 } 3063 3064 case Instruction::THROW: { 3065 HInstruction* exception = LoadLocal(instruction.VRegA_11x(), DataType::Type::kReference); 3066 AppendInstruction(new (allocator_) HThrow(exception, dex_pc)); 3067 // We finished building this block. Set the current block to null to avoid 3068 // adding dead instructions to it. 3069 current_block_ = nullptr; 3070 break; 3071 } 3072 3073 case Instruction::INSTANCE_OF: { 3074 uint8_t destination = instruction.VRegA_22c(); 3075 uint8_t reference = instruction.VRegB_22c(); 3076 dex::TypeIndex type_index(instruction.VRegC_22c()); 3077 BuildTypeCheck(instruction, destination, reference, type_index, dex_pc); 3078 break; 3079 } 3080 3081 case Instruction::CHECK_CAST: { 3082 uint8_t reference = instruction.VRegA_21c(); 3083 dex::TypeIndex type_index(instruction.VRegB_21c()); 3084 BuildTypeCheck(instruction, -1, reference, type_index, dex_pc); 3085 break; 3086 } 3087 3088 case Instruction::MONITOR_ENTER: { 3089 AppendInstruction(new (allocator_) HMonitorOperation( 3090 LoadLocal(instruction.VRegA_11x(), DataType::Type::kReference), 3091 HMonitorOperation::OperationKind::kEnter, 3092 dex_pc)); 3093 break; 3094 } 3095 3096 case Instruction::MONITOR_EXIT: { 3097 AppendInstruction(new (allocator_) HMonitorOperation( 3098 LoadLocal(instruction.VRegA_11x(), DataType::Type::kReference), 3099 HMonitorOperation::OperationKind::kExit, 3100 dex_pc)); 3101 break; 3102 } 3103 3104 case Instruction::SPARSE_SWITCH: 3105 case Instruction::PACKED_SWITCH: { 3106 BuildSwitch(instruction, dex_pc); 3107 break; 3108 } 3109 3110 case Instruction::UNUSED_3E: 3111 case Instruction::UNUSED_3F: 3112 case Instruction::UNUSED_40: 3113 case Instruction::UNUSED_41: 3114 case Instruction::UNUSED_42: 3115 case Instruction::UNUSED_43: 3116 case Instruction::UNUSED_79: 3117 case Instruction::UNUSED_7A: 3118 case Instruction::UNUSED_F3: 3119 case Instruction::UNUSED_F4: 3120 case Instruction::UNUSED_F5: 3121 case Instruction::UNUSED_F6: 3122 case Instruction::UNUSED_F7: 3123 case Instruction::UNUSED_F8: 3124 case Instruction::UNUSED_F9: { 3125 VLOG(compiler) << "Did not compile " 3126 << dex_file_->PrettyMethod(dex_compilation_unit_->GetDexMethodIndex()) 3127 << " because of unhandled instruction " 3128 << instruction.Name(); 3129 MaybeRecordStat(compilation_stats_, 3130 MethodCompilationStat::kNotCompiledUnhandledInstruction); 3131 return false; 3132 } 3133 } 3134 return true; 3135 } // NOLINT(readability/fn_size) 3136 3137 ObjPtr<mirror::Class> HInstructionBuilder::LookupResolvedType( 3138 dex::TypeIndex type_index, 3139 const DexCompilationUnit& compilation_unit) const { 3140 return compilation_unit.GetClassLinker()->LookupResolvedType( 3141 type_index, compilation_unit.GetDexCache().Get(), compilation_unit.GetClassLoader().Get()); 3142 } 3143 3144 ObjPtr<mirror::Class> HInstructionBuilder::LookupReferrerClass() const { 3145 // TODO: Cache the result in a Handle<mirror::Class>. 3146 const dex::MethodId& method_id = 3147 dex_compilation_unit_->GetDexFile()->GetMethodId(dex_compilation_unit_->GetDexMethodIndex()); 3148 return LookupResolvedType(method_id.class_idx_, *dex_compilation_unit_); 3149 } 3150 3151 } // namespace art 3152