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

Unified Diff: runtime/vm/pages.cc

Issue 578443003: Support old-space allocation in generated code (bump block only for now). (Closed) Base URL: http://dart.googlecode.com/svn/branches/bleeding_edge/dart/
Patch Set: Created 6 years, 3 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
Index: runtime/vm/pages.cc
===================================================================
--- runtime/vm/pages.cc (revision 40250)
+++ runtime/vm/pages.cc (working copy)
@@ -403,43 +403,69 @@
}
+// Provides exclusive access to the pages, and ensures they are walkable.
+class ExclusivePageIterator : ValueObject {
+ public:
+ explicit ExclusivePageIterator(const PageSpace* space)
+ : space_(space), ml_(space->pages_lock_) {
+ space_->MakeIterable();
+ page_ = space_->pages_;
+ if (page_ == NULL) {
+ page_ = space_->exec_pages_;
+ if (page_ == NULL) {
+ page_ = space_->large_pages_;
+ }
+ }
+ }
+ HeapPage* page() const { return page_; }
+ bool done() const { return page_ == NULL; }
+ void Advance() {
+ ASSERT(!done());
+ page_ = space_->NextPageAnySize(page_);
+ }
+ private:
+ const PageSpace* space_;
+ MutexLocker ml_;
+ NoGCScope no_gc;
+ HeapPage* page_;
+};
+
+
+void PageSpace::MakeIterable() const {
+ // TODO(koda): Assert not called from concurrent sweeper task.
+ if (bump_top_ < bump_end_) {
+ FreeListElement::AsElement(bump_top_, bump_end_ - bump_top_);
+ }
+}
+
+
bool PageSpace::Contains(uword addr) const {
- MutexLocker ml(pages_lock_);
- NoGCScope no_gc;
- HeapPage* page = pages_;
- while (page != NULL) {
- if (page->Contains(addr)) {
+ for (ExclusivePageIterator it(this); !it.done(); it.Advance()) {
+ if (it.page()->Contains(addr)) {
return true;
}
- page = NextPageAnySize(page);
}
return false;
}
bool PageSpace::Contains(uword addr, HeapPage::PageType type) const {
- MutexLocker ml(pages_lock_);
- NoGCScope no_gc;
- HeapPage* page = pages_;
- while (page != NULL) {
- if ((page->type() == type) && page->Contains(addr)) {
+ for (ExclusivePageIterator it(this); !it.done(); it.Advance()) {
+ if ((it.page()->type() == type) && it.page()->Contains(addr)) {
return true;
}
- page = NextPageAnySize(page);
}
return false;
}
void PageSpace::StartEndAddress(uword* start, uword* end) const {
- MutexLocker ml(pages_lock_);
- NoGCScope no_gc;
ASSERT((pages_ != NULL) || (exec_pages_ != NULL) || (large_pages_ != NULL));
*start = static_cast<uword>(~0);
*end = 0;
- for (HeapPage* page = pages_; page != NULL; page = NextPageAnySize(page)) {
- *start = Utils::Minimum(*start, page->object_start());
- *end = Utils::Maximum(*end, page->object_end());
+ for (ExclusivePageIterator it(this); !it.done(); it.Advance()) {
+ *start = Utils::Minimum(*start, it.page()->object_start());
+ *end = Utils::Maximum(*end, it.page()->object_end());
}
ASSERT(*start != static_cast<uword>(~0));
ASSERT(*end != 0);
@@ -447,53 +473,36 @@
void PageSpace::VisitObjects(ObjectVisitor* visitor) const {
- MutexLocker ml(pages_lock_);
- NoGCScope no_gc;
- HeapPage* page = pages_;
- while (page != NULL) {
- page->VisitObjects(visitor);
- page = NextPageAnySize(page);
+ for (ExclusivePageIterator it(this); !it.done(); it.Advance()) {
+ it.page()->VisitObjects(visitor);
}
}
void PageSpace::VisitObjectPointers(ObjectPointerVisitor* visitor) const {
- MutexLocker ml(pages_lock_);
- NoGCScope no_gc;
- HeapPage* page = pages_;
- while (page != NULL) {
- page->VisitObjectPointers(visitor);
- page = NextPageAnySize(page);
+ for (ExclusivePageIterator it(this); !it.done(); it.Advance()) {
+ it.page()->VisitObjectPointers(visitor);
}
}
RawObject* PageSpace::FindObject(FindObjectVisitor* visitor,
HeapPage::PageType type) const {
- ASSERT(Isolate::Current()->no_gc_scope_depth() != 0);
- MutexLocker ml(pages_lock_);
- NoGCScope no_gc;
- HeapPage* page = pages_;
- while (page != NULL) {
- if (page->type() == type) {
- RawObject* obj = page->FindObject(visitor);
+ for (ExclusivePageIterator it(this); !it.done(); it.Advance()) {
+ if (it.page()->type() == type) {
+ RawObject* obj = it.page()->FindObject(visitor);
if (obj != Object::null()) {
return obj;
}
}
- page = NextPageAnySize(page);
}
return Object::null();
}
void PageSpace::WriteProtect(bool read_only) {
- MutexLocker ml(pages_lock_);
- NoGCScope no_gc;
- HeapPage* page = pages_;
- while (page != NULL) {
- page->WriteProtect(read_only);
- page = NextPageAnySize(page);
+ for (ExclusivePageIterator it(this); !it.done(); it.Advance()) {
+ it.page()->WriteProtect(read_only);
}
}
@@ -554,7 +563,9 @@
{
// "pages" is an array [page0, page1, ..., pageN], each page of the form
// {"object_start": "0x...", "objects": [size, class id, size, ...]}
+ // TODO(19445): Use ExclusivePageIterator once HeapMap supports large pages.
MutexLocker ml(pages_lock_);
+ MakeIterable();
NoGCScope no_gc;
JSONArray all_pages(&heap_map, "pages");
for (HeapPage* page = pages_; page != NULL; page = page->next()) {
@@ -662,6 +673,7 @@
int64_t mid1 = OS::GetCurrentTimeMicros();
// Abandon the remainder of the bump allocation block.
+ MakeIterable();
bump_top_ = 0;
bump_end_ = 0;
// Reset the freelists and setup sweeping.
@@ -672,7 +684,7 @@
int64_t mid3 = 0;
{
- GCSweeper sweeper(heap_);
+ GCSweeper sweeper;
// During stop-the-world phases we should use bulk lock when adding elements
// to the free list.
@@ -812,10 +824,14 @@
uword result = bump_top_;
bump_top_ += size;
usage_.used_in_words += size >> kWordSizeLog2;
- remaining -= size;
- if (remaining > 0) {
- FreeListElement::AsElement(bump_top_, remaining);
+ // Note: Remaining block is unwalkable until MakeIterable is called.
+ #ifdef DEBUG
+ if (bump_top_ < bump_end_) {
+ // Fail fast if we try to walk the remaining block.
+ COMPILE_ASSERT(kIllegalCid == 0);
+ *reinterpret_cast<uword*>(bump_top_) = 0;
}
+ #endif // DEBUG
return result;
}

Powered by Google App Engine
This is Rietveld 408576698