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

Unified Diff: src/objects.cc

Issue 1508703002: Use WeakCells in the optimized code map rather than traversing in pause. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Fixed nit. Created 5 years 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/heap/objects-visiting-inl.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 63c22b5f7304beb8b96b14b07781ab136e9772a9..2dba1bb9a5d019cc69e78a8fafc351c0c979de52 100644
--- a/src/objects.cc
+++ b/src/objects.cc
@@ -11941,7 +11941,8 @@ void SharedFunctionInfo::AddSharedCodeToOptimizedCodeMap(
DCHECK(code->kind() == Code::OPTIMIZED_FUNCTION);
// Empty code maps are unsupported.
if (shared->OptimizedCodeMapIsCleared()) return;
- shared->optimized_code_map()->set(kSharedCodeIndex, *code);
+ Handle<WeakCell> cell = isolate->factory()->NewWeakCell(code);
+ shared->optimized_code_map()->set(kSharedCodeIndex, *cell);
}
@@ -11959,66 +11960,87 @@ void SharedFunctionInfo::AddToOptimizedCodeMap(
STATIC_ASSERT(kEntryLength == 4);
Handle<FixedArray> new_code_map;
int entry;
+
if (shared->OptimizedCodeMapIsCleared()) {
new_code_map = isolate->factory()->NewFixedArray(kInitialLength, TENURED);
+ new_code_map->set(kSharedCodeIndex, *isolate->factory()->empty_weak_cell(),
+ SKIP_WRITE_BARRIER);
entry = kEntriesStart;
} else {
Handle<FixedArray> old_code_map(shared->optimized_code_map(), isolate);
entry = shared->SearchOptimizedCodeMapEntry(*native_context, osr_ast_id);
if (entry > kSharedCodeIndex) {
// Found an existing context-specific entry, it must not contain any code.
- DCHECK_EQ(isolate->heap()->undefined_value(),
- old_code_map->get(entry + kCachedCodeOffset));
+ DCHECK(WeakCell::cast(old_code_map->get(entry + kCachedCodeOffset))
+ ->cleared());
// Just set the code and literals to the entry.
- old_code_map->set(entry + kCachedCodeOffset, *code);
- old_code_map->set(entry + kLiteralsOffset, *literals);
+ Handle<WeakCell> code_cell = code->IsUndefined()
+ ? isolate->factory()->empty_weak_cell()
+ : isolate->factory()->NewWeakCell(code);
+ Handle<WeakCell> literals_cell =
+ isolate->factory()->NewWeakCell(literals);
+ old_code_map->set(entry + kCachedCodeOffset, *code_cell);
+ old_code_map->set(entry + kLiteralsOffset, *literals_cell);
return;
}
- // Copy old optimized code map and append one new entry.
- new_code_map = isolate->factory()->CopyFixedArrayAndGrow(
- old_code_map, kEntryLength, TENURED);
- // TODO(mstarzinger): Temporary workaround. The allocation above might have
- // flushed the optimized code map and the copy we created is full of holes.
- // For now we just give up on adding the entry and pretend it got flushed.
- if (shared->OptimizedCodeMapIsCleared()) return;
- entry = old_code_map->length();
+ // Can we reuse an entry?
+ DCHECK(entry < kEntriesStart);
+ int length = old_code_map->length();
+ for (int i = kEntriesStart; i < length; i += kEntryLength) {
+ if (WeakCell::cast(old_code_map->get(i + kContextOffset))->cleared()) {
+ new_code_map = old_code_map;
+ entry = i;
+ break;
+ }
+ }
+
+ if (entry < kEntriesStart) {
+ // Copy old optimized code map and append one new entry.
+ new_code_map = isolate->factory()->CopyFixedArrayAndGrow(
+ old_code_map, kEntryLength, TENURED);
+ // TODO(mstarzinger): Temporary workaround. The allocation above might
+ // have flushed the optimized code map and the copy we created is full of
+ // holes. For now we just give up on adding the entry and pretend it got
+ // flushed.
+ if (shared->OptimizedCodeMapIsCleared()) return;
+ entry = old_code_map->length();
+ }
}
- new_code_map->set(entry + kContextOffset, *native_context);
- new_code_map->set(entry + kCachedCodeOffset, *code);
- new_code_map->set(entry + kLiteralsOffset, *literals);
+
+ Handle<WeakCell> code_cell = code->IsUndefined()
+ ? isolate->factory()->empty_weak_cell()
+ : isolate->factory()->NewWeakCell(code);
+ Handle<WeakCell> literals_cell = isolate->factory()->NewWeakCell(literals);
+ WeakCell* context_cell = native_context->self_weak_cell();
+
+ new_code_map->set(entry + kContextOffset, context_cell);
+ new_code_map->set(entry + kCachedCodeOffset, *code_cell);
+ new_code_map->set(entry + kLiteralsOffset, *literals_cell);
new_code_map->set(entry + kOsrAstIdOffset, Smi::FromInt(osr_ast_id.ToInt()));
#ifdef DEBUG
for (int i = kEntriesStart; i < new_code_map->length(); i += kEntryLength) {
- DCHECK(new_code_map->get(i + kContextOffset)->IsNativeContext());
- Object* code = new_code_map->get(i + kCachedCodeOffset);
- if (code != isolate->heap()->undefined_value()) {
- DCHECK(code->IsCode());
- DCHECK(Code::cast(code)->kind() == Code::OPTIMIZED_FUNCTION);
- }
- DCHECK(new_code_map->get(i + kLiteralsOffset)->IsFixedArray());
+ WeakCell* cell = WeakCell::cast(new_code_map->get(i + kContextOffset));
+ DCHECK(cell->cleared() || cell->value()->IsNativeContext());
+ cell = WeakCell::cast(new_code_map->get(i + kCachedCodeOffset));
+ DCHECK(cell->cleared() ||
+ (cell->value()->IsCode() &&
+ Code::cast(cell->value())->kind() == Code::OPTIMIZED_FUNCTION));
+ cell = WeakCell::cast(new_code_map->get(i + kLiteralsOffset));
+ DCHECK(cell->cleared() || cell->value()->IsFixedArray());
DCHECK(new_code_map->get(i + kOsrAstIdOffset)->IsSmi());
}
#endif
- // Zap any old optimized code map.
- if (!shared->OptimizedCodeMapIsCleared()) {
- FixedArray* old_code_map = shared->optimized_code_map();
- old_code_map->FillWithHoles(0, old_code_map->length());
+ FixedArray* old_code_map = shared->optimized_code_map();
+ if (old_code_map != *new_code_map) {
+ shared->set_optimized_code_map(*new_code_map);
}
-
- shared->set_optimized_code_map(*new_code_map);
}
void SharedFunctionInfo::ClearOptimizedCodeMap() {
- // Zap any old optimized code map.
- if (!OptimizedCodeMapIsCleared()) {
- FixedArray* old_code_map = optimized_code_map();
- old_code_map->FillWithHoles(0, old_code_map->length());
- }
-
FixedArray* cleared_map = GetHeap()->cleared_optimized_code_map();
set_optimized_code_map(cleared_map, SKIP_WRITE_BARRIER);
}
@@ -12034,8 +12056,10 @@ void SharedFunctionInfo::EvictFromOptimizedCodeMap(Code* optimized_code,
int dst = kEntriesStart;
int length = code_map->length();
for (int src = kEntriesStart; src < length; src += kEntryLength) {
- DCHECK(code_map->get(src)->IsNativeContext());
- if (code_map->get(src + kCachedCodeOffset) == optimized_code) {
+ DCHECK(WeakCell::cast(code_map->get(src))->cleared() ||
+ WeakCell::cast(code_map->get(src))->value()->IsNativeContext());
+ if (WeakCell::cast(code_map->get(src + kCachedCodeOffset))->value() ==
+ optimized_code) {
BailoutId osr(Smi::cast(code_map->get(src + kOsrAstIdOffset))->value());
if (FLAG_trace_opt) {
PrintF("[evicting entry from optimizing code map (%s) for ", reason);
@@ -12052,7 +12076,8 @@ void SharedFunctionInfo::EvictFromOptimizedCodeMap(Code* optimized_code,
}
// In case of non-OSR entry just clear the code in order to proceed
// sharing literals.
- code_map->set_undefined(src + kCachedCodeOffset);
+ code_map->set(src + kCachedCodeOffset, heap->empty_weak_cell(),
+ SKIP_WRITE_BARRIER);
}
// Keep the src entry by copying it to the dst entry.
@@ -12067,9 +12092,11 @@ void SharedFunctionInfo::EvictFromOptimizedCodeMap(Code* optimized_code,
}
dst += kEntryLength;
}
- if (code_map->get(kSharedCodeIndex) == optimized_code) {
+ if (WeakCell::cast(code_map->get(kSharedCodeIndex))->value() ==
+ optimized_code) {
// Evict context-independent code as well.
- code_map->set_undefined(kSharedCodeIndex);
+ code_map->set(kSharedCodeIndex, heap->empty_weak_cell(),
+ SKIP_WRITE_BARRIER);
if (FLAG_trace_opt) {
PrintF("[evicting entry from optimizing code map (%s) for ", reason);
ShortPrint();
@@ -12081,7 +12108,7 @@ void SharedFunctionInfo::EvictFromOptimizedCodeMap(Code* optimized_code,
heap->RightTrimFixedArray<Heap::CONCURRENT_TO_SWEEPER>(code_map,
length - dst);
if (code_map->length() == kEntriesStart &&
- code_map->get(kSharedCodeIndex)->IsUndefined()) {
+ WeakCell::cast(code_map->get(kSharedCodeIndex))->cleared()) {
ClearOptimizedCodeMap();
}
}
@@ -12096,7 +12123,7 @@ void SharedFunctionInfo::TrimOptimizedCodeMap(int shrink_by) {
GetHeap()->RightTrimFixedArray<Heap::SEQUENTIAL_TO_SWEEPER>(code_map,
shrink_by);
if (code_map->length() == kEntriesStart &&
- code_map->get(kSharedCodeIndex)->IsUndefined()) {
+ WeakCell::cast(code_map->get(kSharedCodeIndex))->cleared()) {
ClearOptimizedCodeMap();
}
}
@@ -13337,12 +13364,14 @@ int SharedFunctionInfo::SearchOptimizedCodeMapEntry(Context* native_context,
int length = optimized_code_map->length();
Smi* osr_ast_id_smi = Smi::FromInt(osr_ast_id.ToInt());
for (int i = kEntriesStart; i < length; i += kEntryLength) {
- if (optimized_code_map->get(i + kContextOffset) == native_context &&
+ if (WeakCell::cast(optimized_code_map->get(i + kContextOffset))
+ ->value() == native_context &&
optimized_code_map->get(i + kOsrAstIdOffset) == osr_ast_id_smi) {
return i;
}
}
- Object* shared_code = optimized_code_map->get(kSharedCodeIndex);
+ Object* shared_code =
+ WeakCell::cast(optimized_code_map->get(kSharedCodeIndex))->value();
if (shared_code->IsCode() && osr_ast_id.IsNone()) {
return kSharedCodeIndex;
}
@@ -13358,13 +13387,22 @@ CodeAndLiterals SharedFunctionInfo::SearchOptimizedCodeMap(
if (entry != kNotFound) {
FixedArray* code_map = optimized_code_map();
if (entry == kSharedCodeIndex) {
- result = {Code::cast(code_map->get(kSharedCodeIndex)), nullptr};
-
+ // We know the weak cell isn't cleared because we made sure of it in
+ // SearchOptimizedCodeMapEntry and performed no allocations since that
+ // call.
+ result = {
+ Code::cast(WeakCell::cast(code_map->get(kSharedCodeIndex))->value()),
+ nullptr};
} else {
DCHECK_LE(entry + kEntryLength, code_map->length());
- Object* code = code_map->get(entry + kCachedCodeOffset);
- result = {code->IsUndefined() ? nullptr : Code::cast(code),
- LiteralsArray::cast(code_map->get(entry + kLiteralsOffset))};
+ WeakCell* cell = WeakCell::cast(code_map->get(entry + kCachedCodeOffset));
+ WeakCell* literals_cell =
+ WeakCell::cast(code_map->get(entry + kLiteralsOffset));
+
+ result = {cell->cleared() ? nullptr : Code::cast(cell->value()),
+ literals_cell->cleared()
+ ? nullptr
+ : LiteralsArray::cast(literals_cell->value())};
}
}
if (FLAG_trace_opt && !OptimizedCodeMapIsCleared() &&
« no previous file with comments | « src/heap/objects-visiting-inl.h ('k') | src/objects-inl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698