| Index: runtime/vm/flow_graph_inliner.cc
|
| ===================================================================
|
| --- runtime/vm/flow_graph_inliner.cc (revision 38118)
|
| +++ runtime/vm/flow_graph_inliner.cc (working copy)
|
| @@ -1319,6 +1319,7 @@
|
| RedefinitionInstr(actual->Copy(isolate()));
|
| redefinition->set_ssa_temp_index(
|
| owner_->caller_graph()->alloc_ssa_temp_index());
|
| + redefinition->UpdateType(CompileType::FromCid(receiver_cid));
|
| redefinition->InsertAfter(callee_graph->graph_entry()->normal_entry());
|
| Definition* stub = (*call_data.parameter_stubs)[0];
|
| stub->ReplaceUsesWith(redefinition);
|
| @@ -1433,40 +1434,20 @@
|
| // 1. Guard the body with a class id check.
|
| if ((i == (inlined_variants_.length() - 1)) &&
|
| non_inlined_variants_.is_empty()) {
|
| - // If it is the last variant use a check class or check smi
|
| - // instruction which can deoptimize, followed unconditionally by the
|
| - // body. Check a redefinition of the receiver, to prevent the check
|
| - // from being hoisted.
|
| - RedefinitionInstr* redefinition =
|
| - new(isolate()) RedefinitionInstr(new(isolate()) Value(receiver));
|
| - redefinition->set_ssa_temp_index(
|
| + // If it is the last variant use a check class id instruction which can
|
| + // deoptimize, followed unconditionally by the body.
|
| + RedefinitionInstr* cid_redefinition =
|
| + new RedefinitionInstr(new(isolate()) Value(load_cid));
|
| + cid_redefinition->set_ssa_temp_index(
|
| owner_->caller_graph()->alloc_ssa_temp_index());
|
| - cursor = AppendInstruction(cursor, redefinition);
|
| - if (inlined_variants_[i].cid == kSmiCid) {
|
| - CheckSmiInstr* check_smi =
|
| - new CheckSmiInstr(new Value(redefinition),
|
| - call_->deopt_id(),
|
| - call_->token_pos());
|
| - check_smi->InheritDeoptTarget(isolate(), call_);
|
| - cursor = AppendInstruction(cursor, check_smi);
|
| - } else {
|
| - const ICData& old_checks = call_->ic_data();
|
| - const ICData& new_checks = ICData::ZoneHandle(
|
| - ICData::New(Function::Handle(old_checks.owner()),
|
| - String::Handle(old_checks.target_name()),
|
| - Array::Handle(old_checks.arguments_descriptor()),
|
| - old_checks.deopt_id(),
|
| - 1)); // Number of args tested.
|
| - new_checks.AddReceiverCheck(inlined_variants_[i].cid,
|
| - *inlined_variants_[i].target);
|
| - CheckClassInstr* check_class =
|
| - new CheckClassInstr(new Value(redefinition),
|
| - call_->deopt_id(),
|
| - new_checks,
|
| - call_->token_pos());
|
| - check_class->InheritDeoptTarget(isolate(), call_);
|
| - cursor = AppendInstruction(cursor, check_class);
|
| - }
|
| + cursor = AppendInstruction(cursor, cid_redefinition);
|
| + CheckClassIdInstr* check_class_id = new(isolate()) CheckClassIdInstr(
|
| + new(isolate()) Value(cid_redefinition),
|
| + inlined_variants_[i].cid,
|
| + call_->deopt_id());
|
| + check_class_id->InheritDeoptTarget(isolate(), call_);
|
| + cursor = AppendInstruction(cursor, check_class_id);
|
| +
|
| // The next instruction is the first instruction of the inlined body.
|
| // Handle the two possible cases (unshared and shared subsequent
|
| // predecessors) separately.
|
|
|