[vm/compiler] Move compiler state (CHA, deopt id) from Thread to a special class

Also move deopt id computation logic into a separate class and add a comment
explaining while deopt ids are incremented by 2.

Change-Id: Ife489be7d10c7198a8e7adf9e97e0c516d78ea55
Reviewed-on: https://dart-review.googlesource.com/72685
Commit-Queue: Vyacheslav Egorov <vegorov@google.com>
Reviewed-by: Martin Kustermann <kustermann@google.com>
This commit is contained in:
Vyacheslav Egorov
2018-09-03 16:01:24 +00:00
committed by commit-bot@chromium.org
parent d01d6f454c
commit 7558644bd6
51 changed files with 489 additions and 432 deletions
+2 -2
View File
@@ -4,6 +4,7 @@
#include "vm/code_descriptors.h"
#include "vm/compiler/compiler_state.h"
#include "vm/log.h"
namespace dart {
@@ -14,8 +15,7 @@ void DescriptorList::AddDescriptor(RawPcDescriptors::Kind kind,
TokenPosition token_pos,
intptr_t try_index) {
ASSERT((kind == RawPcDescriptors::kRuntimeCall) ||
(kind == RawPcDescriptors::kOther) ||
(deopt_id != Thread::kNoDeoptId));
(kind == RawPcDescriptors::kOther) || (deopt_id != DeoptId::kNone));
// When precompiling, we only use pc descriptors for exceptions.
if (!FLAG_precompiled_mode || try_index != -1) {
+31 -27
View File
@@ -13,6 +13,7 @@
#include "vm/compiler/backend/inliner.h"
#include "vm/compiler/backend/range_analysis.h"
#include "vm/compiler/cha.h"
#include "vm/compiler/compiler_state.h"
#include "vm/compiler/frontend/flow_graph_builder.h"
#include "vm/compiler/jit/compiler.h"
#include "vm/compiler/jit/jit_call_specializer.h"
@@ -302,7 +303,7 @@ Value* AotCallSpecializer::PrepareStaticOpInput(Value* input,
conversion = new (Z) SmiToDoubleInstr(input, call->token_pos());
} else if (FlowGraphCompiler::SupportsUnboxedInt64() &&
FlowGraphCompiler::CanConvertInt64ToDouble()) {
conversion = new (Z) Int64ToDoubleInstr(input, Thread::kNoDeoptId,
conversion = new (Z) Int64ToDoubleInstr(input, DeoptId::kNone,
Instruction::kNotSpeculative);
} else {
UNREACHABLE();
@@ -375,14 +376,14 @@ bool AotCallSpecializer::TryOptimizeInstanceCallUsingStaticTypes(
right_value = PrepareStaticOpInput(right_value, kMintCid, instr);
replacement = new (Z) RelationalOpInstr(
instr->token_pos(), op_kind, left_value, right_value, kMintCid,
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
} else {
// TODO(dartbug.com/30480): Figure out how to handle null in
// equality comparisons.
// replacement = new (Z) EqualityCompareInstr(
// instr->token_pos(), op_kind, left_value->CopyWithType(Z),
// right_value->CopyWithType(Z), kMintCid, Thread::kNoDeoptId);
// right_value->CopyWithType(Z), kMintCid, DeoptId::kNone);
replacement = new (Z) CheckedSmiComparisonInstr(
instr->token_kind(), left_value->CopyWithType(Z),
right_value->CopyWithType(Z), instr);
@@ -396,7 +397,7 @@ bool AotCallSpecializer::TryOptimizeInstanceCallUsingStaticTypes(
instr->token_pos(),
(op_kind == Token::kEQ) ? Token::kEQ_STRICT : Token::kNE_STRICT,
left_value->CopyWithType(Z), right_value->CopyWithType(Z),
/* number_check = */ false, Thread::kNoDeoptId);
/* number_check = */ false, DeoptId::kNone);
} else {
replacement = new (Z) CheckedSmiComparisonInstr(
instr->token_kind(), left_value->CopyWithType(Z),
@@ -415,7 +416,7 @@ bool AotCallSpecializer::TryOptimizeInstanceCallUsingStaticTypes(
right_value = PrepareStaticOpInput(right_value, kDoubleCid, instr);
replacement = new (Z) RelationalOpInstr(
instr->token_pos(), op_kind, left_value, right_value, kDoubleCid,
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
}
}
break;
@@ -444,7 +445,7 @@ bool AotCallSpecializer::TryOptimizeInstanceCallUsingStaticTypes(
// TODO(dartbug.com/30480): Enable 64-bit integer shifts.
// replacement = new ShiftInt64OpInstr(
// op_kind, left_value->CopyWithType(Z),
// right_value->CopyWithType(Z), Thread::kNoDeoptId);
// right_value->CopyWithType(Z), DeoptId::kNone);
replacement =
new (Z) CheckedSmiOpInstr(op_kind, left_value->CopyWithType(Z),
right_value->CopyWithType(Z), instr);
@@ -452,7 +453,7 @@ bool AotCallSpecializer::TryOptimizeInstanceCallUsingStaticTypes(
left_value = PrepareStaticOpInput(left_value, kMintCid, instr);
right_value = PrepareStaticOpInput(right_value, kMintCid, instr);
replacement = new (Z) BinaryInt64OpInstr(
op_kind, left_value, right_value, Thread::kNoDeoptId,
op_kind, left_value, right_value, DeoptId::kNone,
Instruction::kNotSpeculative);
}
} else {
@@ -472,7 +473,7 @@ bool AotCallSpecializer::TryOptimizeInstanceCallUsingStaticTypes(
left_value = PrepareStaticOpInput(left_value, kDoubleCid, instr);
right_value = PrepareStaticOpInput(right_value, kDoubleCid, instr);
replacement = new (Z) BinaryDoubleOpInstr(
op_kind, left_value, right_value, Thread::kNoDeoptId,
op_kind, left_value, right_value, DeoptId::kNone,
instr->token_pos(), Instruction::kNotSpeculative);
}
}
@@ -536,7 +537,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
right_value = PrepareStaticOpInput(right_value, kMintCid, instr);
replacement = new (Z) EqualityCompareInstr(
instr->token_pos(), op_kind, left_value, right_value, kMintCid,
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
}
break;
}
@@ -553,7 +554,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
right_value = PrepareStaticOpInput(right_value, kMintCid, instr);
replacement = new (Z) RelationalOpInstr(
instr->token_pos(), op_kind, left_value, right_value, kMintCid,
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
} else if (FlowGraphCompiler::SupportsUnboxedDoubles() &&
right_type->IsNullableDouble() &&
IsSupportedIntOperandForStaticDoubleOp(left_type)) {
@@ -561,7 +562,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
right_value = PrepareStaticOpInput(right_value, kDoubleCid, instr);
replacement = new (Z) RelationalOpInstr(
instr->token_pos(), op_kind, left_value, right_value, kDoubleCid,
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
}
break;
}
@@ -588,9 +589,9 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
if (right_type->IsNullableInt() && (op_kind != Token::kDIV)) {
left_value = PrepareReceiverOfDevirtualizedCall(left_value, kMintCid);
right_value = PrepareStaticOpInput(right_value, kMintCid, instr);
replacement = new (Z) BinaryInt64OpInstr(
op_kind, left_value, right_value, Thread::kNoDeoptId,
Instruction::kNotSpeculative);
replacement = new (Z)
BinaryInt64OpInstr(op_kind, left_value, right_value,
DeoptId::kNone, Instruction::kNotSpeculative);
} else if (FlowGraphCompiler::SupportsUnboxedDoubles() &&
right_type->IsNullableDouble() &&
IsSupportedIntOperandForStaticDoubleOp(left_type)) {
@@ -601,7 +602,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
left_value = PrepareStaticOpInput(left_value, kDoubleCid, instr);
right_value = PrepareStaticOpInput(right_value, kDoubleCid, instr);
replacement = new (Z) BinaryDoubleOpInstr(
op_kind, left_value, right_value, Thread::kNoDeoptId,
op_kind, left_value, right_value, DeoptId::kNone,
instr->token_pos(), Instruction::kNotSpeculative);
}
}
@@ -612,7 +613,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
Value* left_value = instr->PushArgumentAt(receiver_index)->value();
left_value = PrepareReceiverOfDevirtualizedCall(left_value, kMintCid);
replacement = new (Z)
UnaryInt64OpInstr(Token::kNEGATE, left_value, Thread::kNoDeoptId,
UnaryInt64OpInstr(Token::kNEGATE, left_value, DeoptId::kNone,
Instruction::kNotSpeculative);
break;
}
@@ -625,8 +626,8 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
if (right_type->IsNullableInt()) {
left_value = PrepareReceiverOfDevirtualizedCall(left_value, kMintCid);
right_value = PrepareStaticOpInput(right_value, kMintCid, instr);
replacement = new (Z) ShiftInt64OpInstr(
op_kind, left_value, right_value, Thread::kNoDeoptId);
replacement = new (Z) ShiftInt64OpInstr(op_kind, left_value,
right_value, DeoptId::kNone);
}
break;
}
@@ -650,7 +651,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
right_value = PrepareStaticOpInput(right_value, kDoubleCid, instr);
replacement = new (Z) EqualityCompareInstr(
instr->token_pos(), op_kind, left_value, right_value, kDoubleCid,
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
}
break;
}
@@ -667,7 +668,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
right_value = PrepareStaticOpInput(right_value, kDoubleCid, instr);
replacement = new (Z) RelationalOpInstr(
instr->token_pos(), op_kind, left_value, right_value, kDoubleCid,
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
}
break;
}
@@ -683,7 +684,7 @@ bool AotCallSpecializer::TryOptimizeStaticCallUsingStaticTypes(
PrepareReceiverOfDevirtualizedCall(left_value, kDoubleCid);
right_value = PrepareStaticOpInput(right_value, kDoubleCid, instr);
replacement = new (Z) BinaryDoubleOpInstr(
op_kind, left_value, right_value, Thread::kNoDeoptId,
op_kind, left_value, right_value, DeoptId::kNone,
instr->token_pos(), Instruction::kNotSpeculative);
}
break;
@@ -910,7 +911,8 @@ void AotCallSpecializer::VisitInstanceCall(InstanceCallInstr* instr) {
}
if (!receiver_class.IsNull()) {
GrowableArray<intptr_t> class_ids(6);
if (thread()->cha()->ConcreteSubclasses(receiver_class, &class_ids)) {
if (thread()->compiler_state().cha().ConcreteSubclasses(receiver_class,
&class_ids)) {
// First check if all subclasses end up calling the same method.
// If this is the case we will replace instance call with a direct
// static call.
@@ -960,7 +962,7 @@ void AotCallSpecializer::VisitInstanceCall(InstanceCallInstr* instr) {
// Create an ICData and map all previously seen classes (< i) to
// the computed single_target.
ic_data = ICData::New(function, instr->function_name(),
args_desc_array, Thread::kNoDeoptId,
args_desc_array, DeoptId::kNone,
/* args_tested = */ 1, ICData::kOptimized);
for (intptr_t j = 0; j < i; j++) {
ic_data.AddReceiverCheck(class_ids[j], single_target);
@@ -981,7 +983,7 @@ void AotCallSpecializer::VisitInstanceCall(InstanceCallInstr* instr) {
// Create fake IC data with the resolved target.
const ICData& ic_data = ICData::Handle(
ICData::New(flow_graph()->function(), instr->function_name(),
args_desc_array, Thread::kNoDeoptId,
args_desc_array, DeoptId::kNone,
/* args_tested = */ 1, ICData::kOptimized));
cls = single_target.Owner();
ic_data.AddReceiverCheck(cls.id(), single_target);
@@ -1082,7 +1084,8 @@ bool AotCallSpecializer::TryExpandCallThroughGetter(const Class& receiver_class,
call->token_pos(), getter_name, Token::kGET, get_arguments,
/*type_args_len=*/0,
/*argument_names=*/Object::empty_array(),
/*checked_argument_count=*/1, thread()->GetNextDeoptId());
/*checked_argument_count=*/1,
thread()->compiler_state().GetNextDeoptId());
// Arguments to the .call() are the same as arguments to the
// original call (including type arguments), but receiver
@@ -1102,7 +1105,8 @@ bool AotCallSpecializer::TryExpandCallThroughGetter(const Class& receiver_class,
InstanceCallInstr* invoke_call = new (Z) InstanceCallInstr(
call->token_pos(), Symbols::Call(), Token::kILLEGAL, call_arguments,
call->type_args_len(), call->argument_names(),
/*checked_argument_count=*/1, thread()->GetNextDeoptId());
/*checked_argument_count=*/1,
thread()->compiler_state().GetNextDeoptId());
// Insert all new instructions, except .call() invocation into the
// graph.
@@ -1185,7 +1189,7 @@ bool AotCallSpecializer::TryReplaceInstanceOfWithRangeCheck(
StrictCompareInstr* check_cid = new (Z)
StrictCompareInstr(call->token_pos(), Token::kEQ_STRICT,
new (Z) Value(left_cid), new (Z) Value(lower_cid),
/* number_check = */ false, Thread::kNoDeoptId);
/* number_check = */ false, DeoptId::kNone);
ReplaceCall(call, check_cid);
return true;
}
+3 -5
View File
@@ -22,6 +22,7 @@
#include "vm/compiler/backend/type_propagator.h"
#include "vm/compiler/cha.h"
#include "vm/compiler/compiler_pass.h"
#include "vm/compiler/compiler_state.h"
#include "vm/compiler/frontend/flow_graph_builder.h"
#include "vm/compiler/jit/compiler.h"
#include "vm/dart_entry.h"
@@ -883,7 +884,7 @@ void Precompiler::CollectCallbackFields() {
args_desc = ArgumentsDescriptor::New(0, // No type argument vector.
function.num_fixed_parameters());
cids.Clear();
if (T->cha()->ConcreteSubclasses(cls, &cids)) {
if (CHA::ConcreteSubclasses(cls, &cids)) {
for (intptr_t j = 0; j < cids.length(); ++j) {
subcls ^= I->class_table()->At(cids[j]);
if (subcls.is_allocated()) {
@@ -2832,16 +2833,13 @@ bool PrecompileParsedFunctionHelper::Compile(CompilationPipeline* pipeline) {
true, FLAG_max_speculative_inlining_attempts);
while (!done) {
DeoptIdScope deopt_id_scope(thread(), 0);
LongJumpScope jump;
const intptr_t val = setjmp(*jump.Set());
if (val == 0) {
FlowGraph* flow_graph = nullptr;
ZoneGrowableArray<const ICData*>* ic_data_array = nullptr;
// Class hierarchy analysis is registered with the thread in the
// constructor and unregisters itself upon destruction.
CHA cha(thread());
CompilerState compiler_state(thread());
// TimerScope needs an isolate to be properly terminated in case of a
// LongJump.
@@ -6,6 +6,7 @@
#if defined(TARGET_ARCH_DBC)
#include "vm/compiler/assembler/assembler.h"
#include "vm/compiler/compiler_state.h"
#include "vm/stack_frame.h"
#include "vm/unit_test.h"
@@ -83,7 +84,7 @@ static void MakeDummyInstanceCall(Assembler* assembler, const Object& result) {
Array::Handle(ArgumentsDescriptor::New(kTypeArgsLen, kNumArgs));
const ICData& ic_data = ICData::Handle(ICData::New(
dummy_instance_function, String::Handle(dummy_instance_function.name()),
dummy_arguments_descriptor, Thread::kNoDeoptId, 2, ICData::kInstance));
dummy_arguments_descriptor, DeoptId::kNone, 2, ICData::kInstance));
// Wire up the Function in the ICData.
GrowableArray<intptr_t> cids(2);
@@ -62,7 +62,7 @@ void BlockScheduler::AssignEdgeWeights() const {
if (Compiler::IsBackgroundCompilation() && ic_data_array.IsNull()) {
// Deferred loading cleared ic_data_array.
Compiler::AbortBackgroundCompilation(
Thread::kNoDeoptId, "BlockScheduler: ICData array cleared");
DeoptId::kNone, "BlockScheduler: ICData array cleared");
}
if (ic_data_array.IsNull()) {
DEBUG_ASSERT(Isolate::Current()->HasAttemptedReload());
+12 -15
View File
@@ -65,8 +65,8 @@ JoinEntryInstr* BranchSimplifier::ToJoinEntry(Zone* zone,
// Convert a target block into a join block. Branches will be duplicated
// so the former true and false targets become joins of the control flows
// from all the duplicated branches.
JoinEntryInstr* join = new (zone) JoinEntryInstr(
target->block_id(), target->try_index(), Thread::kNoDeoptId);
JoinEntryInstr* join = new (zone)
JoinEntryInstr(target->block_id(), target->try_index(), DeoptId::kNone);
join->InheritDeoptTarget(zone, target);
join->LinkTo(target->next());
join->set_last_instruction(target->last_instruction());
@@ -82,7 +82,7 @@ BranchInstr* BranchSimplifier::CloneBranch(Zone* zone,
ComparisonInstr* new_comparison =
comparison->CopyWithNewOperands(new_left, new_right);
BranchInstr* new_branch =
new (zone) BranchInstr(new_comparison, Thread::kNoDeoptId);
new (zone) BranchInstr(new_comparison, DeoptId::kNone);
return new_branch;
}
@@ -182,24 +182,21 @@ void BranchSimplifier::Simplify(FlowGraph* flow_graph) {
// Connect the branch to the true and false joins, via empty target
// blocks.
TargetEntryInstr* true_target =
new (zone) TargetEntryInstr(flow_graph->max_block_id() + 1,
block->try_index(), Thread::kNoDeoptId);
TargetEntryInstr* true_target = new (zone) TargetEntryInstr(
flow_graph->max_block_id() + 1, block->try_index(), DeoptId::kNone);
true_target->InheritDeoptTarget(zone, join_true);
TargetEntryInstr* false_target =
new (zone) TargetEntryInstr(flow_graph->max_block_id() + 2,
block->try_index(), Thread::kNoDeoptId);
TargetEntryInstr* false_target = new (zone) TargetEntryInstr(
flow_graph->max_block_id() + 2, block->try_index(), DeoptId::kNone);
false_target->InheritDeoptTarget(zone, join_false);
flow_graph->set_max_block_id(flow_graph->max_block_id() + 2);
*new_branch->true_successor_address() = true_target;
*new_branch->false_successor_address() = false_target;
GotoInstr* goto_true =
new (zone) GotoInstr(join_true, Thread::kNoDeoptId);
GotoInstr* goto_true = new (zone) GotoInstr(join_true, DeoptId::kNone);
goto_true->InheritDeoptTarget(zone, join_true);
true_target->LinkTo(goto_true);
true_target->set_last_instruction(goto_true);
GotoInstr* goto_false =
new (zone) GotoInstr(join_false, Thread::kNoDeoptId);
new (zone) GotoInstr(join_false, DeoptId::kNone);
goto_false->InheritDeoptTarget(zone, join_false);
false_target->LinkTo(goto_false);
false_target->set_last_instruction(goto_false);
@@ -302,9 +299,9 @@ void IfConverter::Simplify(FlowGraph* flow_graph) {
ComparisonInstr* new_comparison = comparison->CopyWithNewOperands(
comparison->left()->Copy(zone), comparison->right()->Copy(zone));
IfThenElseInstr* if_then_else = new (zone)
IfThenElseInstr(new_comparison, if_true->Copy(zone),
if_false->Copy(zone), Thread::kNoDeoptId);
IfThenElseInstr* if_then_else =
new (zone) IfThenElseInstr(new_comparison, if_true->Copy(zone),
if_false->Copy(zone), DeoptId::kNone);
flow_graph->InsertBefore(branch, if_then_else, NULL,
FlowGraph::kValue);
@@ -1302,7 +1302,7 @@ void ConstantPropagator::EliminateRedundantBranches() {
JoinEntryInstr* join = if_true->AsJoinEntry();
if (join->phis() == NULL) {
GotoInstr* jump =
new (Z) GotoInstr(if_true->AsJoinEntry(), Thread::kNoDeoptId);
new (Z) GotoInstr(if_true->AsJoinEntry(), DeoptId::kNone);
jump->InheritDeoptTarget(Z, branch);
Instruction* previous = branch->previous();
@@ -1444,8 +1444,8 @@ void ConstantPropagator::Transform() {
ASSERT(reachable_->Contains(if_false->preorder_number()));
ASSERT(if_false->parallel_move() == NULL);
ASSERT(if_false->loop_info() == NULL);
join = new (Z) JoinEntryInstr(
if_false->block_id(), if_false->try_index(), Thread::kNoDeoptId);
join = new (Z) JoinEntryInstr(if_false->block_id(),
if_false->try_index(), DeoptId::kNone);
join->InheritDeoptTarget(Z, if_false);
if_false->UnuseAllInputs();
next = if_false->next();
@@ -1453,7 +1453,7 @@ void ConstantPropagator::Transform() {
ASSERT(if_true->parallel_move() == NULL);
ASSERT(if_true->loop_info() == NULL);
join = new (Z) JoinEntryInstr(if_true->block_id(), if_true->try_index(),
Thread::kNoDeoptId);
DeoptId::kNone);
join->InheritDeoptTarget(Z, if_true);
if_true->UnuseAllInputs();
next = if_true->next();
@@ -1464,7 +1464,7 @@ void ConstantPropagator::Transform() {
// Drop the comparison, which does not have side effects as long
// as it is a strict compare (the only one we can determine is
// constant with the current analysis).
GotoInstr* jump = new (Z) GotoInstr(join, Thread::kNoDeoptId);
GotoInstr* jump = new (Z) GotoInstr(join, DeoptId::kNone);
jump->InheritDeoptTarget(Z, branch);
Instruction* previous = branch->previous();
+17 -16
View File
@@ -12,6 +12,7 @@
#include "vm/compiler/backend/il_printer.h"
#include "vm/compiler/backend/range_analysis.h"
#include "vm/compiler/cha.h"
#include "vm/compiler/compiler_state.h"
#include "vm/compiler/frontend/flow_graph_builder.h"
#include "vm/growable_array.h"
#include "vm/object_store.h"
@@ -507,8 +508,8 @@ FlowGraph::ToCheck FlowGraph::CheckForInstanceCall(
// has a null value are excluded above (to avoid throwing an exception
// on something valid, like null.hashCode).
intptr_t subclass_count = 0;
if (!thread()->cha()->HasOverride(receiver_class, method_name,
&subclass_count)) {
CHA& cha = thread()->compiler_state().cha();
if (!cha.HasOverride(receiver_class, method_name, &subclass_count)) {
if (FLAG_trace_cha) {
THR_Print(
" **(CHA) Instance call needs no class check since there "
@@ -516,7 +517,7 @@ FlowGraph::ToCheck FlowGraph::CheckForInstanceCall(
method_name.ToCString(), receiver_class.ToCString());
}
if (FLAG_use_cha_deopt) {
thread()->cha()->AddToGuardedClasses(receiver_class, subclass_count);
cha.AddToGuardedClasses(receiver_class, subclass_count);
}
return receiver_maybe_null ? ToCheck::kCheckNull : ToCheck::kNoCheck;
}
@@ -1115,7 +1116,7 @@ void FlowGraph::Rename(GrowableArray<PhiInstr*>* live_phis,
if (parsed_function().has_arg_desc_var()) {
Definition* defn =
new SpecialParameterInstr(SpecialParameterInstr::kArgDescriptor,
Thread::kNoDeoptId, graph_entry_);
DeoptId::kNone, graph_entry_);
AllocateSSAIndexes(defn);
AddToInitialDefinitions(defn);
env[ArgumentDescriptorEnvIndex()] = defn;
@@ -1193,10 +1194,10 @@ void FlowGraph::RenameRecursive(BlockEntryInstr* block_entry,
Definition* param = nullptr;
if (raw_exception_var_envindex == i) {
param = new SpecialParameterInstr(SpecialParameterInstr::kException,
Thread::kNoDeoptId, catch_entry);
DeoptId::kNone, catch_entry);
} else if (raw_stacktrace_var_envindex == i) {
param = new SpecialParameterInstr(SpecialParameterInstr::kStackTrace,
Thread::kNoDeoptId, catch_entry);
DeoptId::kNone, catch_entry);
} else {
param = new (zone()) ParameterInstr(i, block_entry);
}
@@ -1650,7 +1651,7 @@ void FlowGraph::InsertConversion(Representation from,
if (IsUnboxedInteger(from) && IsUnboxedInteger(to)) {
const intptr_t deopt_id = (to == kUnboxedInt32) && (deopt_target != NULL)
? deopt_target->DeoptimizationTarget()
: Thread::kNoDeoptId;
: DeoptId::kNone;
converted = new (Z)
UnboxedIntConverterInstr(from, to, use->CopyWithType(), deopt_id);
} else if ((from == kUnboxedInt32) && (to == kUnboxedDouble)) {
@@ -1659,13 +1660,13 @@ void FlowGraph::InsertConversion(Representation from,
CanConvertInt64ToDouble()) {
const intptr_t deopt_id = (deopt_target != NULL)
? deopt_target->DeoptimizationTarget()
: Thread::kNoDeoptId;
: DeoptId::kNone;
ASSERT(CanUnboxDouble());
converted = new Int64ToDoubleInstr(use->CopyWithType(), deopt_id);
} else if ((from == kTagged) && Boxing::Supports(to)) {
const intptr_t deopt_id = (deopt_target != NULL)
? deopt_target->DeoptimizationTarget()
: Thread::kNoDeoptId;
: DeoptId::kNone;
converted = UnboxInstr::Create(to, use->CopyWithType(), deopt_id,
use->instruction()->speculative_mode());
} else if ((to == kTagged) && Boxing::Supports(from)) {
@@ -1677,7 +1678,7 @@ void FlowGraph::InsertConversion(Representation from,
// trigger a deoptimization if executed. See #12417 for a discussion.
const intptr_t deopt_id = (deopt_target != NULL)
? deopt_target->DeoptimizationTarget()
: Thread::kNoDeoptId;
: DeoptId::kNone;
ASSERT(Boxing::Supports(from));
ASSERT(Boxing::Supports(to));
Definition* boxed = BoxInstr::Create(from, use->CopyWithType());
@@ -2277,7 +2278,7 @@ void FlowGraph::OptimizeLeftShiftBitAndSmiOp(
// Replace Mint op with Smi op.
BinarySmiOpInstr* smi_op = new (Z) BinarySmiOpInstr(
Token::kBIT_AND, new (Z) Value(left_instr), new (Z) Value(right_instr),
Thread::kNoDeoptId); // BIT_AND cannot deoptimize.
DeoptId::kNone); // BIT_AND cannot deoptimize.
bit_and_instr->ReplaceWith(smi_op, current_iterator);
}
}
@@ -2369,7 +2370,7 @@ void FlowGraph::AppendExtractNthOutputForMerged(Definition* instr,
static TargetEntryInstr* NewTarget(FlowGraph* graph, Instruction* inherit) {
TargetEntryInstr* target = new (graph->zone())
TargetEntryInstr(graph->allocate_block_id(),
inherit->GetBlock()->try_index(), Thread::kNoDeoptId);
inherit->GetBlock()->try_index(), DeoptId::kNone);
target->InheritDeoptTarget(graph->zone(), inherit);
return target;
}
@@ -2377,7 +2378,7 @@ static TargetEntryInstr* NewTarget(FlowGraph* graph, Instruction* inherit) {
static JoinEntryInstr* NewJoin(FlowGraph* graph, Instruction* inherit) {
JoinEntryInstr* join = new (graph->zone())
JoinEntryInstr(graph->allocate_block_id(),
inherit->GetBlock()->try_index(), Thread::kNoDeoptId);
inherit->GetBlock()->try_index(), DeoptId::kNone);
join->InheritDeoptTarget(graph->zone(), inherit);
return join;
}
@@ -2385,7 +2386,7 @@ static JoinEntryInstr* NewJoin(FlowGraph* graph, Instruction* inherit) {
static GotoInstr* NewGoto(FlowGraph* graph,
JoinEntryInstr* target,
Instruction* inherit) {
GotoInstr* got = new (graph->zone()) GotoInstr(target, Thread::kNoDeoptId);
GotoInstr* got = new (graph->zone()) GotoInstr(target, DeoptId::kNone);
got->InheritDeoptTarget(graph->zone(), inherit);
return got;
}
@@ -2393,7 +2394,7 @@ static GotoInstr* NewGoto(FlowGraph* graph,
static BranchInstr* NewBranch(FlowGraph* graph,
ComparisonInstr* cmp,
Instruction* inherit) {
BranchInstr* bra = new (graph->zone()) BranchInstr(cmp, Thread::kNoDeoptId);
BranchInstr* bra = new (graph->zone()) BranchInstr(cmp, DeoptId::kNone);
bra->InheritDeoptTarget(graph->zone(), inherit);
return bra;
}
@@ -2475,7 +2476,7 @@ JoinEntryInstr* FlowGraph::NewDiamond(Instruction* instruction,
StrictCompareInstr* circuit = new (zone()) StrictCompareInstr(
inherit->token_pos(), Token::kEQ_STRICT, new (zone()) Value(phi),
new (zone()) Value(GetConstant(Bool::True())), false,
Thread::kNoDeoptId); // don't inherit
DeoptId::kNone); // don't inherit
// Return new blocks through the second diamond.
return NewDiamond(mid_point, inherit, circuit, b_true, b_false);
@@ -149,7 +149,7 @@ FlowGraphCompiler::FlowGraphCompiler(
// No need to collect extra ICData objects created during compilation.
deopt_id_to_ic_data_ = nullptr;
} else {
const intptr_t len = thread()->deopt_id();
const intptr_t len = thread()->compiler_state().deopt_id();
deopt_id_to_ic_data_->EnsureLength(len, nullptr);
}
ASSERT(assembler != NULL);
@@ -425,10 +425,10 @@ void FlowGraphCompiler::EmitCallsiteMetadata(TokenPosition token_pos,
AddCurrentDescriptor(kind, deopt_id, token_pos);
RecordSafepoint(locs);
EmitCatchEntryState();
if (deopt_id != Thread::kNoDeoptId) {
if (deopt_id != DeoptId::kNone) {
// Marks either the continuation point in unoptimized code or the
// deoptimization point in optimized code, after call.
const intptr_t deopt_id_after = Thread::ToDeoptAfter(deopt_id);
const intptr_t deopt_id_after = DeoptId::ToDeoptAfter(deopt_id);
if (is_optimizing()) {
AddDeoptIndexAtCall(deopt_id_after);
} else {
@@ -1147,7 +1147,7 @@ void FlowGraphCompiler::GenerateCallWithDeopt(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
GenerateCall(token_pos, stub_entry, kind, locs);
const intptr_t deopt_id_after = Thread::ToDeoptAfter(deopt_id);
const intptr_t deopt_id_after = DeoptId::ToDeoptAfter(deopt_id);
if (is_optimizing()) {
AddDeoptIndexAtCall(deopt_id_after);
} else {
@@ -2209,7 +2209,7 @@ void ThrowErrorSlowPathCode::EmitNativeCode(FlowGraphCompiler* compiler) {
__ CallRuntime(runtime_entry_, num_args_);
}
// Can't query deopt_id() without checking if instruction can deoptimize...
intptr_t deopt_id = Thread::kNoDeoptId;
intptr_t deopt_id = DeoptId::kNone;
if (instruction()->CanDeoptimize() ||
instruction()->CanBecomeDeoptimizationTarget()) {
deopt_id = instruction()->deopt_id();
@@ -118,7 +118,7 @@ RawTypedData* CompilerDeoptInfo::CreateDeoptInfo(FlowGraphCompiler* compiler,
// For any outer environment the deopt id is that of the call instruction
// which is recorded in the outer environment.
builder->AddReturnAddress(current->function(),
Thread::ToDeoptAfter(current->deopt_id()),
DeoptId::ToDeoptAfter(current->deopt_id()),
slot_ix++);
// The values of outgoing arguments can be changed from the inlined call so
@@ -921,7 +921,7 @@ void FlowGraphCompiler::GenerateCall(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
__ BranchLink(stub_entry);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, kind, locs);
EmitCallsiteMetadata(token_pos, DeoptId::kNone, kind, locs);
AddStubCallTarget(Code::ZoneHandle(stub_entry.code()));
}
@@ -930,7 +930,7 @@ void FlowGraphCompiler::GeneratePatchableCall(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
__ BranchLinkPatchable(stub_entry);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, kind, locs);
EmitCallsiteMetadata(token_pos, DeoptId::kNone, kind, locs);
}
void FlowGraphCompiler::GenerateDartCall(intptr_t deopt_id,
@@ -1045,7 +1045,7 @@ void FlowGraphCompiler::EmitMegamorphicInstanceCall(
__ blx(LR);
RecordSafepoint(locs, slow_path_argument_count);
const intptr_t deopt_id_after = Thread::ToDeoptAfter(deopt_id);
const intptr_t deopt_id_after = DeoptId::ToDeoptAfter(deopt_id);
if (FLAG_precompiled_mode) {
// Megamorphic calls may occur in slow path stubs.
// If valid use try_index argument.
@@ -1053,14 +1053,12 @@ void FlowGraphCompiler::EmitMegamorphicInstanceCall(
try_index = CurrentTryIndex();
}
AddDescriptor(RawPcDescriptors::kOther, assembler()->CodeSize(),
Thread::kNoDeoptId, token_pos, try_index);
DeoptId::kNone, token_pos, try_index);
} else if (is_optimizing()) {
AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
token_pos);
AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone, token_pos);
AddDeoptIndexAtCall(deopt_id_after);
} else {
AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
token_pos);
AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone, token_pos);
// Add deoptimization continuation point after the call and before the
// arguments are removed.
AddCurrentDescriptor(RawPcDescriptors::kDeopt, deopt_id_after, token_pos);
@@ -1086,7 +1084,7 @@ void FlowGraphCompiler::EmitSwitchableInstanceCall(const ICData& ic_data,
__ LoadUniqueObject(R9, ic_data);
__ blx(LR);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, RawPcDescriptors::kOther,
EmitCallsiteMetadata(token_pos, DeoptId::kNone, RawPcDescriptors::kOther,
locs);
__ Drop(ic_data.CountWithTypeArgs());
}
@@ -115,7 +115,7 @@ RawTypedData* CompilerDeoptInfo::CreateDeoptInfo(FlowGraphCompiler* compiler,
// For any outer environment the deopt id is that of the call instruction
// which is recorded in the outer environment.
builder->AddReturnAddress(current->function(),
Thread::ToDeoptAfter(current->deopt_id()),
DeoptId::ToDeoptAfter(current->deopt_id()),
slot_ix++);
// The values of outgoing arguments can be changed from the inlined call so
@@ -900,7 +900,7 @@ void FlowGraphCompiler::GenerateCall(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
__ BranchLink(stub_entry);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, kind, locs);
EmitCallsiteMetadata(token_pos, DeoptId::kNone, kind, locs);
AddStubCallTarget(Code::ZoneHandle(stub_entry.code()));
}
@@ -909,7 +909,7 @@ void FlowGraphCompiler::GeneratePatchableCall(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
__ BranchLinkPatchable(stub_entry);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, kind, locs);
EmitCallsiteMetadata(token_pos, DeoptId::kNone, kind, locs);
}
void FlowGraphCompiler::GenerateDartCall(intptr_t deopt_id,
@@ -1021,7 +1021,7 @@ void FlowGraphCompiler::EmitMegamorphicInstanceCall(
__ blr(LR);
RecordSafepoint(locs, slow_path_argument_count);
const intptr_t deopt_id_after = Thread::ToDeoptAfter(deopt_id);
const intptr_t deopt_id_after = DeoptId::ToDeoptAfter(deopt_id);
if (FLAG_precompiled_mode) {
// Megamorphic calls may occur in slow path stubs.
// If valid use try_index argument.
@@ -1029,14 +1029,12 @@ void FlowGraphCompiler::EmitMegamorphicInstanceCall(
try_index = CurrentTryIndex();
}
AddDescriptor(RawPcDescriptors::kOther, assembler()->CodeSize(),
Thread::kNoDeoptId, token_pos, try_index);
DeoptId::kNone, token_pos, try_index);
} else if (is_optimizing()) {
AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
token_pos);
AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone, token_pos);
AddDeoptIndexAtCall(deopt_id_after);
} else {
AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
token_pos);
AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone, token_pos);
// Add deoptimization continuation point after the call and before the
// arguments are removed.
AddCurrentDescriptor(RawPcDescriptors::kDeopt, deopt_id_after, token_pos);
@@ -1061,7 +1059,7 @@ void FlowGraphCompiler::EmitSwitchableInstanceCall(const ICData& ic_data,
__ LoadUniqueObject(R5, ic_data);
__ blr(TMP);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, RawPcDescriptors::kOther,
EmitCallsiteMetadata(token_pos, DeoptId::kNone, RawPcDescriptors::kOther,
locs);
__ Drop(ic_data.CountWithTypeArgs());
}
@@ -129,7 +129,7 @@ RawTypedData* CompilerDeoptInfo::CreateDeoptInfo(FlowGraphCompiler* compiler,
// For any outer environment the deopt id is that of the call instruction
// which is recorded in the outer environment.
builder->AddReturnAddress(current->function(),
Thread::ToDeoptAfter(current->deopt_id()),
DeoptId::ToDeoptAfter(current->deopt_id()),
slot_ix++);
builder->AddPcMarker(previous->function(), slot_ix++);
@@ -179,7 +179,7 @@ void FlowGraphCompiler::RecordAfterCallHelper(TokenPosition token_pos,
RecordSafepoint(locs);
// Marks either the continuation point in unoptimized code or the
// deoptimization point in optimized code, after call.
const intptr_t deopt_id_after = Thread::ToDeoptAfter(deopt_id);
const intptr_t deopt_id_after = DeoptId::ToDeoptAfter(deopt_id);
if (is_optimizing()) {
// Return/ReturnTOS instruction drops incoming arguments so
// we have to drop outgoing arguments from the innermost environment.
@@ -116,7 +116,7 @@ RawTypedData* CompilerDeoptInfo::CreateDeoptInfo(FlowGraphCompiler* compiler,
// For any outer environment the deopt id is that of the call instruction
// which is recorded in the outer environment.
builder->AddReturnAddress(current->function(),
Thread::ToDeoptAfter(current->deopt_id()),
DeoptId::ToDeoptAfter(current->deopt_id()),
slot_ix++);
// The values of outgoing arguments can be changed from the inlined call so
@@ -851,7 +851,7 @@ void FlowGraphCompiler::GenerateCall(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
__ Call(stub_entry);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, kind, locs);
EmitCallsiteMetadata(token_pos, DeoptId::kNone, kind, locs);
AddStubCallTarget(Code::ZoneHandle(stub_entry.code()));
}
@@ -967,9 +967,9 @@ void FlowGraphCompiler::EmitMegamorphicInstanceCall(
__ call(Address(THR, Thread::megamorphic_call_checked_entry_offset()));
__ call(EBX);
AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId, token_pos);
AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone, token_pos);
RecordSafepoint(locs, slow_path_argument_count);
const intptr_t deopt_id_after = Thread::ToDeoptAfter(deopt_id);
const intptr_t deopt_id_after = DeoptId::ToDeoptAfter(deopt_id);
// Precompilation not implemented on ia32 platform.
ASSERT(!FLAG_precompiled_mode);
if (is_optimizing()) {
@@ -115,7 +115,7 @@ RawTypedData* CompilerDeoptInfo::CreateDeoptInfo(FlowGraphCompiler* compiler,
// For any outer environment the deopt id is that of the call instruction
// which is recorded in the outer environment.
builder->AddReturnAddress(current->function(),
Thread::ToDeoptAfter(current->deopt_id()),
DeoptId::ToDeoptAfter(current->deopt_id()),
slot_ix++);
// The values of outgoing arguments can be changed from the inlined call so
@@ -912,7 +912,7 @@ void FlowGraphCompiler::GenerateCall(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
__ Call(stub_entry);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, kind, locs);
EmitCallsiteMetadata(token_pos, DeoptId::kNone, kind, locs);
AddStubCallTarget(Code::ZoneHandle(stub_entry.code()));
}
@@ -921,7 +921,7 @@ void FlowGraphCompiler::GeneratePatchableCall(TokenPosition token_pos,
RawPcDescriptors::Kind kind,
LocationSummary* locs) {
__ CallPatchable(stub_entry);
EmitCallsiteMetadata(token_pos, Thread::kNoDeoptId, kind, locs);
EmitCallsiteMetadata(token_pos, DeoptId::kNone, kind, locs);
}
void FlowGraphCompiler::GenerateDartCall(intptr_t deopt_id,
@@ -1037,7 +1037,7 @@ void FlowGraphCompiler::EmitMegamorphicInstanceCall(
__ call(Address(THR, Thread::megamorphic_call_checked_entry_offset()));
RecordSafepoint(locs, slow_path_argument_count);
const intptr_t deopt_id_after = Thread::ToDeoptAfter(deopt_id);
const intptr_t deopt_id_after = DeoptId::ToDeoptAfter(deopt_id);
if (FLAG_precompiled_mode) {
// Megamorphic calls may occur in slow path stubs.
// If valid use try_index argument.
@@ -1045,14 +1045,12 @@ void FlowGraphCompiler::EmitMegamorphicInstanceCall(
try_index = CurrentTryIndex();
}
AddDescriptor(RawPcDescriptors::kOther, assembler()->CodeSize(),
Thread::kNoDeoptId, token_pos, try_index);
DeoptId::kNone, token_pos, try_index);
} else if (is_optimizing()) {
AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
token_pos);
AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone, token_pos);
AddDeoptIndexAtCall(deopt_id_after);
} else {
AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
token_pos);
AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone, token_pos);
// Add deoptimization continuation point after the call and before the
// arguments are removed.
AddCurrentDescriptor(RawPcDescriptors::kDeopt, deopt_id_after, token_pos);
+17 -18
View File
@@ -477,7 +477,7 @@ const ICData* Instruction::GetICData(
const ZoneGrowableArray<const ICData*>& ic_data_array) const {
// The deopt_id can be outside the range of the IC data array for
// computations added in the optimizing compiler.
ASSERT(deopt_id_ != Thread::kNoDeoptId);
ASSERT(deopt_id_ != DeoptId::kNone);
if (deopt_id_ < ic_data_array.length()) {
const ICData* result = ic_data_array[deopt_id_];
#if defined(TAG_IC_DATA)
@@ -1046,7 +1046,7 @@ GraphEntryInstr::GraphEntryInstr(const ParsedFunction& parsed_function,
intptr_t osr_id)
: BlockEntryInstr(0,
CatchClauseNode::kInvalidTryIndex,
Thread::Current()->GetNextDeoptId()),
CompilerState::Current().GetNextDeoptId()),
parsed_function_(parsed_function),
normal_entry_(normal_entry),
catch_entries_(),
@@ -1322,7 +1322,7 @@ void Instruction::InheritDeoptTargetAfter(FlowGraph* flow_graph,
Definition* call,
Definition* result) {
ASSERT(call->env() != NULL);
deopt_id_ = Thread::ToDeoptAfter(call->deopt_id_);
deopt_id_ = DeoptId::ToDeoptAfter(call->deopt_id_);
call->env()->DeepCopyAfterTo(
flow_graph->zone(), this, call->ArgumentCount(),
flow_graph->constant_dead(),
@@ -1537,8 +1537,8 @@ bool BlockEntryInstr::FindOsrEntryAndRelink(GraphEntryInstr* graph_entry,
// we can simply jump to the beginning of the block.
ASSERT(instr->previous() == this);
GotoInstr* goto_join =
new GotoInstr(AsJoinEntry(), Thread::Current()->GetNextDeoptId());
GotoInstr* goto_join = new GotoInstr(
AsJoinEntry(), CompilerState::Current().GetNextDeoptId());
goto_join->CopyDeoptIdFrom(*parent);
graph_entry->normal_entry()->LinkTo(goto_join);
return true;
@@ -1754,7 +1754,7 @@ BlockEntryInstr* GotoInstr::SuccessorAt(intptr_t index) const {
}
void Instruction::Goto(JoinEntryInstr* entry) {
LinkTo(new GotoInstr(entry, Thread::Current()->GetNextDeoptId()));
LinkTo(new GotoInstr(entry, CompilerState::Current().GetNextDeoptId()));
}
bool UnboxedIntConverterInstr::ComputeCanDeoptimize() const {
@@ -2268,7 +2268,7 @@ Definition* CheckedSmiOpInstr::Canonicalize(FlowGraph* flow_graph) {
case Token::kBIT_XOR:
replacement = new BinarySmiOpInstr(
op_kind(), new Value(left()->definition()),
new Value(right()->definition()), Thread::kNoDeoptId);
new Value(right()->definition()), DeoptId::kNone);
default:
break;
}
@@ -2308,11 +2308,11 @@ Definition* CheckedSmiComparisonInstr::Canonicalize(FlowGraph* flow_graph) {
if (Token::IsRelationalOperator(kind())) {
replacement = new RelationalOpInstr(
token_pos(), kind(), left()->CopyWithType(), right()->CopyWithType(),
op_cid, Thread::kNoDeoptId, speculative_mode);
op_cid, DeoptId::kNone, speculative_mode);
} else if (Token::IsEqualityOperator(kind())) {
replacement = new EqualityCompareInstr(
token_pos(), kind(), left()->CopyWithType(), right()->CopyWithType(),
op_cid, Thread::kNoDeoptId, speculative_mode);
op_cid, DeoptId::kNone, speculative_mode);
}
if (replacement != NULL) {
if (FLAG_trace_strong_mode_types && (op_cid == kMintCid)) {
@@ -2452,7 +2452,7 @@ Definition* BinaryIntegerOpInstr::Canonicalize(FlowGraph* flow_graph) {
// the code generator deal with throw on slowpath.
break;
}
ASSERT(GetDeoptId() != Thread::kNoDeoptId);
ASSERT(GetDeoptId() != DeoptId::kNone);
DeoptimizeInstr* deopt =
new DeoptimizeInstr(ICData::kDeoptBinarySmiOp, GetDeoptId());
flow_graph->InsertBefore(this, deopt, env(), FlowGraph::kEffect);
@@ -2476,7 +2476,7 @@ Definition* BinaryIntegerOpInstr::Canonicalize(FlowGraph* flow_graph) {
// the code generator deal with throw on slowpath.
break;
}
ASSERT(GetDeoptId() != Thread::kNoDeoptId);
ASSERT(GetDeoptId() != DeoptId::kNone);
DeoptimizeInstr* deopt =
new DeoptimizeInstr(ICData::kDeoptBinarySmiOp, GetDeoptId());
flow_graph->InsertBefore(this, deopt, env(), FlowGraph::kEffect);
@@ -2939,8 +2939,7 @@ Definition* UnboxIntegerInstr::Canonicalize(FlowGraph* flow_graph) {
UnboxedIntConverterInstr* converter = new UnboxedIntConverterInstr(
from_representation, representation(),
box_defn->value()->CopyWithType(),
(representation() == kUnboxedInt32) ? GetDeoptId()
: Thread::kNoDeoptId);
(representation() == kUnboxedInt32) ? GetDeoptId() : DeoptId::kNone);
// TODO(vegorov): marking resulting converter as truncating when
// unboxing can't deoptimize is a workaround for the missing
// deoptimization environment when we insert converter after
@@ -3030,7 +3029,7 @@ Definition* UnboxedIntConverterInstr::Canonicalize(FlowGraph* flow_graph) {
UnboxedIntConverterInstr* converter = new UnboxedIntConverterInstr(
box_defn->from(), representation(), box_defn->value()->CopyWithType(),
(to() == kUnboxedInt32) ? GetDeoptId() : Thread::kNoDeoptId);
(to() == kUnboxedInt32) ? GetDeoptId() : DeoptId::kNone);
if ((representation() == kUnboxedInt32) && is_truncating()) {
converter->mark_truncating();
}
@@ -3294,7 +3293,7 @@ TestCidsInstr::TestCidsInstr(TokenPosition token_pos,
set_operation_cid(kObjectCid);
#ifdef DEBUG
ASSERT(cid_results[0] == kSmiCid);
if (deopt_id == Thread::kNoDeoptId) {
if (deopt_id == DeoptId::kNone) {
// The entry for Smi can be special, but all other entries have
// to match in the no-deopt case.
for (intptr_t i = 4; i < cid_results.length(); i += 2) {
@@ -3320,7 +3319,7 @@ Definition* TestCidsInstr::Canonicalize(FlowGraph* flow_graph) {
}
if (!CanDeoptimize()) {
ASSERT(deopt_id() == Thread::kNoDeoptId);
ASSERT(deopt_id() == DeoptId::kNone);
return (data[data.length() - 1] == true_result)
? flow_graph->GetConstant(Bool::False())
: flow_graph->GetConstant(Bool::True());
@@ -4561,7 +4560,7 @@ Environment* Environment::From(Zone* zone,
const ParsedFunction& parsed_function) {
Environment* env =
new (zone) Environment(definitions.length(), fixed_parameter_count,
Thread::kNoDeoptId, parsed_function, NULL);
DeoptId::kNone, parsed_function, NULL);
for (intptr_t i = 0; i < definitions.length(); ++i) {
env->values_.Add(new (zone) Value(definitions[i]));
}
@@ -4665,7 +4664,7 @@ ComparisonInstr* RelationalOpInstr::CopyWithNewOperands(Value* new_left,
ComparisonInstr* StrictCompareInstr::CopyWithNewOperands(Value* new_left,
Value* new_right) {
return new StrictCompareInstr(token_pos(), kind(), new_left, new_right,
needs_number_check(), Thread::kNoDeoptId);
needs_number_check(), DeoptId::kNone);
}
ComparisonInstr* TestSmiInstr::CopyWithNewOperands(Value* new_left,
+14 -28
View File
@@ -8,6 +8,7 @@
#include "vm/allocation.h"
#include "vm/ast.h"
#include "vm/compiler/backend/locations.h"
#include "vm/compiler/compiler_state.h"
#include "vm/compiler/method_recognizer.h"
#include "vm/flags.h"
#include "vm/growable_array.h"
@@ -759,21 +760,6 @@ class CallTargets : public Cids {
void MergeIntoRanges();
};
class DeoptIdScope : public StackResource {
public:
DeoptIdScope(Thread* thread, intptr_t deopt_id)
: StackResource(thread), prev_deopt_id_(thread->deopt_id()) {
thread->set_deopt_id(deopt_id);
}
~DeoptIdScope() { thread()->set_deopt_id(prev_deopt_id_); }
private:
const intptr_t prev_deopt_id_;
DISALLOW_COPY_AND_ASSIGN(DeoptIdScope);
};
class Instruction : public ZoneAllocated {
public:
#define DECLARE_TAG(type, attrs) k##type,
@@ -790,7 +776,7 @@ class Instruction : public ZoneAllocated {
kNotSpeculative
};
explicit Instruction(intptr_t deopt_id = Thread::kNoDeoptId)
explicit Instruction(intptr_t deopt_id = DeoptId::kNone)
: deopt_id_(deopt_id),
lifetime_position_(kNoPlaceId),
previous_(NULL),
@@ -974,7 +960,7 @@ class Instruction : public ZoneAllocated {
// to.
virtual intptr_t DeoptimizationTarget() const {
UNREACHABLE();
return Thread::kNoDeoptId;
return DeoptId::kNone;
}
// Returns a replacement for the instruction or NULL if the instruction can
@@ -1151,7 +1137,7 @@ template <intptr_t N,
class TemplateInstruction
: public CSETrait<Instruction, PureInstruction>::Base {
public:
explicit TemplateInstruction(intptr_t deopt_id = Thread::kNoDeoptId)
explicit TemplateInstruction(intptr_t deopt_id = DeoptId::kNone)
: CSETrait<Instruction, PureInstruction>::Base(deopt_id), inputs_() {}
virtual intptr_t InputCount() const { return N; }
@@ -1855,7 +1841,7 @@ class AliasIdentity : public ValueObject {
// Abstract super-class of all instructions that define a value (Bind, Phi).
class Definition : public Instruction {
public:
explicit Definition(intptr_t deopt_id = Thread::kNoDeoptId);
explicit Definition(intptr_t deopt_id = DeoptId::kNone);
// Overridden by definitions that have call counts.
virtual intptr_t CallCount() const {
@@ -2037,7 +2023,7 @@ template <intptr_t N,
template <typename Impure, typename Pure> class CSETrait = NoCSE>
class TemplateDefinition : public CSETrait<Definition, PureDefinition>::Base {
public:
explicit TemplateDefinition(intptr_t deopt_id = Thread::kNoDeoptId)
explicit TemplateDefinition(intptr_t deopt_id = DeoptId::kNone)
: CSETrait<Definition, PureDefinition>::Base(deopt_id), inputs_() {}
virtual intptr_t InputCount() const { return N; }
@@ -2651,7 +2637,7 @@ class ComparisonInstr : public Definition {
protected:
ComparisonInstr(TokenPosition token_pos,
Token::Kind kind,
intptr_t deopt_id = Thread::kNoDeoptId)
intptr_t deopt_id = DeoptId::kNone)
: Definition(deopt_id),
token_pos_(token_pos),
kind_(kind),
@@ -2683,7 +2669,7 @@ class TemplateComparison
public:
TemplateComparison(TokenPosition token_pos,
Token::Kind kind,
intptr_t deopt_id = Thread::kNoDeoptId)
intptr_t deopt_id = DeoptId::kNone)
: CSETrait<ComparisonInstr, PureComparison>::Base(token_pos,
kind,
deopt_id),
@@ -3592,7 +3578,7 @@ class TestCidsInstr : public TemplateComparison<1, NoThrow, Pure> {
virtual Definition* Canonicalize(FlowGraph* flow_graph);
virtual bool ComputeCanDeoptimize() const {
return GetDeoptId() != Thread::kNoDeoptId;
return GetDeoptId() != DeoptId::kNone;
}
virtual Representation RequiredInputRepresentation(intptr_t idx) const {
@@ -4105,7 +4091,7 @@ class NativeCallInstr : public TemplateDartCall<0> {
bool link_lazily,
TokenPosition position,
PushArgumentsArray* args)
: TemplateDartCall(Thread::kNoDeoptId,
: TemplateDartCall(DeoptId::kNone,
0,
Array::null_array(),
args,
@@ -4495,7 +4481,7 @@ class LoadIndexedInstr : public TemplateDefinition<2, NoThrow> {
bool aligned() const { return alignment_ == kAlignedAccess; }
virtual bool ComputeCanDeoptimize() const {
return GetDeoptId() != Thread::kNoDeoptId;
return GetDeoptId() != DeoptId::kNone;
}
virtual Representation representation() const;
@@ -4776,7 +4762,7 @@ class InstanceOfInstr : public TemplateDefinition<3, Throws> {
// either reside in new space or be in the store buffer.
class AllocationInstr : public Definition {
public:
explicit AllocationInstr(intptr_t deopt_id = Thread::kNoDeoptId)
explicit AllocationInstr(intptr_t deopt_id = DeoptId::kNone)
: Definition(deopt_id) {}
// TODO(sjindel): Update these conditions when the incremental write barrier
@@ -4792,7 +4778,7 @@ class AllocationInstr : public Definition {
template <intptr_t N, typename ThrowsTrait>
class TemplateAllocation : public AllocationInstr {
public:
explicit TemplateAllocation(intptr_t deopt_id = Thread::kNoDeoptId)
explicit TemplateAllocation(intptr_t deopt_id = DeoptId::kNone)
: AllocationInstr(deopt_id), inputs_() {}
virtual intptr_t InputCount() const { return N; }
@@ -5542,7 +5528,7 @@ class BoxInstr : public TemplateDefinition<1, NoThrow, Pure> {
virtual CompileType ComputeType() const;
virtual bool ComputeCanDeoptimize() const { return false; }
virtual intptr_t DeoptimizationTarget() const { return Thread::kNoDeoptId; }
virtual intptr_t DeoptimizationTarget() const { return DeoptId::kNone; }
virtual Representation RequiredInputRepresentation(intptr_t idx) const {
ASSERT(idx == 0);
+1 -1
View File
@@ -2957,7 +2957,7 @@ void CatchBlockEntryInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
catch_handler_types_, needs_stacktrace());
// On lazy deoptimization we patch the optimized code here to enter the
// deoptimization stub.
const intptr_t deopt_id = Thread::ToDeoptAfter(GetDeoptId());
const intptr_t deopt_id = DeoptId::ToDeoptAfter(GetDeoptId());
if (compiler->is_optimizing()) {
compiler->AddDeoptIndexAtCall(deopt_id);
} else {
+1 -1
View File
@@ -2652,7 +2652,7 @@ void CatchBlockEntryInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
catch_handler_types_, needs_stacktrace());
// On lazy deoptimization we patch the optimized code here to enter the
// deoptimization stub.
const intptr_t deopt_id = Thread::ToDeoptAfter(GetDeoptId());
const intptr_t deopt_id = DeoptId::ToDeoptAfter(GetDeoptId());
if (compiler->is_optimizing()) {
compiler->AddDeoptIndexAtCall(deopt_id);
} else {
+12 -12
View File
@@ -991,7 +991,7 @@ EMIT_NATIVE_CODE(NativeCall,
__ object_pool_wrapper().FindImmediate(static_cast<uword>(argc_tag));
__ NativeCall(trampoline_kidx, target_kidx, argc_tag_kidx);
compiler->RecordSafepoint(locs());
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
}
@@ -1040,15 +1040,15 @@ EMIT_NATIVE_CODE(AllocateObject,
}
__ PushConstant(cls());
__ AllocateT();
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther,
Thread::kNoDeoptId, token_pos());
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
compiler->RecordSafepoint(locs());
__ PopLocal(locs()->out(0).reg());
} else {
__ PushConstant(cls());
__ AllocateT();
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther,
Thread::kNoDeoptId, token_pos());
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
compiler->RecordSafepoint(locs());
}
} else if (compiler->is_optimizing()) {
@@ -1069,14 +1069,14 @@ EMIT_NATIVE_CODE(AllocateObject,
}
const intptr_t kidx = __ AddConstant(cls());
__ Allocate(kidx);
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
compiler->RecordSafepoint(locs());
__ PopLocal(locs()->out(0).reg());
} else {
const intptr_t kidx = __ AddConstant(cls());
__ Allocate(kidx);
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
compiler->RecordSafepoint(locs());
}
@@ -1141,7 +1141,7 @@ EMIT_NATIVE_CODE(AllocateContext,
ASSERT(!compiler->is_optimizing());
__ AllocateContext(num_context_variables());
compiler->RecordSafepoint(locs());
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
}
@@ -1154,7 +1154,7 @@ EMIT_NATIVE_CODE(AllocateUninitializedContext,
num_context_variables());
__ AllocateContext(num_context_variables());
compiler->RecordSafepoint(locs());
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
__ PopLocal(locs()->out(0).reg());
}
@@ -1168,7 +1168,7 @@ EMIT_NATIVE_CODE(CloneContext,
}
__ CloneContext();
compiler->RecordSafepoint(locs());
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
if (compiler->is_optimizing()) {
__ PopLocal(locs()->out(0).reg());
@@ -1183,7 +1183,7 @@ EMIT_NATIVE_CODE(CatchBlockEntry, 0) {
catch_handler_types_, needs_stacktrace());
// On lazy deoptimization we patch the optimized code here to enter the
// deoptimization stub.
const intptr_t deopt_id = Thread::ToDeoptAfter(GetDeoptId());
const intptr_t deopt_id = DeoptId::ToDeoptAfter(GetDeoptId());
if (compiler->is_optimizing()) {
compiler->AddDeoptIndexAtCall(deopt_id);
} else {
@@ -1630,7 +1630,7 @@ EMIT_NATIVE_CODE(Box, 1, Location::RequiresRegister(), LocationSummary::kCall) {
}
const intptr_t kidx = __ AddConstant(compiler->double_class());
__ Allocate(kidx);
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, Thread::kNoDeoptId,
compiler->AddCurrentDescriptor(RawPcDescriptors::kOther, DeoptId::kNone,
token_pos());
compiler->RecordSafepoint(locs());
__ PopLocal(out);
+1 -1
View File
@@ -2534,7 +2534,7 @@ void CatchBlockEntryInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
catch_handler_types_, needs_stacktrace());
// On lazy deoptimization we patch the optimized code here to enter the
// deoptimization stub.
const intptr_t deopt_id = Thread::ToDeoptAfter(GetDeoptId());
const intptr_t deopt_id = DeoptId::ToDeoptAfter(GetDeoptId());
if (compiler->is_optimizing()) {
compiler->AddDeoptIndexAtCall(deopt_id);
} else {
+6 -6
View File
@@ -340,7 +340,7 @@ const char* Instruction::ToCString() const {
}
void Instruction::PrintTo(BufferFormatter* f) const {
if (GetDeoptId() != Thread::kNoDeoptId) {
if (GetDeoptId() != DeoptId::kNone) {
f->Print("%s:%" Pd "(", DebugName(), GetDeoptId());
} else {
f->Print("%s(", DebugName());
@@ -359,7 +359,7 @@ void Instruction::PrintOperandsTo(BufferFormatter* f) const {
void Definition::PrintTo(BufferFormatter* f) const {
PrintUse(f, *this);
if (HasSSATemp() || HasTemp()) f->Print(" <- ");
if (GetDeoptId() != Thread::kNoDeoptId) {
if (GetDeoptId() != DeoptId::kNone) {
f->Print("%s:%" Pd "(", DebugName(), GetDeoptId());
} else {
f->Print("%s(", DebugName());
@@ -562,10 +562,10 @@ void TestCidsInstr::PrintOperandsTo(BufferFormatter* f) const {
}
f->Print("] ");
if (CanDeoptimize()) {
ASSERT(deopt_id() != Thread::kNoDeoptId);
ASSERT(deopt_id() != DeoptId::kNone);
f->Print("else deoptimize ");
} else {
ASSERT(deopt_id() == Thread::kNoDeoptId);
ASSERT(deopt_id() == DeoptId::kNone);
f->Print("else %s ", cid_results()[length - 1] != 0 ? "false" : "true");
}
}
@@ -1075,7 +1075,7 @@ void GotoInstr::PrintTo(BufferFormatter* f) const {
parallel_move()->PrintTo(f);
f->Print(" ");
}
if (GetDeoptId() != Thread::kNoDeoptId) {
if (GetDeoptId() != DeoptId::kNone) {
f->Print("goto:%" Pd " B%" Pd "", GetDeoptId(), successor()->block_id());
} else {
f->Print("goto: B%" Pd "", successor()->block_id());
@@ -1083,7 +1083,7 @@ void GotoInstr::PrintTo(BufferFormatter* f) const {
}
void IndirectGotoInstr::PrintTo(BufferFormatter* f) const {
if (GetDeoptId() != Thread::kNoDeoptId) {
if (GetDeoptId() != DeoptId::kNone) {
f->Print("igoto:%" Pd "(", GetDeoptId());
} else {
f->Print("igoto:(");
+4 -4
View File
@@ -9,19 +9,19 @@ namespace dart {
TEST_CASE(InstructionTests) {
TargetEntryInstr* target_instr = new TargetEntryInstr(
1, CatchClauseNode::kInvalidTryIndex, Thread::kNoDeoptId);
1, CatchClauseNode::kInvalidTryIndex, DeoptId::kNone);
EXPECT(target_instr->IsBlockEntry());
EXPECT(!target_instr->IsDefinition());
SpecialParameterInstr* context = new SpecialParameterInstr(
SpecialParameterInstr::kContext, Thread::kNoDeoptId, target_instr);
SpecialParameterInstr::kContext, DeoptId::kNone, target_instr);
EXPECT(context->IsDefinition());
EXPECT(!context->IsBlockEntry());
EXPECT(context->GetBlock() == target_instr);
}
TEST_CASE(OptimizationTests) {
JoinEntryInstr* join = new JoinEntryInstr(
1, CatchClauseNode::kInvalidTryIndex, Thread::kNoDeoptId);
JoinEntryInstr* join =
new JoinEntryInstr(1, CatchClauseNode::kInvalidTryIndex, DeoptId::kNone);
Definition* def1 = new PhiInstr(join, 0);
Definition* def2 = new PhiInstr(join, 0);
+1 -1
View File
@@ -2657,7 +2657,7 @@ void CatchBlockEntryInstr::EmitNativeCode(FlowGraphCompiler* compiler) {
catch_handler_types_, needs_stacktrace());
// On lazy deoptimization we patch the optimized code here to enter the
// deoptimization stub.
const intptr_t deopt_id = Thread::ToDeoptAfter(GetDeoptId());
const intptr_t deopt_id = DeoptId::ToDeoptAfter(GetDeoptId());
if (compiler->is_optimizing()) {
compiler->AddDeoptIndexAtCall(deopt_id);
} else {
+94 -96
View File
@@ -925,7 +925,7 @@ class CallSiteInliner : public ValueObject {
// Loading occured while parsing. We need to abort here because
// state changed while compiling.
Compiler::AbortBackgroundCompilation(
Thread::kNoDeoptId, "Loading occured while parsing in inliner");
DeoptId::kNone, "Loading occured while parsing in inliner");
}
}
@@ -936,7 +936,7 @@ class CallSiteInliner : public ValueObject {
function.RestoreICDataMap(ic_data_array, clone_ic_data);
if (Compiler::IsBackgroundCompilation() &&
(function.ic_data_array() == Array::null())) {
Compiler::AbortBackgroundCompilation(Thread::kNoDeoptId,
Compiler::AbortBackgroundCompilation(DeoptId::kNone,
"ICData cleared while inlining");
}
@@ -1667,9 +1667,9 @@ bool PolymorphicInliner::CheckInlinedDuplicate(const Function& target) {
}
// Create a new target with the join as unconditional successor.
TargetEntryInstr* new_target = new TargetEntryInstr(
AllocateBlockId(), old_target->try_index(), Thread::kNoDeoptId);
AllocateBlockId(), old_target->try_index(), DeoptId::kNone);
new_target->InheritDeoptTarget(zone(), new_join);
GotoInstr* new_goto = new (Z) GotoInstr(new_join, Thread::kNoDeoptId);
GotoInstr* new_goto = new (Z) GotoInstr(new_join, DeoptId::kNone);
new_goto->InheritDeoptTarget(zone(), new_join);
new_target->LinkTo(new_goto);
new_target->set_last_instruction(new_goto);
@@ -1768,7 +1768,7 @@ bool PolymorphicInliner::TryInlineRecognizedMethod(intptr_t receiver_cid,
new (Z) InlineExitCollector(owner_->caller_graph(), call_);
ReturnInstr* result = new (Z)
ReturnInstr(call_->instance_call()->token_pos(),
new (Z) Value(last->AsDefinition()), Thread::kNoDeoptId);
new (Z) Value(last->AsDefinition()), DeoptId::kNone);
owner_->caller_graph()->AppendTo(
last, result,
call_->env(), // Return can become deoptimization target.
@@ -1798,7 +1798,7 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
// Start with a fresh target entry.
TargetEntryInstr* entry = new (Z) TargetEntryInstr(
AllocateBlockId(), try_idx, Thread::Current()->GetNextDeoptId());
AllocateBlockId(), try_idx, CompilerState::Current().GetNextDeoptId());
entry->InheritDeoptTarget(zone(), call_);
// This function uses a cursor (a pointer to the 'current' instruction) to
@@ -1863,7 +1863,7 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
// the join.
JoinEntryInstr* join = callee_entry->AsJoinEntry();
ASSERT(join->dominator() != NULL);
GotoInstr* goto_join = new GotoInstr(join, Thread::kNoDeoptId);
GotoInstr* goto_join = new GotoInstr(join, DeoptId::kNone);
goto_join->InheritDeoptTarget(zone(), join);
cursor->LinkTo(goto_join);
current_block->set_last_instruction(goto_join);
@@ -1896,13 +1896,13 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
new Value(load_cid), new Value(cid_constant_end), kSmiCid,
call_->deopt_id());
BranchInstr* branch_top = upper_limit_branch =
new BranchInstr(compare_top, Thread::kNoDeoptId);
new BranchInstr(compare_top, DeoptId::kNone);
branch_top->InheritDeoptTarget(zone(), call_);
cursor = AppendInstruction(cursor, branch_top);
current_block->set_last_instruction(branch_top);
TargetEntryInstr* below_target = new TargetEntryInstr(
AllocateBlockId(), try_idx, Thread::kNoDeoptId);
TargetEntryInstr* below_target =
new TargetEntryInstr(AllocateBlockId(), try_idx, DeoptId::kNone);
below_target->InheritDeoptTarget(zone(), call_);
current_block->AddDominatedBlock(below_target);
cursor = current_block = below_target;
@@ -1912,13 +1912,13 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
call_->instance_call()->token_pos(), Token::kGTE,
new Value(load_cid), new Value(cid_constant), kSmiCid,
call_->deopt_id());
branch = new BranchInstr(compare_bottom, Thread::kNoDeoptId);
branch = new BranchInstr(compare_bottom, DeoptId::kNone);
} else {
StrictCompareInstr* compare = new StrictCompareInstr(
call_->instance_call()->token_pos(), Token::kEQ_STRICT,
new Value(load_cid), new Value(cid_constant),
/* number_check = */ false, Thread::kNoDeoptId);
branch = new BranchInstr(compare, Thread::kNoDeoptId);
/* number_check = */ false, DeoptId::kNone);
branch = new BranchInstr(compare, DeoptId::kNone);
}
branch->InheritDeoptTarget(zone(), call_);
@@ -1949,10 +1949,10 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
JoinEntryInstr* join = callee_entry->AsJoinEntry();
ASSERT(join != NULL);
ASSERT(join->dominator() != NULL);
true_target = new TargetEntryInstr(AllocateBlockId(), try_idx,
Thread::kNoDeoptId);
true_target =
new TargetEntryInstr(AllocateBlockId(), try_idx, DeoptId::kNone);
true_target->InheritDeoptTarget(zone(), join);
GotoInstr* goto_join = new GotoInstr(join, Thread::kNoDeoptId);
GotoInstr* goto_join = new GotoInstr(join, DeoptId::kNone);
goto_join->InheritDeoptTarget(zone(), join);
true_target->LinkTo(goto_join);
true_target->set_last_instruction(goto_join);
@@ -1964,7 +1964,7 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
// fall-through code below for non-inlined variants.
TargetEntryInstr* false_target =
new TargetEntryInstr(AllocateBlockId(), try_idx, Thread::kNoDeoptId);
new TargetEntryInstr(AllocateBlockId(), try_idx, DeoptId::kNone);
false_target->InheritDeoptTarget(zone(), call_);
*branch->false_successor_address() = false_target;
cid_test_entry_block->AddDominatedBlock(false_target);
@@ -1975,14 +1975,14 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
// If we tested against a range of Cids there are two different tests
// that can go to the no-cid-match target.
JoinEntryInstr* join =
new JoinEntryInstr(AllocateBlockId(), try_idx, Thread::kNoDeoptId);
TargetEntryInstr* false_target2 = new TargetEntryInstr(
AllocateBlockId(), try_idx, Thread::kNoDeoptId);
new JoinEntryInstr(AllocateBlockId(), try_idx, DeoptId::kNone);
TargetEntryInstr* false_target2 =
new TargetEntryInstr(AllocateBlockId(), try_idx, DeoptId::kNone);
*upper_limit_branch->false_successor_address() = false_target2;
cid_test_entry_block->AddDominatedBlock(false_target2);
cid_test_entry_block->AddDominatedBlock(join);
GotoInstr* goto_1 = new GotoInstr(join, Thread::kNoDeoptId);
GotoInstr* goto_2 = new GotoInstr(join, Thread::kNoDeoptId);
GotoInstr* goto_1 = new GotoInstr(join, DeoptId::kNone);
GotoInstr* goto_2 = new GotoInstr(join, DeoptId::kNone);
false_target->LinkTo(goto_1);
false_target2->LinkTo(goto_2);
false_target->set_last_instruction(goto_1);
@@ -2017,7 +2017,7 @@ TargetEntryInstr* PolymorphicInliner::BuildDecisionGraph() {
fallback_call->set_total_call_count(call_->CallCount());
ReturnInstr* fallback_return =
new ReturnInstr(call_->instance_call()->token_pos(),
new Value(fallback_call), Thread::kNoDeoptId);
new Value(fallback_call), DeoptId::kNone);
fallback_return->InheritDeoptTargetAfter(owner_->caller_graph(), call_,
fallback_call);
AppendInstruction(AppendInstruction(cursor, fallback_call),
@@ -2358,20 +2358,20 @@ static bool InlineGetIndexed(FlowGraph* flow_graph,
Definition* array = receiver;
Definition* index = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Instruction* cursor = *entry;
array_cid = PrepareInlineIndexedOp(flow_graph, call, array_cid, &array, index,
&cursor, can_speculate);
intptr_t deopt_id = Thread::kNoDeoptId;
intptr_t deopt_id = DeoptId::kNone;
if ((array_cid == kTypedDataInt32ArrayCid) ||
(array_cid == kTypedDataUint32ArrayCid)) {
// Deoptimization may be needed if result does not always fit in a Smi.
deopt_id = (kSmiBits >= 32) ? Thread::kNoDeoptId : call->deopt_id();
deopt_id = (kSmiBits >= 32) ? DeoptId::kNone : call->deopt_id();
}
// Array load and return.
@@ -2380,14 +2380,14 @@ static bool InlineGetIndexed(FlowGraph* flow_graph,
LoadIndexedInstr(new (Z) Value(array), new (Z) Value(index), index_scale,
array_cid, kAlignedAccess, deopt_id, call->token_pos());
*last = load;
cursor = flow_graph->AppendTo(
cursor, load, deopt_id != Thread::kNoDeoptId ? call->env() : NULL,
FlowGraph::kValue);
cursor = flow_graph->AppendTo(cursor, load,
deopt_id != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kValue);
if (array_cid == kTypedDataFloat32ArrayCid) {
*last = new (Z) FloatToDoubleInstr(new (Z) Value(load), deopt_id);
flow_graph->AppendTo(cursor, *last,
deopt_id != Thread::kNoDeoptId ? call->env() : NULL,
deopt_id != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kValue);
}
return true;
@@ -2409,9 +2409,9 @@ static bool InlineSetIndexed(FlowGraph* flow_graph,
Definition* index = call->ArgumentAt(1);
Definition* stored_value = call->ArgumentAt(2);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Instruction* cursor = *entry;
if (flow_graph->isolate()->argument_type_checks() &&
@@ -2552,9 +2552,9 @@ static bool InlineDoubleOp(FlowGraph* flow_graph,
Definition* left = receiver;
Definition* right = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
// Arguments are checked. No need for class check.
BinaryDoubleOpInstr* double_bin_op = new (Z)
@@ -2576,9 +2576,9 @@ static bool InlineDoubleTestOp(FlowGraph* flow_graph,
return false;
}
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
// Arguments are checked. No need for class check.
@@ -2598,9 +2598,9 @@ static bool InlineSmiBitAndFromSmi(FlowGraph* flow_graph,
Definition* left = receiver;
Definition* right = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
// Right arguments is known to be smi: other._bitAndFromSmi(this);
BinarySmiOpInstr* smi_op =
@@ -2622,9 +2622,9 @@ static bool InlineGrowableArraySetter(FlowGraph* flow_graph,
Definition* array = receiver;
Definition* value = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
// This is an internal method, no need to check argument types.
@@ -2755,8 +2755,8 @@ static LoadIndexedInstr* NewLoad(FlowGraph* flow_graph,
intptr_t view_cid) {
return new (Z) LoadIndexedInstr(new (Z) Value(array), new (Z) Value(index),
1, // Index scale
view_cid, kUnalignedAccess,
Thread::kNoDeoptId, call->token_pos());
view_cid, kUnalignedAccess, DeoptId::kNone,
call->token_pos());
}
static bool InlineByteArrayBaseLoad(FlowGraph* flow_graph,
@@ -2781,9 +2781,9 @@ static bool InlineByteArrayBaseLoad(FlowGraph* flow_graph,
Definition* array = receiver;
Definition* index = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Instruction* cursor = *entry;
@@ -2815,13 +2815,13 @@ static bool InlineByteArrayBaseLoad(FlowGraph* flow_graph,
ASSERT(block_external->next() == array);
flow_graph->InsertAfter(
block_external->next(), load1,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
call->deopt_id() != DeoptId::kNone ? call->env() : nullptr,
FlowGraph::kValue);
LoadIndexedInstr* load2 =
NewLoad(flow_graph, call, receiver, index, view_cid);
flow_graph->InsertAfter(
block_internal, load2,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
call->deopt_id() != DeoptId::kNone ? call->env() : nullptr,
FlowGraph::kValue);
// Construct phi of external and internal load.
*last = flow_graph->AddPhi(cursor->AsJoinEntry(), load1, load2);
@@ -2831,14 +2831,14 @@ static bool InlineByteArrayBaseLoad(FlowGraph* flow_graph,
LoadIndexedInstr* load = NewLoad(flow_graph, call, array, index, view_cid);
flow_graph->AppendTo(
cursor, load,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
call->deopt_id() != DeoptId::kNone ? call->env() : nullptr,
FlowGraph::kValue);
cursor = *last = load;
}
if (view_cid == kTypedDataFloat32ArrayCid) {
*last = new (Z) FloatToDoubleInstr(new (Z) Value((*last)->AsDefinition()),
Thread::kNoDeoptId);
DeoptId::kNone);
flow_graph->AppendTo(cursor, *last, nullptr, FlowGraph::kValue);
}
return true;
@@ -2879,9 +2879,9 @@ static bool InlineByteArrayBaseStore(FlowGraph* flow_graph,
Definition* array = receiver;
Definition* index = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Instruction* cursor = *entry;
@@ -3029,12 +3029,12 @@ static bool InlineByteArrayBaseStore(FlowGraph* flow_graph,
flow_graph->InsertAfter(
block_external->next(),
NewStore(flow_graph, call, array, index, stored_value, view_cid),
call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
call->deopt_id() != DeoptId::kNone ? call->env() : nullptr,
FlowGraph::kEffect);
flow_graph->InsertAfter(
block_internal,
NewStore(flow_graph, call, receiver, index, stored_value, view_cid),
call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
call->deopt_id() != DeoptId::kNone ? call->env() : nullptr,
FlowGraph::kEffect);
*last = cursor;
} else {
@@ -3044,7 +3044,7 @@ static bool InlineByteArrayBaseStore(FlowGraph* flow_graph,
NewStore(flow_graph, call, array, index, stored_value, view_cid);
flow_graph->AppendTo(
cursor, store,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : nullptr,
call->deopt_id() != DeoptId::kNone ? call->env() : nullptr,
FlowGraph::kEffect);
*last = store;
}
@@ -3083,7 +3083,7 @@ static Definition* PrepareInlineStringIndexOp(FlowGraph* flow_graph,
LoadIndexedInstr* load_indexed = new (Z) LoadIndexedInstr(
new (Z) Value(str), new (Z) Value(index), Instance::ElementSizeFor(cid),
cid, kAlignedAccess, Thread::kNoDeoptId, call->token_pos());
cid, kAlignedAccess, DeoptId::kNone, call->token_pos());
cursor = flow_graph->AppendTo(cursor, load_indexed, NULL, FlowGraph::kValue);
ASSERT(cursor == load_indexed);
@@ -3102,9 +3102,9 @@ static bool InlineStringBaseCharAt(FlowGraph* flow_graph,
Definition* str = receiver;
Definition* index = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
*last = PrepareInlineStringIndexOp(flow_graph, call, cid, str, index, *entry);
@@ -3134,9 +3134,9 @@ static bool InlineStringCodeUnitAt(FlowGraph* flow_graph,
Definition* str = receiver;
Definition* index = call->ArgumentAt(1);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
*last = PrepareInlineStringIndexOp(flow_graph, call, cid, str, index, *entry);
@@ -3318,9 +3318,9 @@ static bool InlineSimdOp(FlowGraph* flow_graph,
if (!ShouldInlineSimd()) {
return false;
}
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Instruction* cursor = *entry;
switch (kind) {
@@ -3373,10 +3373,9 @@ static bool InlineSimdOp(FlowGraph* flow_graph,
*last = SimdOpInstr::CreateFromCall(Z, kind, receiver, call);
break;
}
flow_graph->AppendTo(
cursor, *last,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : NULL,
FlowGraph::kValue);
flow_graph->AppendTo(cursor, *last,
call->deopt_id() != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kValue);
return true;
}
@@ -3388,9 +3387,9 @@ static bool InlineMathCFunction(FlowGraph* flow_graph,
if (!CanUnboxDouble()) {
return false;
}
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
*entry =
new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Instruction* cursor = *entry;
@@ -3412,10 +3411,9 @@ static bool InlineMathCFunction(FlowGraph* flow_graph,
break;
}
}
flow_graph->AppendTo(
cursor, *last,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : NULL,
FlowGraph::kValue);
flow_graph->AppendTo(cursor, *last,
call->deopt_id() != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kValue);
return true;
}
@@ -3425,7 +3423,7 @@ static Instruction* InlineMul(FlowGraph* flow_graph,
Definition* y) {
BinaryInt64OpInstr* mul = new (Z)
BinaryInt64OpInstr(Token::kMUL, new (Z) Value(x), new (Z) Value(y),
Thread::kNoDeoptId, Instruction::kNotSpeculative);
DeoptId::kNone, Instruction::kNotSpeculative);
return flow_graph->AppendTo(cursor, mul, nullptr, FlowGraph::kValue);
}
@@ -3454,7 +3452,7 @@ static bool InlineMathIntPow(FlowGraph* flow_graph,
// Lazily construct entry only in this case.
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Definition* x_def = x->definition();
Definition* square =
@@ -3868,7 +3866,7 @@ bool FlowGraphInliner::TryInlineRecognizedMethod(
case MethodRecognizer::kObjectConstructor: {
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
ASSERT(!call->HasUses());
*last = NULL; // Empty body.
@@ -3886,13 +3884,13 @@ bool FlowGraphInliner::TryInlineRecognizedMethod(
const auto num_elements = new (Z) Value(call->ArgumentAt(1));
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
*last = new (Z) CreateArrayInstr(call->token_pos(), type, num_elements,
call->deopt_id());
flow_graph->AppendTo(
*entry, *last,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : NULL,
call->deopt_id() != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kValue);
return true;
}
@@ -3903,15 +3901,15 @@ bool FlowGraphInliner::TryInlineRecognizedMethod(
if (IsSmiValue(num_elements, &length)) {
if (length >= 0 && length <= Array::kMaxElements) {
Value* type = new (Z) Value(call->ArgumentAt(0));
*entry = new (Z) TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(),
Thread::kNoDeoptId);
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
*last = new (Z) CreateArrayInstr(call->token_pos(), type,
num_elements, call->deopt_id());
flow_graph->AppendTo(
*entry, *last,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : NULL,
call->deopt_id() != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kValue);
return true;
}
@@ -3940,12 +3938,12 @@ bool FlowGraphInliner::TryInlineRecognizedMethod(
if (!type.IsNull()) {
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
*last = new (Z) ConstantInstr(type);
flow_graph->AppendTo(
*entry, *last,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : NULL,
call->deopt_id() != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kValue);
return true;
}
@@ -3957,7 +3955,7 @@ bool FlowGraphInliner::TryInlineRecognizedMethod(
// range.
*entry = new (Z)
TargetEntryInstr(flow_graph->allocate_block_id(),
call->GetBlock()->try_index(), Thread::kNoDeoptId);
call->GetBlock()->try_index(), DeoptId::kNone);
(*entry)->InheritDeoptTarget(Z, call);
Definition* str = call->ArgumentAt(0);
Definition* index = call->ArgumentAt(1);
@@ -3970,7 +3968,7 @@ bool FlowGraphInliner::TryInlineRecognizedMethod(
call->deopt_id(), call->token_pos());
flow_graph->AppendTo(
*entry, *last,
call->deopt_id() != Thread::kNoDeoptId ? call->env() : NULL,
call->deopt_id() != DeoptId::kNone ? call->env() : NULL,
FlowGraph::kEffect);
return true;
}
@@ -983,7 +983,7 @@ class BoundsCheckGeneralizer {
for (intptr_t i = 0; i < non_positive_symbols.length(); i++) {
CheckArrayBoundInstr* precondition = new CheckArrayBoundInstr(
new Value(max_smi), new Value(non_positive_symbols[i]),
Thread::kNoDeoptId);
DeoptId::kNone);
precondition->mark_generalized();
precondition = scheduler_.Emit(precondition, check);
if (precondition == NULL) {
@@ -997,7 +997,7 @@ class BoundsCheckGeneralizer {
CheckArrayBoundInstr* new_check = new CheckArrayBoundInstr(
new Value(UnwrapConstraint(check->length()->definition())),
new Value(upper_bound), Thread::kNoDeoptId);
new Value(upper_bound), DeoptId::kNone);
new_check->mark_generalized();
if (new_check->IsRedundant(array_length)) {
if (FLAG_trace_range_analysis) {
@@ -1035,7 +1035,7 @@ class BoundsCheckGeneralizer {
Definition* left,
Definition* right) {
return new BinarySmiOpInstr(op_kind, new Value(left), new Value(right),
Thread::kNoDeoptId);
DeoptId::kNone);
}
BinarySmiOpInstr* MakeBinaryOp(Token::Kind op_kind,
@@ -8,7 +8,7 @@
#include "vm/bit_vector.h"
#include "vm/compiler/backend/il_printer.h"
#include "vm/compiler/cha.h"
#include "vm/compiler/compiler_state.h"
#include "vm/object_store.h"
#include "vm/regexp_assembler.h"
#include "vm/resolver.h"
@@ -695,7 +695,7 @@ intptr_t CompileType::ToNullableCid() {
} else if (type_->HasResolvedTypeClass()) {
const Class& type_class = Class::Handle(type_->type_class());
Thread* thread = Thread::Current();
CHA* cha = thread->cha();
CHA& cha = thread->compiler_state().cha();
// Don't infer a cid from an abstract type since there can be multiple
// compatible classes with different cids.
if (!type_class.is_abstract() && !CHA::IsImplemented(type_class) &&
@@ -710,7 +710,7 @@ intptr_t CompileType::ToNullableCid() {
type_class.ToCString());
}
if (FLAG_use_cha_deopt) {
cha->AddToGuardedClasses(type_class, /*subclass_count=*/0);
cha.AddToGuardedClasses(type_class, /*subclass_count=*/0);
}
cid_ = type_class.id();
} else {
@@ -968,8 +968,9 @@ CompileType ParameterInstr::ComputeType() const {
type_class.ToCString());
}
if (FLAG_use_cha_deopt) {
thread->cha()->AddToGuardedClasses(type_class,
/*subclass_count=*/0);
thread->compiler_state().cha().AddToGuardedClasses(
type_class,
/*subclass_count=*/0);
}
cid = type_class.id();
}
+7 -5
View File
@@ -8,6 +8,7 @@
#include "vm/compiler/backend/flow_graph_compiler.h"
#include "vm/compiler/backend/inliner.h"
#include "vm/compiler/cha.h"
#include "vm/compiler/compiler_state.h"
#include "vm/cpu.h"
namespace dart {
@@ -557,7 +558,7 @@ bool CallSpecializer::TryReplaceWithEqualityOp(InstanceCallInstr* call,
StrictCompareInstr* comp = new (Z)
StrictCompareInstr(call->token_pos(), Token::kEQ_STRICT,
new (Z) Value(left), new (Z) Value(right),
/* number_check = */ false, Thread::kNoDeoptId);
/* number_check = */ false, DeoptId::kNone);
ReplaceCall(call, comp);
return true;
}
@@ -1310,7 +1311,8 @@ bool CallSpecializer::TypeCheckAsClassEquality(const AbstractType& type) {
type_class.ToCString());
}
if (FLAG_use_cha_deopt) {
thread()->cha()->AddToGuardedClasses(type_class, /*subclass_count=*/0);
thread()->compiler_state().cha().AddToGuardedClasses(
type_class, /*subclass_count=*/0);
}
} else {
return false;
@@ -1357,7 +1359,7 @@ bool CallSpecializer::TryOptimizeInstanceOfUsingStaticTypes(
type.IsNullType() ? Token::kEQ_STRICT : Token::kNE_STRICT,
left_value->CopyWithType(Z),
new (Z) Value(flow_graph()->constant_null()),
/* number_check = */ false, Thread::kNoDeoptId);
/* number_check = */ false, DeoptId::kNone);
if (FLAG_trace_strong_mode_types) {
THR_Print("[Strong mode] replacing %s with %s (%s < %s)\n",
call->ToCString(), replacement->ToCString(),
@@ -1403,7 +1405,7 @@ void CallSpecializer::ReplaceWithInstanceOf(InstanceCallInstr* call) {
StrictCompareInstr* check_cid = new (Z) StrictCompareInstr(
call->token_pos(), Token::kEQ_STRICT, new (Z) Value(left_cid),
new (Z) Value(cid), /* number_check = */ false, Thread::kNoDeoptId);
new (Z) Value(cid), /* number_check = */ false, DeoptId::kNone);
ReplaceCall(call, check_cid);
return;
}
@@ -1430,7 +1432,7 @@ void CallSpecializer::ReplaceWithInstanceOf(InstanceCallInstr* call) {
}
TestCidsInstr* test_cids = new (Z) TestCidsInstr(
call->token_pos(), Token::kIS, new (Z) Value(left), *results,
can_deopt ? call->deopt_id() : Thread::kNoDeoptId);
can_deopt ? call->deopt_id() : DeoptId::kNone);
// Remove type.
ReplaceCall(call, test_cids);
return;
+4 -14
View File
@@ -17,20 +17,10 @@ template <typename T>
class ZoneGrowableArray;
class String;
class CHA : public StackResource {
class CHA : public ValueObject {
public:
explicit CHA(Thread* thread)
: StackResource(thread),
thread_(thread),
guarded_classes_(thread->zone(), 1),
previous_(thread->cha()) {
thread->set_cha(this);
}
~CHA() {
ASSERT(thread_->cha() == this);
thread_->set_cha(previous_);
}
: thread_(thread), guarded_classes_(thread->zone(), 1) {}
// Returns true if the class has subclasses.
static bool HasSubclasses(const Class& cls);
@@ -39,7 +29,8 @@ class CHA : public StackResource {
// Collect the concrete subclasses of 'cls' into 'class_ids'. Return true if
// the result is valid (may be invalid because we don't track the subclasses
// of classes allocated in the VM isolate or class Object).
bool ConcreteSubclasses(const Class& cls, GrowableArray<intptr_t>* class_ids);
static bool ConcreteSubclasses(const Class& cls,
GrowableArray<intptr_t>* class_ids);
// Return true if the class is implemented by some other class.
static bool IsImplemented(const Class& cls);
@@ -81,7 +72,6 @@ class CHA : public StackResource {
};
GrowableArray<GuardedClassInfo> guarded_classes_;
CHA* previous_;
};
} // namespace dart
+1
View File
@@ -75,6 +75,7 @@ compiler_sources = [
"cha.h",
"compiler_pass.cc",
"compiler_pass.h",
"compiler_state.h",
"frontend/base_flow_graph_builder.cc",
"frontend/base_flow_graph_builder.h",
"frontend/bytecode_reader.cc",
+107
View File
@@ -0,0 +1,107 @@
// Copyright (c) 2018, the Dart project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
#ifndef RUNTIME_VM_COMPILER_COMPILER_STATE_H_
#define RUNTIME_VM_COMPILER_COMPILER_STATE_H_
#include "vm/compiler/cha.h"
#include "vm/thread.h"
namespace dart {
// Deoptimization Id logic.
//
// Deoptimization ids are used to refer to deoptimization points, at which
// control can enter unoptimized code from the optimized version of the code.
//
// Note: any instruction that does a call has two deoptimization points,
// one before the call and one after the call - so that we could deoptimize
// to either before or after the call depending on whether the same call
// already occured in the optimized code (and potentially produced
// observable side-effects) or not.
//
// To simplify implementation we always allocate two deopt ids (one for before
// point and one for the after point).
class DeoptId : public AllStatic {
public:
static constexpr intptr_t kNone = -1;
static inline intptr_t Next(intptr_t deopt_id) { return deopt_id + kStep; }
static inline intptr_t ToDeoptAfter(intptr_t deopt_id) {
ASSERT(IsDeoptBefore(deopt_id));
return deopt_id + kAfterOffset;
}
static inline bool IsDeoptBefore(intptr_t deopt_id) {
return (deopt_id % kStep) == kBeforeOffset;
}
static inline bool IsDeoptAfter(intptr_t deopt_id) {
return (deopt_id % kStep) == kAfterOffset;
}
private:
static constexpr intptr_t kStep = 2;
static constexpr intptr_t kBeforeOffset = 0;
static constexpr intptr_t kAfterOffset = 1;
};
// Global compiler state attached to the thread.
class CompilerState : public StackResource {
public:
explicit CompilerState(Thread* thread) : StackResource(thread), cha_(thread) {
previous_ = thread->SetCompilerState(this);
}
~CompilerState() {
ASSERT(&thread()->compiler_state() == this);
thread()->SetCompilerState(previous_);
}
CHA& cha() { return cha_; }
intptr_t deopt_id() const { return deopt_id_; }
void set_deopt_id(int value) {
ASSERT(value >= 0);
deopt_id_ = value;
}
intptr_t GetNextDeoptId() {
ASSERT(deopt_id_ != DeoptId::kNone);
const intptr_t id = deopt_id_;
deopt_id_ = DeoptId::Next(deopt_id_);
return id;
}
static CompilerState& Current() {
return Thread::Current()->compiler_state();
}
private:
CHA cha_;
intptr_t deopt_id_ = 0;
CompilerState* previous_;
};
class DeoptIdScope : public StackResource {
public:
DeoptIdScope(Thread* thread, intptr_t deopt_id)
: StackResource(thread),
prev_deopt_id_(thread->compiler_state().deopt_id()) {
thread->compiler_state().set_deopt_id(deopt_id);
}
~DeoptIdScope() { thread()->compiler_state().set_deopt_id(prev_deopt_id_); }
private:
const intptr_t prev_deopt_id_;
DISALLOW_COPY_AND_ASSIGN(DeoptIdScope);
};
} // namespace dart
#endif // RUNTIME_VM_COMPILER_COMPILER_STATE_H_
@@ -315,7 +315,7 @@ Fragment BaseFlowGraphBuilder::LoadIndexed(intptr_t index_scale) {
Value* array = Pop();
LoadIndexedInstr* instr = new (Z)
LoadIndexedInstr(array, index, index_scale, kArrayCid, kAlignedAccess,
Thread::kNoDeoptId, TokenPosition::kNoSource);
DeoptId::kNone, TokenPosition::kNoSource);
Push(instr);
return Fragment(instr);
}
@@ -445,7 +445,7 @@ Fragment BaseFlowGraphBuilder::StoreIndexed(intptr_t class_id) {
StoreIndexedInstr* store = new (Z) StoreIndexedInstr(
Pop(), // Array.
index, value, emit_store_barrier, Instance::ElementSizeFor(class_id),
class_id, kAlignedAccess, Thread::kNoDeoptId, TokenPosition::kNoSource);
class_id, kAlignedAccess, DeoptId::kNone, TokenPosition::kNoSource);
Push(store);
return Fragment(store);
}
@@ -220,7 +220,7 @@ class BaseFlowGraphBuilder {
Fragment TailCall(const Code& code);
intptr_t GetNextDeoptId() {
intptr_t deopt_id = thread_->GetNextDeoptId();
intptr_t deopt_id = thread_->compiler_state().GetNextDeoptId();
if (context_level_array_ != NULL) {
intptr_t level = context_depth_;
context_level_array_->Add(deopt_id);
@@ -210,7 +210,7 @@ intptr_t BytecodeMetadataHelper::ReadPoolEntries(const Function& function,
}
obj = ICData::New(function, name,
array, // Arguments descriptor.
Thread::kNoDeoptId, checked_argument_count,
DeoptId::kNone, checked_argument_count,
ICData::RebindRule::kInstance);
#if defined(TAG_IC_DATA)
ICData::Cast(obj).set_tag(ICData::Tag::kInstanceCall);
@@ -254,7 +254,7 @@ intptr_t BytecodeMetadataHelper::ReadPoolEntries(const Function& function,
array ^= pool.ObjectAt(arg_desc_index);
obj = ICData::New(function, name,
array, // Arguments descriptor.
Thread::kNoDeoptId, num_args_checked,
DeoptId::kNone, num_args_checked,
ICData::RebindRule::kStatic);
ICData::Cast(obj).AddTarget(Function::Cast(elem));
#if defined(TAG_IC_DATA)
@@ -567,10 +567,10 @@ void BytecodeMetadataHelper::ReadExceptionsTable(const Code& bytecode) {
handler_types.SetAt(i, handler_type);
}
pc_descriptors_list->AddDescriptor(RawPcDescriptors::kOther, start_pc,
Thread::kNoDeoptId,
DeoptId::kNone,
TokenPosition::kNoSource, try_index);
pc_descriptors_list->AddDescriptor(RawPcDescriptors::kOther, end_pc,
Thread::kNoDeoptId,
DeoptId::kNone,
TokenPosition::kNoSource, -1);
exception_handlers_list->AddHandler(
@@ -164,7 +164,7 @@ void NestedStatement::AdjustContextLevel(intptr_t context_level) {
}
intptr_t FlowGraphBuilder::GetNextDeoptId() const {
intptr_t deopt_id = thread()->GetNextDeoptId();
intptr_t deopt_id = thread()->compiler_state().GetNextDeoptId();
if (context_level_array_ != NULL) {
intptr_t level = context_level();
context_level_array_->Add(deopt_id);
@@ -427,8 +427,8 @@ Definition* InlineExitCollector::JoinReturns(BlockEntryInstr** exit_block,
// Create a join of the returns.
intptr_t join_id = caller_graph_->max_block_id() + 1;
caller_graph_->set_max_block_id(join_id);
JoinEntryInstr* join = new (Z)
JoinEntryInstr(join_id, try_index, Thread::Current()->GetNextDeoptId());
JoinEntryInstr* join = new (Z) JoinEntryInstr(
join_id, try_index, CompilerState::Current().GetNextDeoptId());
// The dominator set of the join is the intersection of the dominator
// sets of all the predecessors. If we keep the dominator sets ordered
@@ -447,7 +447,7 @@ Definition* InlineExitCollector::JoinReturns(BlockEntryInstr** exit_block,
for (intptr_t i = 0; i < num_exits; ++i) {
// Add the control-flow edge.
GotoInstr* goto_instr =
new (Z) GotoInstr(join, Thread::Current()->GetNextDeoptId());
new (Z) GotoInstr(join, CompilerState::Current().GetNextDeoptId());
goto_instr->InheritDeoptTarget(zone(), ReturnAt(i));
LastInstructionAt(i)->LinkTo(goto_instr);
ExitBlockAt(i)->set_last_instruction(LastInstructionAt(i)->next());
@@ -533,18 +533,18 @@ void InlineExitCollector::ReplaceCall(TargetEntryInstr* callee_entry) {
// by the constant propagation.
TargetEntryInstr* false_block = new (Z) TargetEntryInstr(
caller_graph_->allocate_block_id(), call_block->try_index(),
Thread::Current()->GetNextDeoptId());
CompilerState::Current().GetNextDeoptId());
false_block->InheritDeoptTargetAfter(caller_graph_, call_, NULL);
false_block->LinkTo(call_->next());
call_block->ReplaceAsPredecessorWith(false_block);
ConstantInstr* true_const = caller_graph_->GetConstant(Bool::True());
BranchInstr* branch = new (Z)
BranchInstr(new (Z) StrictCompareInstr(
TokenPosition::kNoSource, Token::kEQ_STRICT,
new (Z) Value(true_const), new (Z) Value(true_const),
false, Thread::Current()->GetNextDeoptId()),
Thread::Current()->GetNextDeoptId()); // No number check.
BranchInstr* branch = new (Z) BranchInstr(
new (Z) StrictCompareInstr(TokenPosition::kNoSource, Token::kEQ_STRICT,
new (Z) Value(true_const),
new (Z) Value(true_const), false,
CompilerState::Current().GetNextDeoptId()),
CompilerState::Current().GetNextDeoptId()); // No number check.
branch->InheritDeoptTarget(zone(), call_);
*branch->true_successor_address() = callee_entry;
*branch->false_successor_address() = false_block;
@@ -2192,7 +2192,7 @@ void EffectGraphVisitor::VisitArrayNode(ArrayNode* node) {
{
LocalVariable* tmp_var = EnterTempLocalScope(array_val);
const intptr_t class_id = kArrayCid;
const intptr_t deopt_id = Thread::kNoDeoptId;
const intptr_t deopt_id = DeoptId::kNone;
for (int i = 0; i < node->length(); ++i) {
Value* array = Bind(new (Z) LoadLocalInstr(*tmp_var, node->token_pos()));
Value* index = Bind(new (Z) ConstantInstr(Smi::ZoneHandle(Z, Smi::New(i)),
@@ -3490,12 +3490,14 @@ void EffectGraphVisitor::VisitStoreInstanceFieldNode(
if (isolate()->use_field_guards()) {
store_value = Bind(BuildStoreExprTemp(store_value, token_pos));
GuardFieldClassInstr* guard_field_class = new (Z) GuardFieldClassInstr(
store_value, node->field(), thread()->GetNextDeoptId());
GuardFieldClassInstr* guard_field_class = new (Z)
GuardFieldClassInstr(store_value, node->field(),
thread()->compiler_state().GetNextDeoptId());
AddInstruction(guard_field_class);
store_value = Bind(BuildLoadExprTemp(token_pos));
GuardFieldLengthInstr* guard_field_length = new (Z) GuardFieldLengthInstr(
store_value, node->field(), thread()->GetNextDeoptId());
GuardFieldLengthInstr* guard_field_length = new (Z)
GuardFieldLengthInstr(store_value, node->field(),
thread()->compiler_state().GetNextDeoptId());
AddInstruction(guard_field_length);
store_value = Bind(BuildLoadExprTemp(token_pos));
}
@@ -63,6 +63,7 @@ class SourcePositionTest : public ValueObject {
new ParsedFunction(thread_, Function::ZoneHandle(function.raw()));
Parser::ParseFunction(parsed_function);
parsed_function->AllocateVariables();
CompilerState state(thread_);
FlowGraphBuilder builder(*parsed_function, *ic_data_array,
/* not building var desc */ NULL,
/* not inlining */ NULL, Compiler::kNoOSRDeoptId);
@@ -800,7 +800,7 @@ FlowGraph* StreamingFlowGraphBuilder::BuildGraphOfNoSuchMethodForwarder(
loop += condition;
Instruction* entry =
new (Z) GotoInstr(join, Thread::Current()->GetNextDeoptId());
new (Z) GotoInstr(join, CompilerState::Current().GetNextDeoptId());
body += Fragment(entry, loop_exit);
}
@@ -5041,8 +5041,9 @@ Fragment StreamingFlowGraphBuilder::BuildDoStatement() {
condition.IfTrueGoto(flow_graph_builder_, join);
loop_depth_dec();
return Fragment(new (Z) GotoInstr(join, Thread::Current()->GetNextDeoptId()),
condition.CreateFalseSuccessor(flow_graph_builder_));
return Fragment(
new (Z) GotoInstr(join, CompilerState::Current().GetNextDeoptId()),
condition.CreateFalseSuccessor(flow_graph_builder_));
}
Fragment StreamingFlowGraphBuilder::BuildForStatement() {
+1 -1
View File
@@ -172,7 +172,7 @@ class FlowGraphBuilder : public BaseFlowGraphBuilder {
LocalVariable* LookupVariable(intptr_t kernel_offset);
bool IsCompiledForOsr() { return osr_id_ != Thread::kNoDeoptId; }
bool IsCompiledForOsr() { return osr_id_ != DeoptId::kNone; }
TranslationHelper translation_helper_;
Thread* thread_;
+28 -29
View File
@@ -227,7 +227,7 @@ bool Intrinsifier::GraphIntrinsify(const ParsedFunction& parsed_function,
intptr_t block_id = builder.AllocateBlockId();
TargetEntryInstr* normal_entry =
new TargetEntryInstr(block_id, CatchClauseNode::kInvalidTryIndex,
Thread::Current()->GetNextDeoptId());
CompilerState::Current().GetNextDeoptId());
GraphEntryInstr* graph_entry = new GraphEntryInstr(
parsed_function, normal_entry, Compiler::kNoOSRDeoptId);
FlowGraph* graph =
@@ -372,7 +372,7 @@ class BlockBuilder : public ValueObject {
current_(entry),
fall_through_env_(new Environment(0,
0,
Thread::kNoDeoptId,
DeoptId::kNone,
flow_graph->parsed_function(),
NULL)) {}
@@ -400,8 +400,8 @@ class BlockBuilder : public ValueObject {
}
void AddIntrinsicReturn(Value* value) {
ReturnInstr* instr =
new ReturnInstr(TokenPos(), value, Thread::Current()->GetNextDeoptId());
ReturnInstr* instr = new ReturnInstr(
TokenPos(), value, CompilerState::Current().GetNextDeoptId());
AddInstruction(instr);
entry_->set_last_instruction(instr);
}
@@ -420,7 +420,7 @@ class BlockBuilder : public ValueObject {
Definition* AddUnboxInstr(Representation rep, Value* value, bool is_checked) {
Definition* unboxed_value =
AddDefinition(UnboxInstr::Create(rep, value, Thread::kNoDeoptId));
AddDefinition(UnboxInstr::Create(rep, value, DeoptId::kNone));
if (is_checked) {
// The type of |value| has already been checked and it is safe to
// adjust reaching type. This is done manually because there is no type
@@ -446,7 +446,7 @@ class BlockBuilder : public ValueObject {
Definition* InvokeMathCFunctionHelper(MethodRecognizer::Kind recognized_kind,
ZoneGrowableArray<Value*>* args) {
InvokeMathCFunctionInstr* invoke_math_c_function =
new InvokeMathCFunctionInstr(args, Thread::kNoDeoptId, recognized_kind,
new InvokeMathCFunctionInstr(args, DeoptId::kNone, recognized_kind,
TokenPos());
AddDefinition(invoke_math_c_function);
return invoke_math_c_function;
@@ -466,7 +466,7 @@ static void PrepareIndexedOp(BlockBuilder* builder,
new Value(array), length_offset, Type::ZoneHandle(Type::SmiType()),
TokenPosition::kNoSource));
builder->AddInstruction(new CheckArrayBoundInstr(
new Value(length), new Value(index), Thread::kNoDeoptId));
new Value(length), new Value(index), DeoptId::kNone));
}
static bool IntrinsifyArrayGetIndexed(FlowGraph* flow_graph,
@@ -495,7 +495,7 @@ static bool IntrinsifyArrayGetIndexed(FlowGraph* flow_graph,
Definition* result = builder.AddDefinition(new LoadIndexedInstr(
new Value(array), new Value(index),
Instance::ElementSizeFor(array_cid), // index scale
array_cid, kAlignedAccess, Thread::kNoDeoptId, builder.TokenPos()));
array_cid, kAlignedAccess, DeoptId::kNone, builder.TokenPos()));
// Box and/or convert result if necessary.
switch (array_cid) {
case kTypedDataInt32ArrayCid:
@@ -510,7 +510,7 @@ static bool IntrinsifyArrayGetIndexed(FlowGraph* flow_graph,
break;
case kTypedDataFloat32ArrayCid:
result = builder.AddDefinition(
new FloatToDoubleInstr(new Value(result), Thread::kNoDeoptId));
new FloatToDoubleInstr(new Value(result), DeoptId::kNone));
// Fall through.
case kTypedDataFloat64ArrayCid:
result = builder.AddDefinition(
@@ -580,8 +580,8 @@ static bool IntrinsifyArraySetIndexed(FlowGraph* flow_graph,
case kExternalTypedDataUint8ClampedArrayCid:
case kTypedDataInt16ArrayCid:
case kTypedDataUint16ArrayCid:
builder.AddInstruction(new CheckSmiInstr(
new Value(value), Thread::kNoDeoptId, builder.TokenPos()));
builder.AddInstruction(new CheckSmiInstr(new Value(value), DeoptId::kNone,
builder.TokenPos()));
break;
case kTypedDataInt32ArrayCid:
case kExternalTypedDataInt32ArrayCid:
@@ -625,14 +625,13 @@ static bool IntrinsifyArraySetIndexed(FlowGraph* flow_graph,
}
Zone* zone = flow_graph->zone();
Cids* value_check = Cids::CreateMonomorphic(zone, value_check_cid);
builder.AddInstruction(
new CheckClassInstr(new Value(value), Thread::kNoDeoptId,
*value_check, builder.TokenPos()));
builder.AddInstruction(new CheckClassInstr(
new Value(value), DeoptId::kNone, *value_check, builder.TokenPos()));
value = builder.AddUnboxInstr(rep, new Value(value),
/* is_checked = */ true);
if (array_cid == kTypedDataFloat32ArrayCid) {
value = builder.AddDefinition(
new DoubleToFloatInstr(new Value(value), Thread::kNoDeoptId));
new DoubleToFloatInstr(new Value(value), DeoptId::kNone));
}
break;
}
@@ -650,7 +649,7 @@ static bool IntrinsifyArraySetIndexed(FlowGraph* flow_graph,
builder.AddInstruction(new StoreIndexedInstr(
new Value(array), new Value(index), new Value(value), kNoStoreBarrier,
Instance::ElementSizeFor(array_cid), // index scale
array_cid, kAlignedAccess, Thread::kNoDeoptId, builder.TokenPos()));
array_cid, kAlignedAccess, DeoptId::kNone, builder.TokenPos()));
// Return null.
Definition* null_def = builder.AddNullDefinition();
builder.AddIntrinsicReturn(new Value(null_def));
@@ -777,7 +776,7 @@ static bool BuildCodeUnitAt(FlowGraph* flow_graph, intptr_t cid) {
Definition* result = builder.AddDefinition(new LoadIndexedInstr(
new Value(str), new Value(index), Instance::ElementSizeFor(cid), cid,
kAlignedAccess, Thread::kNoDeoptId, builder.TokenPos()));
kAlignedAccess, DeoptId::kNone, builder.TokenPos()));
builder.AddIntrinsicReturn(new Value(result));
return true;
}
@@ -815,8 +814,8 @@ static bool BuildSimdOp(FlowGraph* flow_graph, intptr_t cid, Token::Kind kind) {
Cids* value_check = Cids::CreateMonomorphic(zone, cid);
// Check argument. Receiver (left) is known to be a Float32x4.
builder.AddInstruction(new CheckClassInstr(
new Value(right), Thread::kNoDeoptId, *value_check, builder.TokenPos()));
builder.AddInstruction(new CheckClassInstr(new Value(right), DeoptId::kNone,
*value_check, builder.TokenPos()));
Definition* left_simd = builder.AddUnboxInstr(rep, new Value(left),
/* is_checked = */ true);
@@ -825,7 +824,7 @@ static bool BuildSimdOp(FlowGraph* flow_graph, intptr_t cid, Token::Kind kind) {
Definition* unboxed_result = builder.AddDefinition(SimdOpInstr::Create(
SimdOpInstr::KindForOperator(cid, kind), new Value(left_simd),
new Value(right_simd), Thread::kNoDeoptId));
new Value(right_simd), DeoptId::kNone));
Definition* result =
builder.AddDefinition(BoxInstr::Create(rep, new Value(unboxed_result)));
builder.AddIntrinsicReturn(new Value(result));
@@ -860,8 +859,8 @@ static bool BuildFloat32x4Shuffle(FlowGraph* flow_graph,
builder.AddUnboxInstr(kUnboxedFloat32x4, new Value(receiver),
/* is_checked = */ true);
Definition* unboxed_result = builder.AddDefinition(SimdOpInstr::Create(
kind, new Value(unboxed_receiver), Thread::kNoDeoptId));
Definition* unboxed_result = builder.AddDefinition(
SimdOpInstr::Create(kind, new Value(unboxed_receiver), DeoptId::kNone));
Definition* result = builder.AddDefinition(
BoxInstr::Create(kUnboxedDouble, new Value(unboxed_result)));
@@ -956,7 +955,7 @@ bool Intrinsifier::Build_GrowableArrayGetIndexed(FlowGraph* flow_graph) {
Definition* result = builder.AddDefinition(new LoadIndexedInstr(
new Value(backing_store), new Value(index),
Instance::ElementSizeFor(kArrayCid), // index scale
kArrayCid, kAlignedAccess, Thread::kNoDeoptId, builder.TokenPos()));
kArrayCid, kAlignedAccess, DeoptId::kNone, builder.TokenPos()));
builder.AddIntrinsicReturn(new Value(result));
return true;
}
@@ -998,7 +997,7 @@ bool Intrinsifier::Build_GrowableArraySetIndexedUnchecked(
new Value(backing_store), new Value(index), new Value(value),
kEmitStoreBarrier,
Instance::ElementSizeFor(kArrayCid), // index scale
kArrayCid, kAlignedAccess, Thread::kNoDeoptId, builder.TokenPos()));
kArrayCid, kAlignedAccess, DeoptId::kNone, builder.TokenPos()));
// Return null.
Definition* null_def = builder.AddNullDefinition();
builder.AddIntrinsicReturn(new Value(null_def));
@@ -1015,8 +1014,8 @@ bool Intrinsifier::Build_GrowableArraySetData(FlowGraph* flow_graph) {
Zone* zone = flow_graph->zone();
Cids* value_check = Cids::CreateMonomorphic(zone, kArrayCid);
builder.AddInstruction(new CheckClassInstr(
new Value(data), Thread::kNoDeoptId, *value_check, builder.TokenPos()));
builder.AddInstruction(new CheckClassInstr(new Value(data), DeoptId::kNone,
*value_check, builder.TokenPos()));
builder.AddInstruction(new StoreInstanceFieldInstr(
GrowableObjectArray::data_offset(), new Value(growable_array),
@@ -1035,8 +1034,8 @@ bool Intrinsifier::Build_GrowableArraySetLength(FlowGraph* flow_graph) {
Definition* length = builder.AddParameter(1);
Definition* growable_array = builder.AddParameter(2);
builder.AddInstruction(new CheckSmiInstr(
new Value(length), Thread::kNoDeoptId, builder.TokenPos()));
builder.AddInstruction(
new CheckSmiInstr(new Value(length), DeoptId::kNone, builder.TokenPos()));
builder.AddInstruction(new StoreInstanceFieldInstr(
GrowableObjectArray::length_offset(), new Value(growable_array),
new Value(length), kNoStoreBarrier, builder.TokenPos()));
@@ -1058,7 +1057,7 @@ bool Intrinsifier::Build_DoubleFlipSignBit(FlowGraph* flow_graph) {
builder.AddUnboxInstr(kUnboxedDouble, new Value(receiver),
/* is_checked = */ true);
Definition* unboxed_result = builder.AddDefinition(new UnaryDoubleOpInstr(
Token::kNEGATE, new Value(unboxed_value), Thread::kNoDeoptId));
Token::kNEGATE, new Value(unboxed_value), DeoptId::kNone));
Definition* result = builder.AddDefinition(
BoxInstr::Create(kUnboxedDouble, new Value(unboxed_result)));
builder.AddIntrinsicReturn(new Value(result));
+11 -10
View File
@@ -23,6 +23,7 @@
#include "vm/compiler/backend/type_propagator.h"
#include "vm/compiler/cha.h"
#include "vm/compiler/compiler_pass.h"
#include "vm/compiler/compiler_state.h"
#include "vm/compiler/frontend/flow_graph_builder.h"
#include "vm/compiler/frontend/kernel_to_il.h"
#include "vm/compiler/jit/jit_call_specializer.h"
@@ -676,7 +677,10 @@ RawCode* CompileParsedFunctionHelper::FinalizeCompilation(
THR_Print("--> FAIL: Loading invalidation.");
}
}
if (!thread()->cha()->IsConsistentWithCurrentHierarchy()) {
if (!thread()
->compiler_state()
.cha()
.IsConsistentWithCurrentHierarchy()) {
code_is_valid = false;
if (trace_compiler) {
THR_Print("--> FAIL: Class hierarchy has new subclasses.");
@@ -706,7 +710,7 @@ RawCode* CompileParsedFunctionHelper::FinalizeCompilation(
// The generated code was compiled under certain assumptions about
// class hierarchy and field types. Register these dependencies
// to ensure that the code will be deoptimized if they are violated.
thread()->cha()->RegisterDependencies(code);
thread()->compiler_state().cha().RegisterDependencies(code);
const ZoneGrowableArray<const Field*>& guarded_fields =
*flow_graph->parsed_function().guarded_fields();
@@ -741,7 +745,7 @@ void CompileParsedFunctionHelper::CheckIfBackgroundCompilerIsBeingStopped() {
if (!isolate()->background_compiler()->is_running()) {
// The background compiler is being stopped.
Compiler::AbortBackgroundCompilation(
Thread::kNoDeoptId, "Background compilation is being stopped");
DeoptId::kNone, "Background compilation is being stopped");
}
}
@@ -776,15 +780,12 @@ RawCode* CompileParsedFunctionHelper::Compile(CompilationPipeline* pipeline) {
Code* volatile result = &Code::ZoneHandle(zone);
while (!done) {
*result = Code::null();
DeoptIdScope deopt_id_scope(thread(), 0);
LongJumpScope jump;
if (setjmp(*jump.Set()) == 0) {
FlowGraph* flow_graph = nullptr;
ZoneGrowableArray<const ICData*>* ic_data_array = nullptr;
// Class hierarchy analysis is registered with the thread in the
// constructor and unregisters itself upon destruction.
CHA cha(thread());
CompilerState compiler_state(thread());
// TimerScope needs an isolate to be properly terminated in case of a
// LongJump.
@@ -812,7 +813,7 @@ RawCode* CompileParsedFunctionHelper::Compile(CompilationPipeline* pipeline) {
if (Compiler::IsBackgroundCompilation() &&
(function.ic_data_array() == Array::null())) {
Compiler::AbortBackgroundCompilation(
Thread::kNoDeoptId, "RestoreICDataMap: ICData array cleared.");
DeoptId::kNone, "RestoreICDataMap: ICData array cleared.");
}
}
@@ -1014,7 +1015,7 @@ static RawObject* CompileFunctionHelper(CompilationPipeline* pipeline,
// Loading occured while parsing. We need to abort here because state
// changed while compiling.
Compiler::AbortBackgroundCompilation(
Thread::kNoDeoptId,
DeoptId::kNone,
"Invalidated state during parsing because of script loading");
}
}
@@ -1351,7 +1352,7 @@ void Compiler::ComputeLocalVarDescriptors(const Code& code) {
ASSERT(!function.IsIrregexpFunction());
// In background compilation, parser can produce 'errors": bailouts
// if state changed while compiling in background.
DeoptIdScope deopt_id_scope(Thread::Current(), 0);
CompilerState state(Thread::Current());
LongJumpScope jump;
if (setjmp(*jump.Set()) == 0) {
ZoneGrowableArray<const ICData*>* ic_data_array =
+2 -1
View File
@@ -6,6 +6,7 @@
#define RUNTIME_VM_COMPILER_JIT_COMPILER_H_
#include "vm/allocation.h"
#include "vm/compiler/compiler_state.h"
#include "vm/growable_array.h"
#include "vm/runtime_entry.h"
#include "vm/thread_pool.h"
@@ -79,7 +80,7 @@ class IrregexpCompilationPipeline : public CompilationPipeline {
class Compiler : public AllStatic {
public:
static const intptr_t kNoOSRDeoptId = Thread::kNoDeoptId;
static const intptr_t kNoOSRDeoptId = DeoptId::kNone;
static bool IsBackgroundCompilation();
// The result for a function may change if debugging gets turned on/off.
@@ -211,7 +211,7 @@ void JitCallSpecializer::VisitStoreInstanceField(
if (Compiler::IsBackgroundCompilation()) {
isolate()->AddDeoptimizingBoxedField(field);
Compiler::AbortBackgroundCompilation(
Thread::kNoDeoptId, "Unboxing instance field while compiling");
DeoptId::kNone, "Unboxing instance field while compiling");
UNREACHABLE();
}
if (FLAG_trace_optimization || FLAG_trace_field_guards) {
+2 -2
View File
@@ -250,7 +250,7 @@ ActivationFrame::ActivationFrame(uword pc,
token_pos_initialized_(false),
token_pos_(TokenPosition::kNoSource),
try_index_(-1),
deopt_id_(Thread::kNoDeoptId),
deopt_id_(DeoptId::kNone),
line_number_(-1),
column_number_(-1),
context_level_(-1),
@@ -700,7 +700,7 @@ intptr_t ActivationFrame::ContextLevel() {
GetVarDescriptors();
intptr_t deopt_id = DeoptId();
if (deopt_id == Thread::kNoDeoptId) {
if (deopt_id == DeoptId::kNone) {
PrintDescriptorsError("Missing deopt id");
}
intptr_t var_desc_len = var_descriptors_.Length();
+1 -1
View File
@@ -108,7 +108,7 @@ void DeferredRetAddr::Materialize(DeoptContext* deopt_context) {
// Check that deopt_id exists.
// TODO(vegorov): verify after deoptimization targets as well.
#ifdef DEBUG
ASSERT(Thread::IsDeoptAfter(deopt_id_) ||
ASSERT(DeoptId::IsDeoptAfter(deopt_id_) ||
(code.GetPcForDeoptId(deopt_id_, RawPcDescriptors::kDeopt) != 0));
#endif
+1 -1
View File
@@ -862,7 +862,7 @@ uword DeoptInstr::GetRetAddress(DeoptInstr* instr,
static_cast<DeoptRetAddressInstr*>(instr);
// The following assert may trigger when displaying a backtrace
// from the simulator.
ASSERT(Thread::IsDeoptAfter(ret_address_instr->deopt_id()));
ASSERT(DeoptId::IsDeoptAfter(ret_address_instr->deopt_id()));
ASSERT(!object_table.IsNull());
Thread* thread = Thread::Current();
Zone* zone = thread->zone();
+4 -4
View File
@@ -3613,7 +3613,7 @@ RawError* Class::EnsureIsFinalized(Thread* thread) const {
return Error::null();
}
if (Compiler::IsBackgroundCompilation()) {
Compiler::AbortBackgroundCompilation(Thread::kNoDeoptId,
Compiler::AbortBackgroundCompilation(DeoptId::kNone,
"Class finalization while compiling");
}
ASSERT(thread->IsMutatorThread());
@@ -13735,7 +13735,7 @@ void PcDescriptors::Verify(const Function& function) const {
Iterator iter(*this, RawPcDescriptors::kDeopt | RawPcDescriptors::kIcCall);
while (iter.MoveNext()) {
// 'deopt_id' is set for kDeopt and kIcCall and must be unique for one kind.
if (Thread::IsDeoptAfter(iter.DeoptId())) {
if (DeoptId::IsDeoptAfter(iter.DeoptId())) {
// TODO(vegorov): some instructions contain multiple calls and have
// multiple "after" targets recorded. Right now it is benign but might
// lead to issues in the future. Fix that and enable verification.
@@ -15274,7 +15274,7 @@ RawICData* ICData::New() {
NoSafepointScope no_safepoint;
result ^= raw;
}
result.set_deopt_id(Thread::kNoDeoptId);
result.set_deopt_id(DeoptId::kNone);
result.set_state_bits(0);
#if defined(TAG_IC_DATA)
result.set_tag(ICData::Tag::kUnknown);
@@ -15954,7 +15954,7 @@ intptr_t Code::GetDeoptIdForOsr(uword pc) const {
return iter.DeoptId();
}
}
return Thread::kNoDeoptId;
return DeoptId::kNone;
}
const char* Code::ToCString() const {
+1 -1
View File
@@ -228,7 +228,7 @@ void ParsedFunction::AddToGuardedFields(const Field* field) const {
if (Compiler::IsBackgroundCompilation()) {
if (!other->IsConsistentWith(*field)) {
Compiler::AbortBackgroundCompilation(
Thread::kNoDeoptId,
DeoptId::kNone,
"Field's guarded state changed during compilation");
}
}
+2 -1
View File
@@ -61,7 +61,8 @@ BlockLabel::BlockLabel()
#if !defined(DART_PRECOMPILED_RUNTIME)
if (!FLAG_interpret_irregexp) {
// Only needed by the compiled IR backend.
block_ = new JoinEntryInstr(-1, -1, Thread::Current()->GetNextDeoptId());
block_ =
new JoinEntryInstr(-1, -1, CompilerState::Current().GetNextDeoptId());
}
#endif
}
+3 -1
View File
@@ -133,7 +133,9 @@ class IRRegExpMacroAssembler : public RegExpMacroAssembler {
void FinalizeRegistersArray();
private:
intptr_t GetNextDeoptId() const { return thread_->GetNextDeoptId(); }
intptr_t GetNextDeoptId() const {
return thread_->compiler_state().GetNextDeoptId();
}
// Generate the contents of preset blocks. The entry block is the entry point
// of the generated code.
+3 -3
View File
@@ -1428,7 +1428,7 @@ DEFINE_RUNTIME_ENTRY(SingleTargetMiss, 1) {
kTypeArgsLen, old_target.num_fixed_parameters()));
const ICData& ic_data =
ICData::Handle(zone, ICData::New(caller_function, name, descriptor,
Thread::kNoDeoptId, 1, /* args_tested */
DeoptId::kNone, 1, /* args_tested */
ICData::kInstance));
// Maybe add the new target.
@@ -1504,7 +1504,7 @@ DEFINE_RUNTIME_ENTRY(UnlinkedCall, 2) {
const Array& descriptor = Array::Handle(zone, unlinked.args_descriptor());
const ICData& ic_data =
ICData::Handle(zone, ICData::New(caller_function, name, descriptor,
Thread::kNoDeoptId, 1, /* args_tested */
DeoptId::kNone, 1, /* args_tested */
ICData::kInstance));
Class& cls = Class::Handle(zone, receiver.clazz());
@@ -1584,7 +1584,7 @@ DEFINE_RUNTIME_ENTRY(MonomorphicMiss, 1) {
kTypeArgsLen, old_target.num_fixed_parameters()));
const ICData& ic_data =
ICData::Handle(zone, ICData::New(caller_function, name, descriptor,
Thread::kNoDeoptId, 1, /* args_tested */
DeoptId::kNone, 1, /* args_tested */
ICData::kInstance));
// Add the first target.
-2
View File
@@ -92,10 +92,8 @@ Thread::Thread(Isolate* isolate)
deferred_interrupts_mask_(0),
deferred_interrupts_(0),
stack_overflow_count_(0),
cha_(NULL),
hierarchy_info_(NULL),
type_usage_info_(NULL),
deopt_id_(0),
pending_functions_(GrowableObjectArray::null()),
active_exception_(Object::null()),
active_stacktrace_(Object::null()),
+13 -41
View File
@@ -22,7 +22,7 @@ namespace dart {
class AbstractType;
class ApiLocalScope;
class Array;
class CHA;
class CompilerState;
class Class;
class Code;
class CompilerStats;
@@ -369,15 +369,9 @@ class Thread : public BaseThread {
// Has |this| exited Dart code?
bool HasExitedDartCode() const;
// The (topmost) CHA for the compilation in this thread.
CHA* cha() const {
ASSERT(isolate_ != NULL);
return cha_;
}
void set_cha(CHA* value) {
ASSERT(isolate_ != NULL);
cha_ = value;
CompilerState& compiler_state() {
ASSERT(compiler_state_ != nullptr);
return *compiler_state_;
}
HierarchyInfo* hierarchy_info() const {
@@ -560,35 +554,6 @@ class Thread : public BaseThread {
static bool ObjectAtOffset(intptr_t offset, Object* object);
static intptr_t OffsetFromThread(const RuntimeEntry* runtime_entry);
static const intptr_t kNoDeoptId = -1;
static const intptr_t kDeoptIdStep = 2;
static const intptr_t kDeoptIdBeforeOffset = 0;
static const intptr_t kDeoptIdAfterOffset = 1;
intptr_t deopt_id() const { return deopt_id_; }
void set_deopt_id(int value) {
ASSERT(value >= 0);
deopt_id_ = value;
}
intptr_t GetNextDeoptId() {
ASSERT(deopt_id_ != kNoDeoptId);
const intptr_t id = deopt_id_;
deopt_id_ += kDeoptIdStep;
return id;
}
static intptr_t ToDeoptAfter(intptr_t deopt_id) {
ASSERT(IsDeoptBefore(deopt_id));
return deopt_id + kDeoptIdAfterOffset;
}
static bool IsDeoptBefore(intptr_t deopt_id) {
return (deopt_id % kDeoptIdStep) == kDeoptIdBeforeOffset;
}
static bool IsDeoptAfter(intptr_t deopt_id) {
return (deopt_id % kDeoptIdStep) == kDeoptIdAfterOffset;
}
LongJumpScope* long_jump_base() const { return long_jump_base_; }
void set_long_jump_base(LongJumpScope* value) { long_jump_base_ = value; }
@@ -819,6 +784,13 @@ class Thread : public BaseThread {
template <class T>
T* AllocateReusableHandle();
// Set the current compiler state and return the previous compiler state.
CompilerState* SetCompilerState(CompilerState* state) {
CompilerState* previous = compiler_state_;
compiler_state_ = state;
return previous;
}
// Accessed from generated code.
// ** This block of fields must come first! **
// For AOT cross-compilation, we rely on these members having the same offsets
@@ -886,10 +858,9 @@ class Thread : public BaseThread {
int32_t stack_overflow_count_;
// Compiler state:
CHA* cha_;
CompilerState* compiler_state_ = nullptr;
HierarchyInfo* hierarchy_info_;
TypeUsageInfo* type_usage_info_;
intptr_t deopt_id_; // Compilation specific counter.
RawGrowableObjectArray* pending_functions_;
// JumpToExceptionHandler state:
@@ -958,6 +929,7 @@ class Thread : public BaseThread {
friend class Simulator;
friend class StackZone;
friend class ThreadRegistry;
friend class CompilerState;
DISALLOW_COPY_AND_ASSIGN(Thread);
};