diff --git a/BUILD.gn b/BUILD.gn index 9fe40e6be3..53ecc77d27 100644 --- a/BUILD.gn +++ b/BUILD.gn @@ -538,8 +538,6 @@ source_set("v8_base") { "src/codegen.h", "src/compilation-cache.cc", "src/compilation-cache.h", - "src/compilation-dependencies.cc", - "src/compilation-dependencies.h", "src/compilation-statistics.cc", "src/compilation-statistics.h", "src/compiler/access-builder.cc", diff --git a/src/compilation-dependencies.cc b/src/compilation-dependencies.cc deleted file mode 100644 index 9ea6a7a878..0000000000 --- a/src/compilation-dependencies.cc +++ /dev/null @@ -1,121 +0,0 @@ -// Copyright 2015 the V8 project authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#include "src/factory.h" -#include "src/handles-inl.h" -#include "src/isolate.h" -#include "src/objects-inl.h" -#include "src/zone.h" - -#include "src/compilation-dependencies.h" - -namespace v8 { -namespace internal { - -DependentCode* CompilationDependencies::Get(Handle object) { - if (object->IsMap()) { - return Handle::cast(object)->dependent_code(); - } else if (object->IsPropertyCell()) { - return Handle::cast(object)->dependent_code(); - } else if (object->IsAllocationSite()) { - return Handle::cast(object)->dependent_code(); - } - UNREACHABLE(); - return nullptr; -} - - -void CompilationDependencies::Set(Handle object, - Handle dep) { - if (object->IsMap()) { - Handle::cast(object)->set_dependent_code(*dep); - } else if (object->IsPropertyCell()) { - Handle::cast(object)->set_dependent_code(*dep); - } else if (object->IsAllocationSite()) { - Handle::cast(object)->set_dependent_code(*dep); - } else { - UNREACHABLE(); - } -} - - -void CompilationDependencies::Insert(DependentCode::DependencyGroup group, - Handle object) { - if (groups_[group] == nullptr) { - groups_[group] = new (zone_) ZoneList>(2, zone_); - } - groups_[group]->Add(object, zone_); - - if (object_wrapper_.is_null()) { - // Allocate the wrapper if necessary. - object_wrapper_ = - isolate_->factory()->NewForeign(reinterpret_cast
(this)); - } - - // Get the old dependent code list. - Handle old_dependent_code = - Handle(Get(object), isolate_); - Handle new_dependent_code = - DependentCode::InsertCompilationDependencies(old_dependent_code, group, - object_wrapper_); - - // Set the new dependent code list if the head of the list changed. - if (!new_dependent_code.is_identical_to(old_dependent_code)) { - Set(object, new_dependent_code); - } -} - - -void CompilationDependencies::Commit(Handle code) { - if (IsEmpty()) return; - - DCHECK(!object_wrapper_.is_null()); - Handle cell = Code::WeakCellFor(code); - AllowDeferredHandleDereference get_wrapper; - for (int i = 0; i < DependentCode::kGroupCount; i++) { - ZoneList>* group_objects = groups_[i]; - if (group_objects == nullptr) continue; - DependentCode::DependencyGroup group = - static_cast(i); - for (int j = 0; j < group_objects->length(); j++) { - DependentCode* dependent_code = Get(group_objects->at(j)); - dependent_code->UpdateToFinishedCode(group, *object_wrapper_, *cell); - } - groups_[i] = nullptr; // Zone-allocated, no need to delete. - } -} - - -void CompilationDependencies::Rollback() { - if (IsEmpty()) return; - - AllowDeferredHandleDereference get_wrapper; - // Unregister from all dependent maps if not yet committed. - for (int i = 0; i < DependentCode::kGroupCount; i++) { - ZoneList>* group_objects = groups_[i]; - if (group_objects == nullptr) continue; - DependentCode::DependencyGroup group = - static_cast(i); - for (int j = 0; j < group_objects->length(); j++) { - DependentCode* dependent_code = Get(group_objects->at(j)); - dependent_code->RemoveCompilationDependencies(group, *object_wrapper_); - } - groups_[i] = nullptr; // Zone-allocated, no need to delete. - } -} - - -void CompilationDependencies::AssumeTransitionStable( - Handle site) { - // Do nothing if the object doesn't have any useful element transitions left. - ElementsKind kind = - site->SitePointsToLiteral() - ? JSObject::cast(site->transition_info())->GetElementsKind() - : site->GetElementsKind(); - if (AllocationSite::GetMode(kind) == TRACK_ALLOCATION_SITE) { - Insert(DependentCode::kAllocationSiteTransitionChangedGroup, site); - } -} -} -} // namespace v8::internal diff --git a/src/compilation-dependencies.h b/src/compilation-dependencies.h deleted file mode 100644 index ddd0be83bd..0000000000 --- a/src/compilation-dependencies.h +++ /dev/null @@ -1,67 +0,0 @@ -// Copyright 2015 the V8 project authors. All rights reserved. -// Use of this source code is governed by a BSD-style license that can be -// found in the LICENSE file. - -#ifndef V8_DEPENDENCIES_H_ -#define V8_DEPENDENCIES_H_ - -namespace v8 { -namespace internal { - -// Collects dependencies for this compilation, e.g. assumptions about -// stable maps, constant globals, etc. -class CompilationDependencies { - public: - CompilationDependencies(Isolate* isolate, Zone* zone) - : isolate_(isolate), - zone_(zone), - object_wrapper_(Handle::null()), - aborted_(false) { - std::fill_n(groups_, DependentCode::kGroupCount, nullptr); - } - - void Insert(DependentCode::DependencyGroup group, Handle handle); - - void AssumeInitialMapCantChange(Handle map) { - Insert(DependentCode::kInitialMapChangedGroup, map); - } - void AssumeElementsCantBeAdded(Handle map) { - Insert(DependentCode::kElementsCantBeAddedGroup, map); - } - void AssumeFieldType(Handle map) { - Insert(DependentCode::kFieldTypeGroup, map); - } - void AssumePropertyCell(Handle cell) { - Insert(DependentCode::kPropertyCellChangedGroup, cell); - } - void AssumeTenuringDecision(Handle site) { - Insert(DependentCode::kAllocationSiteTenuringChangedGroup, site); - } - void AssumeTransitionStable(Handle site); - - void Commit(Handle code); - void Rollback(); - void Abort() { aborted_ = true; } - bool HasAborted() const { return aborted_; } - - bool IsEmpty() const { - for (int i = 0; i < DependentCode::kGroupCount; i++) { - if (groups_[i]) return false; - } - return true; - } - - private: - Isolate* isolate_; - Zone* zone_; - Handle object_wrapper_; - bool aborted_; - ZoneList >* groups_[DependentCode::kGroupCount]; - - DependentCode* Get(Handle object); - void Set(Handle object, Handle dep); -}; -} -} // namespace v8::internal - -#endif // V8_DEPENDENCIES_H_ diff --git a/src/compiler.cc b/src/compiler.cc index 0d9c2787b7..4553f2e107 100644 --- a/src/compiler.cc +++ b/src/compiler.cc @@ -87,7 +87,7 @@ class CompilationInfoWithZone : public CompilationInfo { // called when cast as a CompilationInfo. virtual ~CompilationInfoWithZone() { DisableFutureOptimization(); - dependencies()->Rollback(); + RollbackDependencies(); delete parse_info_; parse_info_ = nullptr; } @@ -143,7 +143,6 @@ CompilationInfo::CompilationInfo(ParseInfo* parse_info, CodeStub* code_stub, osr_ast_id_(BailoutId::None()), zone_(zone), deferred_handles_(nullptr), - dependencies_(isolate, zone), bailout_reason_(kNoReason), prologue_offset_(Code::kPrologueOffsetNotSet), no_frame_ranges_(isolate->cpu_profiler()->is_profiling() @@ -154,7 +153,10 @@ CompilationInfo::CompilationInfo(ParseInfo* parse_info, CodeStub* code_stub, opt_count_(has_shared_info() ? shared_info()->opt_count() : 0), parameter_count_(0), optimization_id_(-1), - osr_expr_stack_height_(0) {} + aborted_due_to_dependency_change_(false), + osr_expr_stack_height_(0) { + std::fill_n(dependencies_, DependentCode::kGroupCount, nullptr); +} CompilationInfo::~CompilationInfo() { @@ -164,11 +166,60 @@ CompilationInfo::~CompilationInfo() { #ifdef DEBUG // Check that no dependent maps have been added or added dependent maps have // been rolled back or committed. - DCHECK(dependencies()->IsEmpty()); + for (int i = 0; i < DependentCode::kGroupCount; i++) { + DCHECK(!dependencies_[i]); + } #endif // DEBUG } +void CompilationInfo::CommitDependencies(Handle code) { + bool has_dependencies = false; + for (int i = 0; i < DependentCode::kGroupCount; i++) { + has_dependencies |= + dependencies_[i] != NULL && dependencies_[i]->length() > 0; + } + // Avoid creating a weak cell for code with no dependencies. + if (!has_dependencies) return; + + AllowDeferredHandleDereference get_object_wrapper; + WeakCell* cell = *Code::WeakCellFor(code); + for (int i = 0; i < DependentCode::kGroupCount; i++) { + ZoneList >* group_objects = dependencies_[i]; + if (group_objects == NULL) continue; + DCHECK(!object_wrapper_.is_null()); + for (int j = 0; j < group_objects->length(); j++) { + DependentCode::DependencyGroup group = + static_cast(i); + Foreign* info = *object_wrapper(); + DependentCode* dependent_code = + DependentCode::ForObject(group_objects->at(j), group); + dependent_code->UpdateToFinishedCode(group, info, cell); + } + dependencies_[i] = NULL; // Zone-allocated, no need to delete. + } +} + + +void CompilationInfo::RollbackDependencies() { + AllowDeferredHandleDereference get_object_wrapper; + // Unregister from all dependent maps if not yet committed. + for (int i = 0; i < DependentCode::kGroupCount; i++) { + ZoneList >* group_objects = dependencies_[i]; + if (group_objects == NULL) continue; + for (int j = 0; j < group_objects->length(); j++) { + DependentCode::DependencyGroup group = + static_cast(i); + Foreign* info = *object_wrapper(); + DependentCode* dependent_code = + DependentCode::ForObject(group_objects->at(j), group); + dependent_code->RemoveCompilationInfo(group, info); + } + dependencies_[i] = NULL; // Zone-allocated, no need to delete. + } +} + + int CompilationInfo::num_parameters() const { return has_scope() ? scope()->num_parameters() : parameter_count_; } @@ -442,7 +493,7 @@ OptimizedCompileJob::Status OptimizedCompileJob::CreateGraph() { if (graph_ == NULL) return SetLastStatus(BAILED_OUT); - if (info()->dependencies()->HasAborted()) { + if (info()->HasAbortedDueToDependencyChange()) { // Dependency has changed during graph creation. Let's try again later. return RetryOptimization(kBailedOutDueToDependencyChange); } @@ -490,7 +541,7 @@ OptimizedCompileJob::Status OptimizedCompileJob::GenerateCode() { return last_status(); } - DCHECK(!info()->dependencies()->HasAborted()); + DCHECK(!info()->HasAbortedDueToDependencyChange()); DisallowCodeDependencyChange no_dependency_change; DisallowJavascriptExecution no_js(isolate()); { // Scope for timer. @@ -1471,7 +1522,7 @@ Handle Compiler::GetConcurrentlyOptimizedCode(OptimizedCompileJob* job) { if (job->last_status() == OptimizedCompileJob::SUCCEEDED) { if (shared->optimization_disabled()) { job->RetryOptimization(kOptimizationDisabled); - } else if (info->dependencies()->HasAborted()) { + } else if (info->HasAbortedDueToDependencyChange()) { job->RetryOptimization(kBailedOutDueToDependencyChange); } else if (isolate->debug()->has_break_points()) { job->RetryOptimization(kDebuggerHasBreakPoints); diff --git a/src/compiler.h b/src/compiler.h index 0e50075021..f9acb66c08 100644 --- a/src/compiler.h +++ b/src/compiler.h @@ -8,7 +8,6 @@ #include "src/allocation.h" #include "src/ast.h" #include "src/bailout-reason.h" -#include "src/compilation-dependencies.h" #include "src/zone.h" namespace v8 { @@ -300,6 +299,18 @@ class CompilationInfo { deferred_handles_ = deferred_handles; } + ZoneList >* dependencies( + DependentCode::DependencyGroup group) { + if (dependencies_[group] == NULL) { + dependencies_[group] = new(zone_) ZoneList >(2, zone_); + } + return dependencies_[group]; + } + + void CommitDependencies(Handle code); + + void RollbackDependencies(); + void ReopenHandlesInNewHandleScope() { unoptimized_code_ = Handle(*unoptimized_code_); } @@ -352,7 +363,21 @@ class CompilationInfo { int TraceInlinedFunction(Handle shared, SourcePosition position, int pareint_id); - CompilationDependencies* dependencies() { return &dependencies_; } + Handle object_wrapper() { + if (object_wrapper_.is_null()) { + object_wrapper_ = + isolate()->factory()->NewForeign(reinterpret_cast
(this)); + } + return object_wrapper_; + } + + void AbortDueToDependencyChange() { + aborted_due_to_dependency_change_ = true; + } + + bool HasAbortedDueToDependencyChange() const { + return aborted_due_to_dependency_change_; + } bool HasSameOsrEntry(Handle function, BailoutId osr_ast_id) { return osr_ast_id_ == osr_ast_id && function.is_identical_to(closure()); @@ -435,8 +460,7 @@ class CompilationInfo { DeferredHandles* deferred_handles_; - // Dependencies for this compilation, e.g. stable maps. - CompilationDependencies dependencies_; + ZoneList >* dependencies_[DependentCode::kGroupCount]; BailoutReason bailout_reason_; @@ -453,8 +477,14 @@ class CompilationInfo { // Number of parameters used for compilation of stubs that require arguments. int parameter_count_; + Handle object_wrapper_; + int optimization_id_; + // This flag is used by the main thread to track whether this compilation + // should be abandoned due to dependency change. + bool aborted_due_to_dependency_change_; + int osr_expr_stack_height_; DISALLOW_COPY_AND_ASSIGN(CompilationInfo); diff --git a/src/hydrogen.cc b/src/hydrogen.cc index e966d598a0..46f0bfe043 100644 --- a/src/hydrogen.cc +++ b/src/hydrogen.cc @@ -5396,7 +5396,7 @@ void HOptimizedGraphBuilder::VisitVariableProxy(VariableProxy* expr) { if (type == kUseCell) { Handle cell = it.GetPropertyCell(); - top_info()->dependencies()->AssumePropertyCell(cell); + PropertyCell::AddDependentCompilationInfo(cell, top_info()); if (it.property_details().cell_type() == PropertyCellType::kConstant) { Handle constant_object(cell->value(), isolate()); if (constant_object->IsConsString()) { @@ -5777,7 +5777,7 @@ void HOptimizedGraphBuilder::VisitArrayLiteral(ArrayLiteral* expr) { 4); // Register to deopt if the boilerplate ElementsKind changes. - top_info()->dependencies()->AssumeTransitionStable(site); + AllocationSite::RegisterForDeoptOnTransitionChange(site, top_info()); } // The array is expected in the bailout environment during computation @@ -6092,7 +6092,8 @@ bool HOptimizedGraphBuilder::PropertyAccessInfo::LoadFieldMaps( DCHECK(field_type_.IsHeapObject()); // Add dependency on the map that introduced the field. - top_info()->dependencies()->AssumeFieldType(GetFieldOwnerFromMap(map)); + Map::AddDependentCompilationInfo(GetFieldOwnerFromMap(map), + DependentCode::kFieldTypeGroup, top_info()); return true; } @@ -6561,7 +6562,7 @@ void HOptimizedGraphBuilder::HandleGlobalVariableAssignment( GlobalPropertyAccess type = LookupGlobalProperty(var, &it, STORE); if (type == kUseCell) { Handle cell = it.GetPropertyCell(); - top_info()->dependencies()->AssumePropertyCell(cell); + PropertyCell::AddDependentCompilationInfo(cell, top_info()); if (it.property_details().cell_type() == PropertyCellType::kConstant) { Handle constant(cell->value(), isolate()); if (value->IsConstant()) { @@ -9355,7 +9356,7 @@ void HOptimizedGraphBuilder::BuildInlinedCallArray( HValue* constructor = environment()->ExpressionStackAt(argument_count); // Register on the site for deoptimization if the transition feedback changes. - top_info()->dependencies()->AssumeTransitionStable(site); + AllocationSite::RegisterForDeoptOnTransitionChange(site, top_info()); ElementsKind kind = site->GetElementsKind(); HInstruction* site_instruction = Add(site); @@ -9491,7 +9492,8 @@ void HOptimizedGraphBuilder::VisitCallNew(CallNew* expr) { Handle allocation_site = expr->allocation_site(); allocation_mode = HAllocationMode(allocation_site); // Take a dependency on allocation site. - top_info()->dependencies()->AssumeTenuringDecision(allocation_site); + AllocationSite::RegisterForDeoptOnTenureChange(allocation_site, + top_info()); } } @@ -9535,7 +9537,8 @@ void HOptimizedGraphBuilder::VisitCallNew(CallNew* expr) { // Inlining worked, add a dependency on the initial map to make sure that // this code is deoptimized whenever the initial map of the constructor // changes. - top_info()->dependencies()->AssumeInitialMapCantChange(initial_map); + Map::AddDependentCompilationInfo( + initial_map, DependentCode::kInitialMapChangedGroup, top_info()); return; } @@ -10509,7 +10512,7 @@ HValue* HGraphBuilder::BuildBinaryOperation( if (!allocation_mode.feedback_site().is_null()) { DCHECK(!graph()->info()->IsStub()); Handle site(allocation_mode.feedback_site()); - top_info()->dependencies()->AssumeTenuringDecision(site); + AllocationSite::RegisterForDeoptOnTenureChange(site, top_info()); } // Inline the string addition into the stub when creating allocation @@ -11080,10 +11083,10 @@ HInstruction* HOptimizedGraphBuilder::BuildFastLiteral( Handle site(site_context->current()); if (FLAG_allocation_site_pretenuring) { pretenure_flag = site_context->current()->GetPretenureMode(); - top_info()->dependencies()->AssumeTenuringDecision(site); + AllocationSite::RegisterForDeoptOnTenureChange(site, top_info()); } - top_info()->dependencies()->AssumeTransitionStable(site); + AllocationSite::RegisterForDeoptOnTransitionChange(site, top_info()); HInstruction* object = Add(object_size_constant, type, pretenure_flag, instance_type, site_context->current()); diff --git a/src/hydrogen.h b/src/hydrogen.h index 77b741c723..16d8aecd50 100644 --- a/src/hydrogen.h +++ b/src/hydrogen.h @@ -416,10 +416,12 @@ class HGraph FINAL : public ZoneObject { void MarkDependsOnEmptyArrayProtoElements() { // Add map dependency if not already added. if (depends_on_empty_array_proto_elements_) return; - info()->dependencies()->AssumeElementsCantBeAdded( - handle(isolate()->initial_object_prototype()->map())); - info()->dependencies()->AssumeElementsCantBeAdded( - handle(isolate()->initial_array_prototype()->map())); + Map::AddDependentCompilationInfo( + handle(isolate()->initial_object_prototype()->map()), + DependentCode::kElementsCantBeAddedGroup, info()); + Map::AddDependentCompilationInfo( + handle(isolate()->initial_array_prototype()->map()), + DependentCode::kElementsCantBeAddedGroup, info()); depends_on_empty_array_proto_elements_ = true; } diff --git a/src/lithium.cc b/src/lithium.cc index 53ed919f2f..a2563d88d6 100644 --- a/src/lithium.cc +++ b/src/lithium.cc @@ -484,7 +484,7 @@ void LChunk::CommitDependencies(Handle code) const { Map::AddDependentCode(map, DependentCode::kPrototypeCheckGroup, code); } - info_->dependencies()->Commit(code); + info_->CommitDependencies(code); RegisterWeakObjectsInOptimizedCode(code); } diff --git a/src/objects.cc b/src/objects.cc index 9ae8cbb7aa..037d33c503 100644 --- a/src/objects.cc +++ b/src/objects.cc @@ -15,7 +15,6 @@ #include "src/bootstrapper.h" #include "src/code-stubs.h" #include "src/codegen.h" -#include "src/compilation-dependencies.h" #include "src/compiler.h" #include "src/cpu-profiler.h" #include "src/date.h" @@ -12138,6 +12137,18 @@ MaybeHandle JSArray::SetElementsLength( } +// static +void Map::AddDependentCompilationInfo(Handle map, + DependentCode::DependencyGroup group, + CompilationInfo* info) { + Handle codes = DependentCode::InsertCompilationInfo( + handle(map->dependent_code(), info->isolate()), group, + info->object_wrapper()); + if (*codes != map->dependent_code()) map->set_dependent_code(*codes); + info->dependencies(group)->Add(map, info->zone()); +} + + // static void Map::AddDependentCode(Handle map, DependentCode::DependencyGroup group, @@ -12163,7 +12174,20 @@ void DependentCode::GroupStartIndexes::Recompute(DependentCode* entries) { } -Handle DependentCode::InsertCompilationDependencies( +DependentCode* DependentCode::ForObject(Handle object, + DependencyGroup group) { + AllowDeferredHandleDereference dependencies_are_safe; + if (group == DependentCode::kPropertyCellChangedGroup) { + return Handle::cast(object)->dependent_code(); + } else if (group == DependentCode::kAllocationSiteTenuringChangedGroup || + group == DependentCode::kAllocationSiteTransitionChangedGroup) { + return Handle::cast(object)->dependent_code(); + } + return Handle::cast(object)->dependent_code(); +} + + +Handle DependentCode::InsertCompilationInfo( Handle entries, DependencyGroup group, Handle info) { return Insert(entries, group, info); @@ -12269,8 +12293,8 @@ void DependentCode::UpdateToFinishedCode(DependencyGroup group, Foreign* info, } -void DependentCode::RemoveCompilationDependencies( - DependentCode::DependencyGroup group, Foreign* info) { +void DependentCode::RemoveCompilationInfo(DependentCode::DependencyGroup group, + Foreign* info) { DisallowHeapAllocation no_allocation; GroupStartIndexes starts(this); int start = starts.at(group); @@ -12344,10 +12368,9 @@ bool DependentCode::MarkCodeForDeoptimization( } } else { DCHECK(obj->IsForeign()); - CompilationDependencies* info = - reinterpret_cast( - Foreign::cast(obj)->foreign_address()); - info->Abort(); + CompilationInfo* info = reinterpret_cast( + Foreign::cast(obj)->foreign_address()); + info->AbortDueToDependencyChange(); } } // Compact the array by moving all subsequent groups to fill in the new holes. @@ -13429,6 +13452,41 @@ void AllocationSite::DigestTransitionFeedback(Handle site, } +// static +void AllocationSite::RegisterForDeoptOnTenureChange(Handle site, + CompilationInfo* info) { + AddDependentCompilationInfo( + site, DependentCode::kAllocationSiteTenuringChangedGroup, info); +} + + +// static +void AllocationSite::RegisterForDeoptOnTransitionChange( + Handle site, CompilationInfo* info) { + // Do nothing if the object doesn't have any useful element transitions left. + ElementsKind kind = + site->SitePointsToLiteral() + ? JSObject::cast(site->transition_info())->GetElementsKind() + : site->GetElementsKind(); + if (AllocationSite::GetMode(kind) == TRACK_ALLOCATION_SITE) { + AddDependentCompilationInfo( + site, DependentCode::kAllocationSiteTransitionChangedGroup, info); + } +} + + +// static +void AllocationSite::AddDependentCompilationInfo( + Handle site, DependentCode::DependencyGroup group, + CompilationInfo* info) { + Handle dep(site->dependent_code()); + Handle codes = + DependentCode::InsertCompilationInfo(dep, group, info->object_wrapper()); + if (*codes != site->dependent_code()) site->set_dependent_code(*codes); + info->dependencies(group)->Add(Handle(*site), info->zone()); +} + + const char* AllocationSite::PretenureDecisionName(PretenureDecision decision) { switch (decision) { case kUndecided: return "undecided"; @@ -17082,4 +17140,16 @@ Handle PropertyCell::UpdateCell(Handle dictionary, return value; } + +// static +void PropertyCell::AddDependentCompilationInfo(Handle cell, + CompilationInfo* info) { + Handle codes = DependentCode::InsertCompilationInfo( + handle(cell->dependent_code(), info->isolate()), + DependentCode::kPropertyCellChangedGroup, info->object_wrapper()); + if (*codes != cell->dependent_code()) cell->set_dependent_code(*codes); + info->dependencies(DependentCode::kPropertyCellChangedGroup)->Add( + cell, info->zone()); +} + } } // namespace v8::internal diff --git a/src/objects.h b/src/objects.h index f16dc98a13..722a5424c0 100644 --- a/src/objects.h +++ b/src/objects.h @@ -5696,6 +5696,8 @@ class Code: public HeapObject { }; +class CompilationInfo; + // This class describes the layout of dependent codes array of a map. The // array is partitioned into several groups of dependent codes. Each group // contains codes with the same dependency on the map. The array has the @@ -5765,7 +5767,7 @@ class DependentCode: public FixedArray { bool Contains(DependencyGroup group, WeakCell* code_cell); - static Handle InsertCompilationDependencies( + static Handle InsertCompilationInfo( Handle entries, DependencyGroup group, Handle info); @@ -5776,8 +5778,8 @@ class DependentCode: public FixedArray { void UpdateToFinishedCode(DependencyGroup group, Foreign* info, WeakCell* code_cell); - void RemoveCompilationDependencies(DependentCode::DependencyGroup group, - Foreign* info); + void RemoveCompilationInfo(DependentCode::DependencyGroup group, + Foreign* info); void DeoptimizeDependentCodeGroup(Isolate* isolate, DependentCode::DependencyGroup group); @@ -5795,6 +5797,9 @@ class DependentCode: public FixedArray { inline void copy(int from, int to); DECLARE_CAST(DependentCode) + static DependentCode* ForObject(Handle object, + DependencyGroup group); + static const char* DependencyGroupName(DependencyGroup group); static void SetMarkedForDeoptimization(Code* code, DependencyGroup group); @@ -6352,6 +6357,10 @@ class Map: public HeapObject { inline bool CanOmitMapChecks(); + static void AddDependentCompilationInfo(Handle map, + DependentCode::DependencyGroup group, + CompilationInfo* info); + static void AddDependentCode(Handle map, DependentCode::DependencyGroup group, Handle code); @@ -8554,6 +8563,12 @@ class AllocationSite: public Struct { static void DigestTransitionFeedback(Handle site, ElementsKind to_kind); + static void RegisterForDeoptOnTenureChange(Handle site, + CompilationInfo* info); + + static void RegisterForDeoptOnTransitionChange(Handle site, + CompilationInfo* info); + DECLARE_PRINTER(AllocationSite) DECLARE_VERIFIER(AllocationSite) @@ -8584,6 +8599,10 @@ class AllocationSite: public Struct { kSize> BodyDescriptor; private: + static void AddDependentCompilationInfo(Handle site, + DependentCode::DependencyGroup group, + CompilationInfo* info); + bool PretenuringDecisionMade() { return pretenure_decision() != kUndecided; } @@ -9816,6 +9835,9 @@ class PropertyCell : public HeapObject { static Handle InvalidateEntry(Handle dictionary, int entry); + static void AddDependentCompilationInfo(Handle cell, + CompilationInfo* info); + DECLARE_CAST(PropertyCell) // Dispatched behavior. diff --git a/test/cctest/test-migrations.cc b/test/cctest/test-migrations.cc index 544278575c..3be173453a 100644 --- a/test/cctest/test-migrations.cc +++ b/test/cctest/test-migrations.cc @@ -591,9 +591,10 @@ static void TestGeneralizeRepresentation( // Create new maps by generalizing representation of propX field. Handle field_owner(map->FindFieldOwner(property_index), isolate); CompilationInfo info(&stub, isolate, &zone); - CHECK(!info.dependencies()->HasAborted()); + CHECK(!info.HasAbortedDueToDependencyChange()); - info.dependencies()->AssumeFieldType(field_owner); + Map::AddDependentCompilationInfo(field_owner, DependentCode::kFieldTypeGroup, + &info); Handle new_map = Map::ReconfigureProperty(map, property_index, kData, NONE, @@ -609,22 +610,23 @@ static void TestGeneralizeRepresentation( CHECK(map->is_deprecated()); CHECK_NE(*map, *new_map); CHECK_EQ(expected_field_type_dependency && !field_owner->is_deprecated(), - info.dependencies()->HasAborted()); + info.HasAbortedDueToDependencyChange()); } else if (expected_deprecation) { CHECK(map->is_deprecated()); CHECK(field_owner->is_deprecated()); CHECK_NE(*map, *new_map); - CHECK(!info.dependencies()->HasAborted()); + CHECK(!info.HasAbortedDueToDependencyChange()); } else { CHECK(!field_owner->is_deprecated()); CHECK_EQ(*map, *new_map); - CHECK_EQ(expected_field_type_dependency, info.dependencies()->HasAborted()); + CHECK_EQ(expected_field_type_dependency, + info.HasAbortedDueToDependencyChange()); } - info.dependencies()->Rollback(); // Properly cleanup compilation info. + info.RollbackDependencies(); // Properly cleanup compilation info. // Update all deprecated maps and check that they are now the same. Handle updated_map = Map::Update(map); @@ -959,8 +961,9 @@ static void TestReconfigureDataFieldAttribute_GeneralizeRepresentation( FakeStubForTesting stub(isolate); Handle field_owner(map->FindFieldOwner(kSplitProp), isolate); CompilationInfo info(&stub, isolate, &zone); - CHECK(!info.dependencies()->HasAborted()); - info.dependencies()->AssumeFieldType(field_owner); + CHECK(!info.HasAbortedDueToDependencyChange()); + Map::AddDependentCompilationInfo(field_owner, DependentCode::kFieldTypeGroup, + &info); // Reconfigure attributes of property |kSplitProp| of |map2| to NONE, which // should generalize representations in |map1|. @@ -977,8 +980,8 @@ static void TestReconfigureDataFieldAttribute_GeneralizeRepresentation( expectations.SetDataField(i, expected_representation, expected_type); } CHECK(map->is_deprecated()); - CHECK(!info.dependencies()->HasAborted()); - info.dependencies()->Rollback(); // Properly cleanup compilation info. + CHECK(!info.HasAbortedDueToDependencyChange()); + info.RollbackDependencies(); // Properly cleanup compilation info. CHECK_NE(*map, *new_map); CHECK(!new_map->is_deprecated()); @@ -1044,8 +1047,9 @@ static void TestReconfigureDataFieldAttribute_GeneralizeRepresentationTrivial( FakeStubForTesting stub(isolate); Handle field_owner(map->FindFieldOwner(kSplitProp), isolate); CompilationInfo info(&stub, isolate, &zone); - CHECK(!info.dependencies()->HasAborted()); - info.dependencies()->AssumeFieldType(field_owner); + CHECK(!info.HasAbortedDueToDependencyChange()); + Map::AddDependentCompilationInfo(field_owner, DependentCode::kFieldTypeGroup, + &info); // Reconfigure attributes of property |kSplitProp| of |map2| to NONE, which // should generalize representations in |map1|. @@ -1066,8 +1070,9 @@ static void TestReconfigureDataFieldAttribute_GeneralizeRepresentationTrivial( } CHECK(!map->is_deprecated()); CHECK_EQ(*map, *new_map); - CHECK_EQ(expected_field_type_dependency, info.dependencies()->HasAborted()); - info.dependencies()->Rollback(); // Properly cleanup compilation info. + CHECK_EQ(expected_field_type_dependency, + info.HasAbortedDueToDependencyChange()); + info.RollbackDependencies(); // Properly cleanup compilation info. CHECK(!new_map->is_deprecated()); CHECK(expectations.Check(*new_map)); diff --git a/tools/gyp/v8.gyp b/tools/gyp/v8.gyp index 3cf134c481..eb7f9c7f5f 100644 --- a/tools/gyp/v8.gyp +++ b/tools/gyp/v8.gyp @@ -422,8 +422,6 @@ '../../src/codegen.h', '../../src/compilation-cache.cc', '../../src/compilation-cache.h', - '../../src/compilation-dependencies.cc', - '../../src/compilation-dependencies.h', '../../src/compilation-statistics.cc', '../../src/compilation-statistics.h', '../../src/compiler/access-builder.cc',