LCOV - code coverage report
Current view: top level - src - compilation-dependencies.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 63 65 96.9 %
Date: 2017-10-20 Functions: 9 9 100.0 %

          Line data    Source code
       1             : // Copyright 2015 the V8 project authors. All rights reserved.
       2             : // Use of this source code is governed by a BSD-style license that can be
       3             : // found in the LICENSE file.
       4             : 
       5             : #include "src/compilation-dependencies.h"
       6             : 
       7             : #include "src/factory.h"
       8             : #include "src/handles-inl.h"
       9             : #include "src/isolate.h"
      10             : #include "src/objects-inl.h"
      11             : #include "src/zone/zone.h"
      12             : 
      13             : namespace v8 {
      14             : namespace internal {
      15             : 
      16     1479378 : DependentCode* CompilationDependencies::Get(Handle<Object> object) const {
      17     1479378 :   if (object->IsMap()) {
      18             :     return Handle<Map>::cast(object)->dependent_code();
      19     1039610 :   } else if (object->IsPropertyCell()) {
      20             :     return Handle<PropertyCell>::cast(object)->dependent_code();
      21       16954 :   } else if (object->IsAllocationSite()) {
      22             :     return Handle<AllocationSite>::cast(object)->dependent_code();
      23             :   }
      24           0 :   UNREACHABLE();
      25             : }
      26             : 
      27             : 
      28      242586 : void CompilationDependencies::Set(Handle<Object> object,
      29             :                                   Handle<DependentCode> dep) {
      30      242586 :   if (object->IsMap()) {
      31       81271 :     Handle<Map>::cast(object)->set_dependent_code(*dep);
      32      161315 :   } else if (object->IsPropertyCell()) {
      33      153157 :     Handle<PropertyCell>::cast(object)->set_dependent_code(*dep);
      34        8158 :   } else if (object->IsAllocationSite()) {
      35        8158 :     Handle<AllocationSite>::cast(object)->set_dependent_code(*dep);
      36             :   } else {
      37           0 :     UNREACHABLE();
      38             :   }
      39      242586 : }
      40             : 
      41             : 
      42      739697 : void CompilationDependencies::Insert(DependentCode::DependencyGroup group,
      43             :                                      Handle<HeapObject> object) {
      44      739697 :   if (groups_[group] == nullptr) {
      45      258947 :     groups_[group] = new (zone_->New(sizeof(ZoneVector<Handle<HeapObject>>)))
      46      517894 :         ZoneVector<Handle<HeapObject>>(zone_);
      47             :   }
      48      739697 :   groups_[group]->push_back(object);
      49             : 
      50      739697 :   if (object_wrapper_.is_null()) {
      51             :     // Allocate the wrapper if necessary.
      52             :     object_wrapper_ =
      53      182293 :         isolate_->factory()->NewForeign(reinterpret_cast<Address>(this));
      54             :   }
      55             : 
      56             :   // Get the old dependent code list.
      57             :   Handle<DependentCode> old_dependent_code =
      58     2219091 :       Handle<DependentCode>(Get(object), isolate_);
      59             :   Handle<DependentCode> new_dependent_code =
      60             :       DependentCode::InsertCompilationDependencies(old_dependent_code, group,
      61      739697 :                                                    object_wrapper_);
      62             : 
      63             :   // Set the new dependent code list if the head of the list changed.
      64      739697 :   if (!new_dependent_code.is_identical_to(old_dependent_code)) {
      65      242586 :     Set(object, new_dependent_code);
      66             :   }
      67      739697 : }
      68             : 
      69             : 
      70      439767 : void CompilationDependencies::Commit(Handle<Code> code) {
      71      698703 :   if (IsEmpty()) return;
      72             : 
      73             :   DCHECK(!object_wrapper_.is_null());
      74      180831 :   Handle<WeakCell> cell = Code::WeakCellFor(code);
      75             :   AllowDeferredHandleDereference get_wrapper;
      76     1627479 :   for (int i = 0; i < DependentCode::kGroupCount; i++) {
      77     1446648 :     ZoneVector<Handle<HeapObject>>* group_objects = groups_[i];
      78     1446648 :     if (group_objects == nullptr) continue;
      79             :     DependentCode::DependencyGroup group =
      80      256999 :         static_cast<DependentCode::DependencyGroup>(i);
      81     1976110 :     for (size_t j = 0; j < group_objects->size(); j++) {
      82     1719111 :       DependentCode* dependent_code = Get(group_objects->at(j));
      83      731056 :       dependent_code->UpdateToFinishedCode(group, *object_wrapper_, *cell);
      84             :     }
      85      256999 :     groups_[i] = nullptr;  // Zone-allocated, no need to delete.
      86             :   }
      87             : }
      88             : 
      89             : 
      90     3797342 : void CompilationDependencies::Rollback() {
      91     7594684 :   if (IsEmpty()) return;
      92             : 
      93             :   AllowDeferredHandleDereference get_wrapper;
      94             :   // Unregister from all dependent maps if not yet committed.
      95       11664 :   for (int i = 0; i < DependentCode::kGroupCount; i++) {
      96       11664 :     ZoneVector<Handle<HeapObject>>* group_objects = groups_[i];
      97       11664 :     if (group_objects == nullptr) continue;
      98             :     DependentCode::DependencyGroup group =
      99        1941 :         static_cast<DependentCode::DependencyGroup>(i);
     100       21132 :     for (size_t j = 0; j < group_objects->size(); j++) {
     101       19191 :       DependentCode* dependent_code = Get(group_objects->at(j));
     102        8625 :       dependent_code->RemoveCompilationDependencies(group, *object_wrapper_);
     103             :     }
     104        1941 :     groups_[i] = nullptr;  // Zone-allocated, no need to delete.
     105             :   }
     106             : }
     107             : 
     108             : 
     109       20434 : void CompilationDependencies::AssumeMapNotDeprecated(Handle<Map> map) {
     110             :   DCHECK(!map->is_deprecated());
     111             :   // Do nothing if the map cannot be deprecated.
     112       20434 :   if (map->CanBeDeprecated()) {
     113       11425 :     Insert(DependentCode::kTransitionGroup, map);
     114             :   }
     115       20434 : }
     116             : 
     117             : 
     118      157465 : void CompilationDependencies::AssumeMapStable(Handle<Map> map) {
     119             :   DCHECK(map->is_stable());
     120             :   // Do nothing if the map cannot transition.
     121      157465 :   if (map->CanTransition()) {
     122      155642 :     Insert(DependentCode::kPrototypeCheckGroup, map);
     123             :   }
     124      157465 : }
     125             : 
     126             : 
     127       42809 : void CompilationDependencies::AssumePrototypeMapsStable(
     128             :     Handle<Map> map, MaybeHandle<JSReceiver> prototype) {
     129       78672 :   for (PrototypeIterator i(map); !i.IsAtEnd(); i.Advance()) {
     130             :     Handle<JSReceiver> const current =
     131             :         PrototypeIterator::GetCurrent<JSReceiver>(i);
     132       77026 :     AssumeMapStable(handle(current->map()));
     133             :     Handle<JSReceiver> last;
     134      150760 :     if (prototype.ToHandle(&last) && last.is_identical_to(current)) {
     135             :       break;
     136             :     }
     137             :   }
     138       42809 : }
     139             : 
     140             : 
     141        6515 : void CompilationDependencies::AssumeTransitionStable(
     142             :     Handle<AllocationSite> site) {
     143             :   // Do nothing if the object doesn't have any useful element transitions left.
     144             :   ElementsKind kind = site->PointsToLiteral()
     145             :                           ? site->boilerplate()->GetElementsKind()
     146        6515 :                           : site->GetElementsKind();
     147        6515 :   if (AllocationSite::ShouldTrack(kind)) {
     148        2627 :     Insert(DependentCode::kAllocationSiteTransitionChangedGroup, site);
     149             :   }
     150        6515 : }
     151             : 
     152             : }  // namespace internal
     153             : }  // namespace v8

Generated by: LCOV version 1.10