diff --git a/runtime/vm/compiler/backend/block_builder.h b/runtime/vm/compiler/backend/block_builder.h index 4a366314880..45662802886 100644 --- a/runtime/vm/compiler/backend/block_builder.h +++ b/runtime/vm/compiler/backend/block_builder.h @@ -24,8 +24,7 @@ class BlockBuilder : public ValueObject { flow_graph->inlining_id())), entry_(entry), current_(entry), - dummy_env_( - new Environment(0, 0, 0, flow_graph->parsed_function(), nullptr)) { + dummy_env_(new Environment(0, 0, 0, flow_graph->function(), nullptr)) { // Some graph transformations use environments from block entries. entry->SetEnvironment(dummy_env_); } diff --git a/runtime/vm/compiler/backend/il.cc b/runtime/vm/compiler/backend/il.cc index e7f9172b1db..5330a4e69ea 100644 --- a/runtime/vm/compiler/backend/il.cc +++ b/runtime/vm/compiler/backend/il.cc @@ -5867,9 +5867,9 @@ Environment* Environment::From(Zone* zone, intptr_t fixed_parameter_count, intptr_t lazy_deopt_pruning_count, const ParsedFunction& parsed_function) { - Environment* env = - new (zone) Environment(definitions.length(), fixed_parameter_count, - lazy_deopt_pruning_count, parsed_function, NULL); + Environment* env = new (zone) + Environment(definitions.length(), fixed_parameter_count, + lazy_deopt_pruning_count, parsed_function.function(), NULL); for (intptr_t i = 0; i < definitions.length(); ++i) { env->values_.Add(new (zone) Value(definitions[i])); } @@ -5882,9 +5882,9 @@ void Environment::PushValue(Value* value) { Environment* Environment::DeepCopy(Zone* zone, intptr_t length) const { ASSERT(length <= values_.length()); - Environment* copy = new (zone) Environment( - length, fixed_parameter_count_, LazyDeoptPruneCount(), parsed_function_, - (outer_ == NULL) ? NULL : outer_->DeepCopy(zone)); + Environment* copy = new (zone) + Environment(length, fixed_parameter_count_, LazyDeoptPruneCount(), + function_, (outer_ == NULL) ? NULL : outer_->DeepCopy(zone)); copy->SetDeoptId(DeoptIdBits::decode(bitfield_)); copy->SetLazyDeoptToBeforeDeoptId(LazyDeoptToBeforeDeoptId()); if (locations_ != NULL) { @@ -6355,16 +6355,10 @@ InvokeMathCFunctionInstr::InvokeMathCFunctionInstr( intptr_t deopt_id, MethodRecognizer::Kind recognized_kind, const InstructionSource& source) - : PureDefinition(source, deopt_id), - inputs_(inputs), + : VariadicDefinition(inputs, source, deopt_id), recognized_kind_(recognized_kind), token_pos_(source.token_pos) { ASSERT(inputs_->length() == ArgumentCountFor(recognized_kind_)); - for (intptr_t i = 0; i < inputs_->length(); ++i) { - ASSERT((*inputs)[i] != NULL); - (*inputs)[i]->set_instruction(this); - (*inputs)[i]->set_use_index(i); - } } intptr_t InvokeMathCFunctionInstr::ArgumentCountFor( @@ -6599,7 +6593,7 @@ void FfiCallInstr::EmitParamMoves(FlowGraphCompiler* compiler, } // Moves for arguments. - compiler::ffi::FrameRebase rebase(zone_, /*old_base=*/FPREG, + compiler::ffi::FrameRebase rebase(compiler->zone(), /*old_base=*/FPREG, /*new_base=*/saved_fp, /*stack_delta=*/0); intptr_t def_index = 0; @@ -6627,7 +6621,8 @@ void FfiCallInstr::EmitParamMoves(FlowGraphCompiler* compiler, : arg_target.IsMultiple() ? *arg_target.AsMultiple().locations()[i] : arg_target.IsPointerToMemory() ? arg_target.AsPointerToMemory().pointer_location() - : /*arg_target.IsStack()*/ arg_target.Split(zone_, num_defs, i); + : /*arg_target.IsStack()*/ arg_target.Split(compiler->zone(), + num_defs, i); ConstantTemporaryAllocator temp_alloc(temp0); if (origin.IsConstant()) { @@ -6692,8 +6687,8 @@ void FfiCallInstr::EmitParamMoves(FlowGraphCompiler* compiler, // TypedData/Pointer data pointed to in temp. const auto& dst = compiler::ffi::NativeRegistersLocation( - zone_, pointer_loc.payload_type(), pointer_loc.container_type(), - temp0); + compiler->zone(), pointer_loc.payload_type(), + pointer_loc.container_type(), temp0); compiler->EmitNativeMove(dst, pointer_loc, &temp_alloc); __ LoadField(temp0, compiler::FieldAddress( @@ -6715,8 +6710,8 @@ void FfiCallInstr::EmitParamMoves(FlowGraphCompiler* compiler, __ MoveRegister(temp0, SPREG); __ AddImmediate(temp0, sp_offset); const auto& src = compiler::ffi::NativeRegistersLocation( - zone_, pointer_loc.payload_type(), pointer_loc.container_type(), - temp0); + compiler->zone(), pointer_loc.payload_type(), + pointer_loc.container_type(), temp0); __ Comment("pointer_loc %s <- src %s", pointer_loc.ToCString(), src.ToCString()); compiler->EmitNativeMove(pointer_loc, src, &temp_alloc); @@ -7001,21 +6996,15 @@ LocationSummary* CCallInstr::MakeLocationSummaryInternal( } CCallInstr::CCallInstr( - Zone* zone, const compiler::ffi::NativeCallingConvention& native_calling_convention, InputsArray* inputs) - : Definition(DeoptId::kNone), - zone_(zone), - native_calling_convention_(native_calling_convention), - inputs_(inputs) { + : VariadicDefinition(inputs, DeoptId::kNone), + native_calling_convention_(native_calling_convention) { #ifdef DEBUG const intptr_t num_inputs = native_calling_convention.argument_locations().length() + 1; ASSERT(num_inputs == inputs->length()); #endif - for (intptr_t i = 0, n = inputs_->length(); i < n; ++i) { - SetInputAt(i, (*inputs_)[i]); - } } Representation CCallInstr::RequiredInputRepresentation(intptr_t idx) const { @@ -7037,7 +7026,7 @@ void CCallInstr::EmitParamMoves(FlowGraphCompiler* compiler, } ConstantTemporaryAllocator temp_alloc(temp0); - compiler::ffi::FrameRebase rebase(zone_, /*old_base=*/FPREG, + compiler::ffi::FrameRebase rebase(compiler->zone(), /*old_base=*/FPREG, /*new_base=*/saved_fp, /*stack_delta=*/0); diff --git a/runtime/vm/compiler/backend/il.h b/runtime/vm/compiler/backend/il.h index af9f8b14a25..a9e3066818a 100644 --- a/runtime/vm/compiler/backend/il.h +++ b/runtime/vm/compiler/backend/il.h @@ -1488,7 +1488,7 @@ class ParallelMoveInstr : public TemplateInstruction<0, NoThrow> { // predecessors. Targets are all other basic block entries. The types // enforce edge-split form---joins are forbidden as the successors of // branches. -class BlockEntryInstr : public Instruction { +class BlockEntryInstr : public TemplateInstruction<0, NoThrow> { public: virtual intptr_t PredecessorCount() const = 0; virtual BlockEntryInstr* PredecessorAt(intptr_t index) const = 0; @@ -1558,12 +1558,6 @@ class BlockEntryInstr : public Instruction { GrowableArray* preorder, GrowableArray* parent); - virtual intptr_t InputCount() const { return 0; } - virtual Value* InputAt(intptr_t i) const { - UNREACHABLE(); - return NULL; - } - virtual bool CanBecomeDeoptimizationTarget() const { // BlockEntry environment is copied to Goto and Branch instructions // when we insert new blocks targeting this block. @@ -1574,8 +1568,6 @@ class BlockEntryInstr : public Instruction { virtual bool HasUnknownSideEffects() const { return false; } - virtual bool MayThrow() const { return false; } - intptr_t try_index() const { return try_index_; } void set_try_index(intptr_t index) { try_index_ = index; } @@ -1629,7 +1621,7 @@ class BlockEntryInstr : public Instruction { intptr_t try_index, intptr_t deopt_id, intptr_t stack_depth) - : Instruction(deopt_id), + : TemplateInstruction(deopt_id), block_id_(block_id), try_index_(try_index), stack_depth_(stack_depth), @@ -1642,8 +1634,6 @@ class BlockEntryInstr : public Instruction { BitVector* block_marks); private: - virtual void RawSetInputAt(intptr_t i, Value* value) { UNREACHABLE(); } - virtual void ClearPredecessors() = 0; virtual void AddPredecessor(BlockEntryInstr* predecessor) = 0; @@ -2253,17 +2243,6 @@ class AliasIdentity : public ValueObject { } } - static bool Parse(const char* str, AliasIdentity* out) { -#define VALUE_CASE(name, val) \ - if (strcmp(str, #name) == 0) { \ - out->value_ = k##name; \ - return true; \ - } - FOR_EACH_ALIAS_IDENTITY_VALUE(VALUE_CASE) -#undef VALUE_CASE - return false; - } - bool IsUnknown() const { return value_ == kUnknown; } bool IsAliased() const { return value_ == kAliased; } bool IsNotAliased() const { return (value_ & kNotAliased) != 0; } @@ -2553,18 +2532,67 @@ class TemplateDefinition : public CSETrait::Base { virtual void RawSetInputAt(intptr_t i, Value* value) { inputs_[i] = value; } }; -class PhiInstr : public Definition { +class VariadicDefinition : public Definition { public: - PhiInstr(JoinEntryInstr* block, intptr_t num_inputs) - : block_(block), - inputs_(num_inputs), - representation_(kTagged), - is_alive_(false), - is_receiver_(kUnknownReceiver) { - for (intptr_t i = 0; i < num_inputs; ++i) { - inputs_.Add(NULL); + explicit VariadicDefinition(InputsArray* inputs, + intptr_t deopt_id = DeoptId::kNone) + : Definition(deopt_id), inputs_(inputs) { + for (intptr_t i = 0, n = inputs_->length(); i < n; ++i) { + SetInputAt(i, (*inputs_)[i]); } } + VariadicDefinition(InputsArray* inputs, + const InstructionSource& source, + intptr_t deopt_id = DeoptId::kNone) + : Definition(source, deopt_id), inputs_(inputs) { + for (intptr_t i = 0, n = inputs_->length(); i < n; ++i) { + SetInputAt(i, (*inputs_)[i]); + } + } + + intptr_t InputCount() const { return inputs_->length(); } + Value* InputAt(intptr_t i) const { return (*inputs_)[i]; } + + protected: + InputsArray* inputs_; + + private: + void RawSetInputAt(intptr_t i, Value* value) { (*inputs_)[i] = value; } +}; + +class VariadicDefinitionWithEmbeddedInputs : public Definition { + public: + explicit VariadicDefinitionWithEmbeddedInputs( + const intptr_t num_inputs, + intptr_t deopt_id = DeoptId::kNone) + : Definition(deopt_id), inputs_(num_inputs) { + inputs_.EnsureLength(num_inputs, nullptr); + } + VariadicDefinitionWithEmbeddedInputs(const intptr_t num_inputs, + const InstructionSource& source, + intptr_t deopt_id = DeoptId::kNone) + : Definition(source, deopt_id), inputs_(num_inputs) { + inputs_.EnsureLength(num_inputs, nullptr); + } + + intptr_t InputCount() const { return inputs_.length(); } + Value* InputAt(intptr_t i) const { return inputs_[i]; } + + protected: + GrowableArray inputs_; + + private: + void RawSetInputAt(intptr_t i, Value* value) { inputs_[i] = value; } +}; + +class PhiInstr : public VariadicDefinitionWithEmbeddedInputs { + public: + PhiInstr(JoinEntryInstr* block, intptr_t num_inputs) + : VariadicDefinitionWithEmbeddedInputs(num_inputs), + block_(block), + representation_(kTagged), + is_alive_(false), + is_receiver_(kUnknownReceiver) {} // Get the block entry for that instruction. virtual BlockEntryInstr* GetBlock() { return block(); } @@ -2573,10 +2601,6 @@ class PhiInstr : public Definition { virtual CompileType ComputeType() const; virtual bool RecomputeType(); - intptr_t InputCount() const { return inputs_.length(); } - - Value* InputAt(intptr_t i) const { return inputs_[i]; } - virtual bool ComputeCanDeoptimize() const { return false; } virtual bool HasUnknownSideEffects() const { return false; } @@ -2644,10 +2668,7 @@ class PhiInstr : public Definition { // predecessors. friend class ConstantPropagator; - void RawSetInputAt(intptr_t i, Value* value) { inputs_[i] = value; } - JoinEntryInstr* block_; - GrowableArray inputs_; Representation representation_; BitVector* reaching_defs_ = nullptr; bool is_alive_; @@ -2663,7 +2684,7 @@ class PhiInstr : public Definition { // (0 is the very first parameter, 1 is next and so on). When [base_reg] is // set to SPREG, value [index] needs to be reversed (0 is the very last // parameter, 1 is next and so on) to get the sp relative position. -class ParameterInstr : public Definition { +class ParameterInstr : public TemplateDefinition<0, NoThrow> { public: ParameterInstr(intptr_t index, intptr_t param_offset, @@ -2687,12 +2708,6 @@ class ParameterInstr : public Definition { virtual BlockEntryInstr* GetBlock() { return block_; } void set_block(BlockEntryInstr* block) { block_ = block; } - intptr_t InputCount() const { return 0; } - Value* InputAt(intptr_t i) const { - UNREACHABLE(); - return NULL; - } - virtual Representation representation() const { return representation_; } virtual Representation RequiredInputRepresentation(intptr_t index) const { @@ -2711,13 +2726,9 @@ class ParameterInstr : public Definition { virtual CompileType ComputeType() const; - virtual bool MayThrow() const { return false; } - PRINT_OPERANDS_TO_SUPPORT private: - virtual void RawSetInputAt(intptr_t i, Value* value) { UNREACHABLE(); } - const intptr_t index_; // The offset (in words) of the last slot of the parameter, relative @@ -2739,7 +2750,7 @@ class ParameterInstr : public Definition { // NativeEntryInstr::EmitNativeCode for more details. // // TOOD(33549): Unify with ParameterInstr. -class NativeParameterInstr : public Definition { +class NativeParameterInstr : public TemplateDefinition<0, NoThrow> { public: NativeParameterInstr(const compiler::ffi::CallbackMarshaller& marshaller, intptr_t def_index) @@ -2751,12 +2762,6 @@ class NativeParameterInstr : public Definition { return marshaller_.RepInFfiCall(def_index_); } - intptr_t InputCount() const { return 0; } - Value* InputAt(intptr_t i) const { - UNREACHABLE(); - return NULL; - } - virtual bool ComputeCanDeoptimize() const { return false; } virtual bool HasUnknownSideEffects() const { return false; } @@ -2764,13 +2769,9 @@ class NativeParameterInstr : public Definition { // TODO(sjindel): We can make this more precise. virtual CompileType ComputeType() const { return CompileType::Dynamic(); } - virtual bool MayThrow() const { return false; } - PRINT_OPERANDS_TO_SUPPORT private: - virtual void RawSetInputAt(intptr_t i, Value* value) { UNREACHABLE(); } - const compiler::ffi::CallbackMarshaller& marshaller_; const intptr_t def_index_; @@ -4013,23 +4014,19 @@ struct ArgumentsInfo { }; template -class TemplateDartCall : public Definition { +class TemplateDartCall : public VariadicDefinition { public: TemplateDartCall(intptr_t deopt_id, intptr_t type_args_len, const Array& argument_names, InputsArray* inputs, const InstructionSource& source) - : Definition(source, deopt_id), + : VariadicDefinition(inputs, source, deopt_id), type_args_len_(type_args_len), argument_names_(argument_names), - inputs_(inputs), token_pos_(source.token_pos) { ASSERT(argument_names.IsZoneHandle() || argument_names.InVMIsolateHeap()); ASSERT(inputs_->length() >= kExtraInputs); - for (intptr_t i = 0, n = inputs_->length(); i < n; ++i) { - SetInputAt(i, (*inputs_)[i]); - } } inline StringPtr Selector(); @@ -4037,8 +4034,6 @@ class TemplateDartCall : public Definition { virtual bool MayThrow() const { return true; } virtual bool CanCallDart() const { return true; } - virtual intptr_t InputCount() const { return inputs_->length(); } - virtual Value* InputAt(intptr_t i) const { return inputs_->At(i); } virtual bool ComputeCanDeoptimize() const { return false; } virtual bool ComputeCanDeoptimizeAfterCall() const { return !CompilerState::Current().is_aot(); @@ -4095,13 +4090,8 @@ class TemplateDartCall : public Definition { } private: - virtual void RawSetInputAt(intptr_t i, Value* value) { - (*inputs_)[i] = value; - } - intptr_t type_args_len_; const Array& argument_names_; - InputsArray* inputs_; PushArgumentsArray* push_arguments_ = nullptr; TokenPosition token_pos_; @@ -5063,17 +5053,17 @@ class LoadLocalInstr : public TemplateDefinition<0, NoThrow> { class DropTempsInstr : public Definition { public: DropTempsInstr(intptr_t num_temps, Value* value) - : num_temps_(num_temps), value_(NULL) { - if (value != NULL) { + : num_temps_(num_temps), has_input_(value != nullptr) { + if (has_input_) { SetInputAt(0, value); } } DECLARE_INSTRUCTION(DropTemps) - virtual intptr_t InputCount() const { return value_ != NULL ? 1 : 0; } + virtual intptr_t InputCount() const { return has_input_ ? 1 : 0; } virtual Value* InputAt(intptr_t i) const { - ASSERT((value_ != NULL) && (i == 0)); + ASSERT(has_input_ && (i == 0)); return value_; } @@ -5097,10 +5087,14 @@ class DropTempsInstr : public Definition { PRINT_OPERANDS_TO_SUPPORT private: - virtual void RawSetInputAt(intptr_t i, Value* value) { value_ = value; } + virtual void RawSetInputAt(intptr_t i, Value* value) { + ASSERT(has_input_); + value_ = value; + } const intptr_t num_temps_; - Value* value_; + const bool has_input_; + Value* value_ = nullptr; DISALLOW_COPY_AND_ASSIGN(DropTempsInstr); }; @@ -5194,8 +5188,8 @@ class StoreLocalInstr : public TemplateDefinition<1, NoThrow> { class NativeCallInstr : public TemplateDartCall<0> { public: - NativeCallInstr(const String* name, - const Function* function, + NativeCallInstr(const String& name, + const Function& function, bool link_lazily, const InstructionSource& source, InputsArray* args) @@ -5207,14 +5201,14 @@ class NativeCallInstr : public TemplateDartCall<0> { is_auto_scope_(true), link_lazily_(link_lazily), token_pos_(source.token_pos) { - ASSERT(name->IsZoneHandle()); - ASSERT(function->IsZoneHandle()); + ASSERT(name.IsZoneHandle()); + ASSERT(function.IsZoneHandle()); } DECLARE_INSTRUCTION(NativeCall) - const String& native_name() const { return *native_name_; } - const Function& function() const { return *function_; } + const String& native_name() const { return native_name_; } + const Function& function() const { return function_; } NativeFunction native_c_function() const { return native_c_function_; } bool is_bootstrap_native() const { return is_bootstrap_native_; } bool is_auto_scope() const { return is_auto_scope_; } @@ -5240,8 +5234,8 @@ class NativeCallInstr : public TemplateDartCall<0> { void set_is_bootstrap_native(bool value) { is_bootstrap_native_ = value; } void set_is_auto_scope(bool value) { is_auto_scope_ = value; } - const String* native_name_; - const Function* function_; + const String& native_name_; + const Function& function_; NativeFunction native_c_function_; bool is_bootstrap_native_; bool is_auto_scope_; @@ -5260,22 +5254,17 @@ class NativeCallInstr : public TemplateDartCall<0> { // - The arguments to the native call, marshalled in IL as far as possible. // - The argument address. // - A TypedData for the return value to populate in machine code (optional). -class FfiCallInstr : public Definition { +class FfiCallInstr : public VariadicDefinitionWithEmbeddedInputs { public: - FfiCallInstr(Zone* zone, - intptr_t deopt_id, + FfiCallInstr(intptr_t deopt_id, const compiler::ffi::CallMarshaller& marshaller, bool is_leaf) - : Definition(deopt_id), - zone_(zone), + : VariadicDefinitionWithEmbeddedInputs( + marshaller.NumDefinitions() + 1 + + (marshaller.PassTypedData() ? 1 : 0), + deopt_id), marshaller_(marshaller), - inputs_(marshaller.NumDefinitions() + 1 + - (marshaller.PassTypedData() ? 1 : 0)), - is_leaf_(is_leaf) { - inputs_.FillWith( - nullptr, 0, - marshaller.NumDefinitions() + 1 + (marshaller.PassTypedData() ? 1 : 0)); - } + is_leaf_(is_leaf) {} DECLARE_INSTRUCTION(FfiCall) @@ -5288,8 +5277,6 @@ class FfiCallInstr : public Definition { return marshaller_.NumDefinitions() + 1; } - virtual intptr_t InputCount() const { return inputs_.length(); } - virtual Value* InputAt(intptr_t i) const { return inputs_[i]; } virtual bool MayThrow() const { // By Dart_PropagateError. return true; @@ -5320,8 +5307,6 @@ class FfiCallInstr : public Definition { PRINT_OPERANDS_TO_SUPPORT private: - virtual void RawSetInputAt(intptr_t i, Value* value) { inputs_[i] = value; } - LocationSummary* MakeLocationSummaryInternal(Zone* zone, bool is_optimizing, const RegList temps) const; @@ -5338,21 +5323,16 @@ class FfiCallInstr : public Definition { const Register temp0, const Register temp1); - Zone* const zone_; const compiler::ffi::CallMarshaller& marshaller_; - - GrowableArray inputs_; - bool is_leaf_; DISALLOW_COPY_AND_ASSIGN(FfiCallInstr); }; // Has the target address in a register passed as the last input in IL. -class CCallInstr : public Definition { +class CCallInstr : public VariadicDefinition { public: CCallInstr( - Zone* zone, const compiler::ffi::NativeCallingConvention& native_calling_convention, InputsArray* inputs); @@ -5366,8 +5346,6 @@ class CCallInstr : public Definition { return native_calling_convention_.argument_locations().length(); } - virtual intptr_t InputCount() const { return inputs_->length(); } - virtual Value* InputAt(intptr_t i) const { return inputs_->At(i); } virtual bool MayThrow() const { return false; } virtual bool ComputeCanDeoptimize() const { return false; } @@ -5386,13 +5364,7 @@ class CCallInstr : public Definition { PRINT_OPERANDS_TO_SUPPORT private: - virtual void RawSetInputAt(intptr_t i, Value* value) { - (*inputs_)[i] = value; - } - - Zone* const zone_; const compiler::ffi::NativeCallingConvention& native_calling_convention_; - InputsArray* inputs_; DISALLOW_COPY_AND_ASSIGN(CCallInstr); }; @@ -6392,11 +6364,12 @@ class AllocateObjectInstr : public AllocationInstr { Value* type_arguments = nullptr) : AllocationInstr(source, deopt_id), cls_(cls), + has_type_arguments_(type_arguments != nullptr), type_arguments_(type_arguments) { ASSERT(cls.IsZoneHandle()); ASSERT(!cls.IsNull()); - ASSERT((cls.NumTypeArguments() > 0) == (type_arguments != nullptr)); - if (type_arguments != nullptr) { + ASSERT((cls.NumTypeArguments() > 0) == has_type_arguments_); + if (has_type_arguments_) { SetInputAt(kTypeArgumentsPos, type_arguments); type_arguments_slot_ = &Slot::GetTypeArgumentsSlotFor(Thread::Current(), cls); @@ -6409,11 +6382,9 @@ class AllocateObjectInstr : public AllocationInstr { const Class& cls() const { return cls_; } Value* type_arguments() const { return type_arguments_; } - virtual intptr_t InputCount() const { - return (type_arguments_ != nullptr) ? 1 : 0; - } + virtual intptr_t InputCount() const { return has_type_arguments_ ? 1 : 0; } virtual Value* InputAt(intptr_t i) const { - ASSERT(type_arguments_ != nullptr && i == kTypeArgumentsPos); + ASSERT(has_type_arguments_ && i == kTypeArgumentsPos); return type_arguments_; } @@ -6435,12 +6406,12 @@ class AllocateObjectInstr : public AllocationInstr { private: virtual void RawSetInputAt(intptr_t i, Value* value) { - ASSERT((type_arguments_ != nullptr) && (i == kTypeArgumentsPos)); - ASSERT(value != nullptr); + ASSERT(has_type_arguments_ && (i == kTypeArgumentsPos)); type_arguments_ = value; } const Class& cls_; + const bool has_type_arguments_; Value* type_arguments_; const Slot* type_arguments_slot_ = nullptr; @@ -6529,26 +6500,22 @@ class AllocateUninitializedContextInstr : public TemplateAllocation<0> { // This instruction captures the state of the object which had its allocation // removed during the AllocationSinking pass. // It does not produce any real code only deoptimization information. -class MaterializeObjectInstr : public Definition { +class MaterializeObjectInstr : public VariadicDefinition { public: MaterializeObjectInstr(AllocationInstr* allocation, const Class& cls, intptr_t num_elements, const ZoneGrowableArray& slots, ZoneGrowableArray* values) - : allocation_(allocation), + : VariadicDefinition(values), + allocation_(allocation), cls_(cls), num_elements_(num_elements), slots_(slots), - values_(values), locations_(nullptr), visited_for_liveness_(false), registers_remapped_(false) { - ASSERT(slots_.length() == values_->length()); - for (intptr_t i = 0; i < InputCount(); i++) { - InputAt(i)->set_instruction(this); - InputAt(i)->set_use_index(i); - } + ASSERT(slots_.length() == values->length()); } AllocationInstr* allocation() const { return allocation_; } @@ -6564,10 +6531,6 @@ class MaterializeObjectInstr : public Definition { DECLARE_INSTRUCTION(MaterializeObject) - virtual intptr_t InputCount() const { return values_->length(); } - - virtual Value* InputAt(intptr_t i) const { return (*values_)[i]; } - // SelectRepresentations pass is run once more while MaterializeObject // instructions are still in the graph. To avoid any redundant boxing // operations inserted by that pass we should indicate that this @@ -6594,15 +6557,10 @@ class MaterializeObjectInstr : public Definition { PRINT_OPERANDS_TO_SUPPORT private: - virtual void RawSetInputAt(intptr_t i, Value* value) { - (*values_)[i] = value; - } - AllocationInstr* allocation_; const Class& cls_; intptr_t num_elements_; const ZoneGrowableArray& slots_; - ZoneGrowableArray* values_; Location* locations_; bool visited_for_liveness_; @@ -8692,7 +8650,7 @@ class FloatToDoubleInstr : public TemplateDefinition<1, NoThrow, Pure> { }; // TODO(sjindel): Replace with FFICallInstr. -class InvokeMathCFunctionInstr : public PureDefinition { +class InvokeMathCFunctionInstr : public VariadicDefinition { public: InvokeMathCFunctionInstr(ZoneGrowableArray* inputs, intptr_t deopt_id, @@ -8726,9 +8684,8 @@ class InvokeMathCFunctionInstr : public PureDefinition { virtual intptr_t DeoptimizationTarget() const { return GetDeoptId(); } - virtual intptr_t InputCount() const { return inputs_->length(); } - - virtual Value* InputAt(intptr_t i) const { return (*inputs_)[i]; } + virtual bool AllowsCSE() const { return true; } + virtual bool HasUnknownSideEffects() const { return false; } virtual bool AttributesEqual(const Instruction& other) const { auto const other_invoke = other.AsInvokeMathCFunction(); @@ -8744,11 +8701,6 @@ class InvokeMathCFunctionInstr : public PureDefinition { PRINT_OPERANDS_TO_SUPPORT private: - virtual void RawSetInputAt(intptr_t i, Value* value) { - (*inputs_)[i] = value; - } - - ZoneGrowableArray* inputs_; const MethodRecognizer::Kind recognized_kind_; const TokenPosition token_pos_; @@ -9853,7 +9805,7 @@ class Environment : public ZoneAllocated { return count; } - const Function& function() const { return parsed_function_.function(); } + const Function& function() const { return function_; } Environment* DeepCopy(Zone* zone) const { return DeepCopy(zone, Length()); } @@ -9893,14 +9845,14 @@ class Environment : public ZoneAllocated { Environment(intptr_t length, intptr_t fixed_parameter_count, intptr_t lazy_deopt_pruning_count, - const ParsedFunction& parsed_function, + const Function& function, Environment* outer) : values_(length), fixed_parameter_count_(fixed_parameter_count), bitfield_(DeoptIdBits::encode(DeoptId::kNone) | LazyDeoptToBeforeDeoptId::encode(false) | LazyDeoptPruningBits::encode(lazy_deopt_pruning_count)), - parsed_function_(parsed_function), + function_(function), outer_(outer) {} void SetDeoptId(intptr_t deopt_id) { @@ -9919,7 +9871,7 @@ class Environment : public ZoneAllocated { // Deoptimization id associated with this environment. Only set for // outer environments. uintptr_t bitfield_; - const ParsedFunction& parsed_function_; + const Function& function_; Environment* outer_; DISALLOW_COPY_AND_ASSIGN(Environment); diff --git a/runtime/vm/compiler/backend/il_test.cc b/runtime/vm/compiler/backend/il_test.cc index d004834acaa..8ae38a11af5 100644 --- a/runtime/vm/compiler/backend/il_test.cc +++ b/runtime/vm/compiler/backend/il_test.cc @@ -961,7 +961,7 @@ FlowGraph* SetupFfiFlowgraph(TestPipeline* pipeline, FlowGraph* flow_graph = pipeline->RunPasses({CompilerPass::kComputeSSA}); // Make an FfiCall based on ffi_trampoline that calls our native function. - auto ffi_call = new FfiCallInstr(zone, DeoptId::kNone, marshaller, is_leaf); + auto ffi_call = new FfiCallInstr(DeoptId::kNone, marshaller, is_leaf); RELEASE_ASSERT(ffi_call->InputCount() == 1); // TargetAddress is the function pointer called. const Representation address_repr = diff --git a/runtime/vm/compiler/frontend/kernel_to_il.cc b/runtime/vm/compiler/frontend/kernel_to_il.cc index 1e3707ed993..66de960259f 100644 --- a/runtime/vm/compiler/frontend/kernel_to_il.cc +++ b/runtime/vm/compiler/frontend/kernel_to_il.cc @@ -394,9 +394,8 @@ Fragment FlowGraphBuilder::FfiCall( const compiler::ffi::CallMarshaller& marshaller) { Fragment body; - FfiCallInstr* const call = - new (Z) FfiCallInstr(Z, GetNextDeoptId(), marshaller, - parsed_function_->function().FfiIsLeaf()); + FfiCallInstr* const call = new (Z) FfiCallInstr( + GetNextDeoptId(), marshaller, parsed_function_->function().FfiIsLeaf()); for (intptr_t i = call->InputCount() - 1; i >= 0; --i) { call->SetInputAt(i, Pop()); @@ -419,8 +418,7 @@ Fragment FlowGraphBuilder::CCall( for (intptr_t i = num_arguments - 1; i >= 0; --i) { (*arguments)[i] = Pop(); } - auto* const call = - new (Z) CCallInstr(Z, native_calling_convention, arguments); + auto* const call = new (Z) CCallInstr(native_calling_convention, arguments); Push(call); body <<= call; @@ -559,15 +557,15 @@ Fragment FlowGraphBuilder::StoreLateField(const Field& field, return instructions; } -Fragment FlowGraphBuilder::NativeCall(const String* name, - const Function* function) { +Fragment FlowGraphBuilder::NativeCall(const String& name, + const Function& function) { InlineBailout("kernel::FlowGraphBuilder::NativeCall"); const intptr_t num_args = - function->NumParameters() + (function->IsGeneric() ? 1 : 0); + function.NumParameters() + (function.IsGeneric() ? 1 : 0); InputsArray* arguments = GetArguments(num_args); NativeCallInstr* call = new (Z) NativeCallInstr(name, function, FLAG_link_natives_lazily, - InstructionSource(function->end_token_pos()), arguments); + InstructionSource(function.end_token_pos()), arguments); Push(call); return Fragment(call); } @@ -838,7 +836,7 @@ Fragment FlowGraphBuilder::NativeFunctionBody(const Function& function, for (intptr_t i = 0; i < function.NumParameters(); ++i) { body += LoadLocal(parsed_function_->RawParameterVariable(i)); } - body += NativeCall(&name, &function); + body += NativeCall(name, function); // We typecheck results of native calls for type safety. body += Return(TokenPosition::kNoSource, /* omit_result_type_check = */ false); diff --git a/runtime/vm/compiler/frontend/kernel_to_il.h b/runtime/vm/compiler/frontend/kernel_to_il.h index b1845038c8d..045750e9ef3 100644 --- a/runtime/vm/compiler/frontend/kernel_to_il.h +++ b/runtime/vm/compiler/frontend/kernel_to_il.h @@ -197,7 +197,7 @@ class FlowGraphBuilder : public BaseFlowGraphBuilder { Fragment StoreLateField(const Field& field, LocalVariable* instance, LocalVariable* setter_value); - Fragment NativeCall(const String* name, const Function* function); + Fragment NativeCall(const String& name, const Function& function); Fragment Return( TokenPosition position, bool omit_result_type_check = false,