Commit a1e22519 authored by Dominik Inführ's avatar Dominik Inführ Committed by Commit Bot

[heap] Remove deletion entries from store buffer

Get rid of deletion entries in the store buffer. Clearing a slot now
first empties the store buffer and then directly deletes the slot
from the remembered set.

Bug: v8:9454
Change-Id: I656db593a0478db3fa63324d7f3c6862b4b5e776
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1766130Reviewed-by: 's avatarUlan Degenbaev <ulan@chromium.org>
Commit-Queue: Dominik Inführ <dinfuehr@chromium.org>
Cr-Commit-Position: refs/heads/master@{#63359}
parent b3d1fdcb
......@@ -5527,7 +5527,8 @@ void Heap::ClearRecordedSlot(HeapObject object, ObjectSlot slot) {
Page* page = Page::FromAddress(slot.address());
if (!page->InYoungGeneration()) {
DCHECK_EQ(page->owner_identity(), OLD_SPACE);
store_buffer()->DeleteEntry(slot.address());
store_buffer()->MoveAllEntriesToRememberedSet();
RememberedSet<OLD_TO_NEW>::Remove(page, slot.address());
}
}
......@@ -5550,7 +5551,9 @@ void Heap::ClearRecordedSlotRange(Address start, Address end) {
DCHECK(!page->IsLargePage());
if (!page->InYoungGeneration()) {
DCHECK_EQ(page->owner_identity(), OLD_SPACE);
store_buffer()->DeleteEntry(start, end);
store_buffer()->MoveAllEntriesToRememberedSet();
RememberedSet<OLD_TO_NEW>::RemoveRange(page, start, end,
SlotSet::KEEP_EMPTY_BUCKETS);
}
}
......
......@@ -12,16 +12,6 @@
namespace v8 {
namespace internal {
void StoreBuffer::InsertDeletionIntoStoreBuffer(Address start, Address end) {
if (top_ + sizeof(Address) * 2 > limit_[current_]) {
StoreBufferOverflow(heap_->isolate());
}
*top_ = MarkDeletionAddress(start);
top_++;
*top_ = end;
top_++;
}
void StoreBuffer::InsertIntoStoreBuffer(Address slot) {
if (top_ + sizeof(Address) > limit_[current_]) {
StoreBufferOverflow(heap_->isolate());
......
......@@ -28,7 +28,6 @@ StoreBuffer::StoreBuffer(Heap* heap)
}
task_running_ = false;
insertion_callback = &InsertDuringRuntime;
deletion_callback = &DeleteDuringRuntime;
}
void StoreBuffer::SetUp() {
......@@ -91,22 +90,11 @@ void StoreBuffer::TearDown() {
}
}
void StoreBuffer::DeleteDuringRuntime(StoreBuffer* store_buffer, Address start,
Address end) {
DCHECK(store_buffer->mode() == StoreBuffer::NOT_IN_GC);
store_buffer->InsertDeletionIntoStoreBuffer(start, end);
}
void StoreBuffer::InsertDuringRuntime(StoreBuffer* store_buffer, Address slot) {
DCHECK(store_buffer->mode() == StoreBuffer::NOT_IN_GC);
store_buffer->InsertIntoStoreBuffer(slot);
}
void StoreBuffer::DeleteDuringGarbageCollection(StoreBuffer* store_buffer,
Address start, Address end) {
UNREACHABLE();
}
void StoreBuffer::InsertDuringGarbageCollection(StoreBuffer* store_buffer,
Address slot) {
DCHECK(store_buffer->mode() != StoreBuffer::NOT_IN_GC);
......@@ -117,10 +105,8 @@ void StoreBuffer::SetMode(StoreBufferMode mode) {
mode_ = mode;
if (mode == NOT_IN_GC) {
insertion_callback = &InsertDuringRuntime;
deletion_callback = &DeleteDuringRuntime;
} else {
insertion_callback = &InsertDuringGarbageCollection;
deletion_callback = &DeleteDuringGarbageCollection;
}
}
......@@ -160,24 +146,9 @@ void StoreBuffer::MoveEntriesToRememberedSet(int index) {
MemoryChunk::BaseAddress(addr) != chunk->address()) {
chunk = MemoryChunk::FromAnyPointerAddress(addr);
}
if (IsDeletionAddress(addr)) {
last_inserted_addr = kNullAddress;
current++;
Address end = *current;
DCHECK(!IsDeletionAddress(end));
addr = UnmarkDeletionAddress(addr);
if (end) {
RememberedSet<OLD_TO_NEW>::RemoveRange(chunk, addr, end,
SlotSet::PREFREE_EMPTY_BUCKETS);
} else {
RememberedSet<OLD_TO_NEW>::Remove(chunk, addr);
}
} else {
DCHECK(!IsDeletionAddress(addr));
if (addr != last_inserted_addr) {
RememberedSet<OLD_TO_NEW>::Insert(chunk, addr);
last_inserted_addr = addr;
}
if (addr != last_inserted_addr) {
RememberedSet<OLD_TO_NEW>::Insert(chunk, addr);
last_inserted_addr = addr;
}
}
lazy_top_[index] = nullptr;
......
......@@ -33,17 +33,11 @@ class StoreBuffer {
Max(static_cast<int>(kMinExpectedOSPageSize / kStoreBuffers),
1 << (11 + kSystemPointerSizeLog2));
static const int kStoreBufferMask = kStoreBufferSize - 1;
static const intptr_t kDeletionTag = 1;
V8_EXPORT_PRIVATE static int StoreBufferOverflow(Isolate* isolate);
static void DeleteDuringGarbageCollection(StoreBuffer* store_buffer,
Address start, Address end);
static void InsertDuringGarbageCollection(StoreBuffer* store_buffer,
Address slot);
static void DeleteDuringRuntime(StoreBuffer* store_buffer, Address start,
Address end);
static void InsertDuringRuntime(StoreBuffer* store_buffer, Address slot);
explicit StoreBuffer(Heap* heap);
......@@ -61,19 +55,6 @@ class StoreBuffer {
// the remembered set.
void MoveAllEntriesToRememberedSet();
inline bool IsDeletionAddress(Address address) const {
return address & kDeletionTag;
}
inline Address MarkDeletionAddress(Address address) {
return address | kDeletionTag;
}
inline Address UnmarkDeletionAddress(Address address) {
return address & ~kDeletionTag;
}
inline void InsertDeletionIntoStoreBuffer(Address start, Address end);
inline void InsertIntoStoreBuffer(Address slot);
void InsertEntry(Address slot) {
......@@ -83,16 +64,6 @@ class StoreBuffer {
insertion_callback(this, slot);
}
// If we only want to delete a single slot, end should be set to null which
// will be written into the second field. When processing the store buffer
// the more efficient Remove method will be called in this case.
void DeleteEntry(Address start, Address end = kNullAddress) {
// Deletions coming from the GC are directly deleted from the remembered
// set. Deletions coming from the runtime are added to the store buffer
// to allow concurrent processing.
deletion_callback(this, start, end);
}
void SetMode(StoreBufferMode mode);
// Used by the concurrent processing thread to transfer entries from the
......@@ -174,7 +145,6 @@ class StoreBuffer {
// Callbacks are more efficient than reading out the gc state for every
// store buffer operation.
void (*insertion_callback)(StoreBuffer*, Address);
void (*deletion_callback)(StoreBuffer*, Address, Address);
};
} // namespace internal
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment