[pypy-commit] stmgc c8-new-page-handling: progress
Raemi
noreply at buildbot.pypy.org
Fri Sep 19 13:09:29 CEST 2014
Author: Remi Meier <remi.meier at inf.ethz.ch>
Branch: c8-new-page-handling
Changeset: r1394:5647127245ea
Date: 2014-09-19 12:54 +0200
http://bitbucket.org/pypy/stmgc/changeset/5647127245ea/
Log: progress
diff --git a/c8/stm/core.c b/c8/stm/core.c
--- a/c8/stm/core.c
+++ b/c8/stm/core.c
@@ -91,8 +91,6 @@
/* make our page private */
page_privatize_in(STM_SEGMENT->segment_num, pagenum);
- volatile char *dummy = REAL_ADDRESS(STM_SEGMENT->segment_base, pagenum*4096UL);
- *dummy = *dummy; /* force copy-on-write from shared page */
/* if there were modifications in the page, revert them: */
copy_bk_objs_from(shared_page_holder, pagenum);
@@ -328,33 +326,6 @@
/* ############# STM ############# */
-void _privatize_shared_page(uintptr_t pagenum)
-{
- /* privatize pages of obj for our segment iff previously
- the pages were fully shared. */
-#ifndef NDEBUG
- long l;
- for (l = 0; l < NB_SEGMENTS; l++) {
- assert(get_priv_segment(l)->privatization_lock);
- }
-#endif
-
- uintptr_t i;
- int my_segnum = STM_SEGMENT->segment_num;
-
- XXX();
- //assert(is_shared_log_page(pagenum));
- /* char *src = (char*)(get_virt_page_of(0, pagenum) * 4096UL); */
-
- /* for (i = 1; i < NB_SEGMENTS; i++) { */
- /* page_privatize_in(i, pagenum, src); */
- /* } */
- /* set_page_private_in(0, pagenum); */
-
- /* OPT_ASSERT(is_private_log_page_in(my_segnum, pagenum)); */
- /* assert(!is_shared_log_page(pagenum)); */
-}
-
void _stm_write_slowpath(object_t *obj)
{
assert(_seems_to_be_running_transaction());
@@ -374,31 +345,39 @@
/* add to read set: */
stm_read(obj);
- /* create backup copy: */
+ /* create backup copy (this may cause several page faults XXX): */
struct object_s *bk_obj = malloc(obj_size);
memcpy(bk_obj, realobj, obj_size);
- /* if there are shared pages, privatize them */
+ /* privatize pages: */
+ acquire_all_privatization_locks();
uintptr_t page;
for (page = first_page; page <= end_page; page++) {
- XXX();
- /* if (is_shared_log_page(page)) { */
- /* long i; */
- /* for (i = 0; i < NB_SEGMENTS; i++) { */
- /* acquire_privatization_lock(i); */
- /* } */
- /* if (is_shared_log_page(page)) */
- /* _privatize_shared_page(page); */
- /* for (i = NB_SEGMENTS-1; i >= 0; i--) { */
- /* release_privatization_lock(i); */
- /* } */
- /* } */
+ /* check if our page is private or we are the only shared-page holder */
+ assert(get_page_status_in(my_segnum, page) != PAGE_NO_ACCESS);
+
+ if (get_page_status_in(my_segnum, page) == PAGE_PRIVATE)
+ continue;
+
+ /* make sure all the others are NO_ACCESS
+ choosing to make us PRIVATE is harder because then nobody must ever
+ update the shared page in stm_validate() except if it is the sole
+ reader of it. But then we don't actually know which revision the page is at. */
+ long i;
+ for (i = 0; i < NB_SEGMENTS; i++) {
+ if (i == my_segnum)
+ continue;
+
+ if (get_page_status_in(i, page) == PAGE_SHARED) {
+ /* xxx: unmap? */
+ mprotect((char*)(get_virt_page_of(i, page) * 4096UL), 4096UL, PROT_NONE);
+ set_page_status_in(i, page, PAGE_NO_ACCESS);
+ }
+ }
}
- /* pages not shared anymore. but we still may have
- only a read protected page ourselves: */
-
- acquire_privatization_lock(my_segnum);
+ /* all pages are either private or we were the first to write to a shared
+ page and therefore got it as our private one */
/* remove the WRITE_BARRIER flag */
obj->stm_flags &= ~GCFLAG_WRITE_BARRIER;
@@ -407,7 +386,7 @@
LIST_APPEND(STM_PSEGMENT->objects_pointing_to_nursery, obj);
/* done fiddling with protection and privatization */
- release_privatization_lock(my_segnum);
+ release_all_privatization_locks();
/* phew, now add the obj to the write-set and register the
backup copy. */
diff --git a/c8/stm/pages.c b/c8/stm/pages.c
--- a/c8/stm/pages.c
+++ b/c8/stm/pages.c
@@ -15,39 +15,6 @@
}
/************************************************************/
-static void check_remap_makes_sense(char *addr, size_t size, ssize_t pgoff)
-{
- dprintf(("remap_file_pages: 0x%lx bytes: (seg%ld %p) --> (seg%ld %p)\n",
- (long)size,
- (long)((addr - stm_object_pages) / 4096UL) / NB_PAGES,
- (void *)((addr - stm_object_pages) % (4096UL * NB_PAGES)),
- (long)pgoff / NB_PAGES,
- (void *)((pgoff % NB_PAGES) * 4096UL)));
- assert(size % 4096 == 0);
- assert(size <= TOTAL_MEMORY);
- assert(((uintptr_t)addr) % 4096 == 0);
- assert(addr >= stm_object_pages);
- assert(addr <= stm_object_pages + TOTAL_MEMORY - size);
- assert(pgoff >= 0);
- assert(pgoff <= (TOTAL_MEMORY - size) / 4096UL);
-
- /* assert remappings follow the rule that page N in one segment
- can only be remapped to page N in another segment */
- assert(((addr - stm_object_pages) / 4096UL - pgoff) % NB_PAGES == 0);
-}
-
-static void d_remap_file_pages(char *addr, size_t size, ssize_t pgoff)
-{
- check_remap_makes_sense(addr, size, pgoff);
-
- char *res = mmap(addr, size,
- PROT_READ | PROT_WRITE,
- MAP_PRIVATE | MAP_NORESERVE | MAP_FIXED,
- stm_object_pages_fd, pgoff * 4096UL);
- if (UNLIKELY(res != addr))
- stm_fatalerror("mmap (remapping page): %m");
-}
-
static void pages_initialize_shared_for(long segnum, uintptr_t pagenum, uintptr_t count)
{
@@ -101,6 +68,9 @@
stm_fatalerror("page_privatize_in failed (mmap): %m");
set_page_status_in(segnum, pagenum, PAGE_PRIVATE);
+
+ volatile char *dummy = REAL_ADDRESS(get_segment_base(segnum), pagenum*4096UL);
+ *dummy = *dummy; /* force copy-on-write from shared page */
}
More information about the pypy-commit
mailing list