Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(28)

Unified Diff: src/objects.cc

Issue 295933012: Revert "Inobject slack tracking is done on a per-closure basis instead of per-shared info basis." (Closed) Base URL: https://v8.googlecode.com/svn/branches/bleeding_edge
Patch Set: Created 6 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/objects.h ('k') | src/objects-inl.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/objects.cc
diff --git a/src/objects.cc b/src/objects.cc
index 03d10cdb1273ca40dfc2fae432870170f3cea4f5..ddeaacd6b44011e6bd1cfd8ee12e377fa154adc7 100644
--- a/src/objects.cc
+++ b/src/objects.cc
@@ -10225,8 +10225,8 @@ void JSFunction::SetInstancePrototype(Handle<JSFunction> function,
// copy containing the new prototype. Also complete any in-object
// slack tracking that is in progress at this point because it is
// still tracking the old copy.
- if (function->IsInobjectSlackTrackingInProgress()) {
- function->CompleteInobjectSlackTracking();
+ if (function->shared()->IsInobjectSlackTrackingInProgress()) {
+ function->shared()->CompleteInobjectSlackTracking();
}
Handle<Map> new_map = Map::Copy(handle(function->initial_map()));
new_map->set_prototype(*value);
@@ -10335,13 +10335,13 @@ void JSFunction::EnsureHasInitialMap(Handle<JSFunction> function) {
map->set_prototype(*prototype);
ASSERT(map->has_fast_object_elements());
+ if (!function->shared()->is_generator()) {
+ function->shared()->StartInobjectSlackTracking(*map);
+ }
+
// Finally link initial map and constructor function.
function->set_initial_map(*map);
map->set_constructor(*function);
-
- if (!function->shared()->is_generator()) {
- function->StartInobjectSlackTracking();
- }
}
@@ -10726,15 +10726,14 @@ bool SharedFunctionInfo::VerifyBailoutId(BailoutId id) {
}
-void JSFunction::StartInobjectSlackTracking() {
- ASSERT(has_initial_map() && !IsInobjectSlackTrackingInProgress());
+void SharedFunctionInfo::StartInobjectSlackTracking(Map* map) {
+ ASSERT(!IsInobjectSlackTrackingInProgress());
if (!FLAG_clever_optimizations) return;
- Map* map = initial_map();
// Only initiate the tracking the first time.
- if (map->done_inobject_slack_tracking()) return;
- map->set_done_inobject_slack_tracking(true);
+ if (live_objects_may_exist()) return;
+ set_live_objects_may_exist(true);
// No tracking during the snapshot construction phase.
Isolate* isolate = GetIsolate();
@@ -10742,7 +10741,56 @@ void JSFunction::StartInobjectSlackTracking() {
if (map->unused_property_fields() == 0) return;
- map->set_construction_count(kGenerousAllocationCount);
+ // Nonzero counter is a leftover from the previous attempt interrupted
+ // by GC, keep it.
+ if (construction_count() == 0) {
+ set_construction_count(kGenerousAllocationCount);
+ }
+ set_initial_map(map);
+ Builtins* builtins = isolate->builtins();
+ ASSERT_EQ(builtins->builtin(Builtins::kJSConstructStubGeneric),
+ construct_stub());
+ set_construct_stub(builtins->builtin(Builtins::kJSConstructStubCountdown));
+}
+
+
+// Called from GC, hence reinterpret_cast and unchecked accessors.
+void SharedFunctionInfo::DetachInitialMap() {
+ Map* map = reinterpret_cast<Map*>(initial_map());
+
+ // Make the map remember to restore the link if it survives the GC.
+ map->set_bit_field2(
+ map->bit_field2() | (1 << Map::kAttachedToSharedFunctionInfo));
+
+ // Undo state changes made by StartInobjectTracking (except the
+ // construction_count). This way if the initial map does not survive the GC
+ // then StartInobjectTracking will be called again the next time the
+ // constructor is called. The countdown will continue and (possibly after
+ // several more GCs) CompleteInobjectSlackTracking will eventually be called.
+ Heap* heap = map->GetHeap();
+ set_initial_map(heap->undefined_value());
+ Builtins* builtins = heap->isolate()->builtins();
+ ASSERT_EQ(builtins->builtin(Builtins::kJSConstructStubCountdown),
+ *RawField(this, kConstructStubOffset));
+ set_construct_stub(builtins->builtin(Builtins::kJSConstructStubGeneric));
+ // It is safe to clear the flag: it will be set again if the map is live.
+ set_live_objects_may_exist(false);
+}
+
+
+// Called from GC, hence reinterpret_cast and unchecked accessors.
+void SharedFunctionInfo::AttachInitialMap(Map* map) {
+ map->set_bit_field2(
+ map->bit_field2() & ~(1 << Map::kAttachedToSharedFunctionInfo));
+
+ // Resume inobject slack tracking.
+ set_initial_map(map);
+ Builtins* builtins = map->GetHeap()->isolate()->builtins();
+ ASSERT_EQ(builtins->builtin(Builtins::kJSConstructStubGeneric),
+ *RawField(this, kConstructStubOffset));
+ set_construct_stub(builtins->builtin(Builtins::kJSConstructStubCountdown));
+ // The map survived the gc, so there may be objects referencing it.
+ set_live_objects_may_exist(true);
}
@@ -10785,18 +10833,26 @@ static void ShrinkInstanceSize(Map* map, void* data) {
}
-void JSFunction::CompleteInobjectSlackTracking() {
- ASSERT(has_initial_map());
- Map* map = initial_map();
+void SharedFunctionInfo::CompleteInobjectSlackTracking() {
+ ASSERT(live_objects_may_exist() && IsInobjectSlackTrackingInProgress());
+ Map* map = Map::cast(initial_map());
- ASSERT(map->done_inobject_slack_tracking());
- map->set_construction_count(kNoSlackTracking);
+ Heap* heap = map->GetHeap();
+ set_initial_map(heap->undefined_value());
+ Builtins* builtins = heap->isolate()->builtins();
+ ASSERT_EQ(builtins->builtin(Builtins::kJSConstructStubCountdown),
+ construct_stub());
+ set_construct_stub(builtins->builtin(Builtins::kJSConstructStubGeneric));
int slack = map->unused_property_fields();
map->TraverseTransitionTree(&GetMinInobjectSlack, &slack);
if (slack != 0) {
// Resize the initial map and all maps in its transition tree.
map->TraverseTransitionTree(&ShrinkInstanceSize, &slack);
+
+ // Give the correct expected_nof_properties to initial maps created later.
+ ASSERT(expected_nof_properties() >= slack);
+ set_expected_nof_properties(expected_nof_properties() - slack);
}
}
« no previous file with comments | « src/objects.h ('k') | src/objects-inl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698