Author: Armin Rigo <ar...@tunes.org> Branch: Changeset: r214:ae4b3bacf4c0 Date: 2013-06-21 11:24 +0200 http://bitbucket.org/pypy/stmgc/changeset/ae4b3bacf4c0/
Log: Pass this test diff --git a/c4/et.c b/c4/et.c --- a/c4/et.c +++ b/c4/et.c @@ -484,6 +484,8 @@ GCFLAG_WRITE_BARRIER | 0); L->h_revision = stm_private_rev_num; + assert(stm_private_rev_num < 0); + assert(stm_private_rev_num & 1); g2l_insert(&d->public_to_private, R, L); fprintf(stderr, "write_barrier: adding %p -> %p to public_to_private\n", R, L); diff --git a/c4/gcpage.c b/c4/gcpage.c --- a/c4/gcpage.c +++ b/c4/gcpage.c @@ -195,8 +195,11 @@ return; restart: - if (obj->h_tid & GCFLAG_VISITED) + if (obj->h_tid & GCFLAG_VISITED) { + fprintf(stderr, "[already visited: %p]\n", obj); + assert(obj == *pobj); return; /* already seen */ + } if (obj->h_revision & 1) { assert(!(obj->h_tid & GCFLAG_PRIVATE_FROM_PROTECTED)); @@ -246,8 +249,11 @@ B->h_tid |= GCFLAG_VISITED; } else { + /* a private_from_protected with a stolen backup copy B */ assert(!(B->h_tid & GCFLAG_BACKUP_COPY)); - abort(); // XXX + gcptr obj1 = B; + visit(&obj1); /* xxx recursion? */ + obj->h_revision = (revision_t)obj1; } } obj->h_tid |= GCFLAG_VISITED; @@ -287,8 +293,12 @@ { //assert(*root == END_MARKER); //root++; - while (root != end) - visit(root++); + while (root != end) { + gcptr o = *root; + visit(root); + fprintf(stderr, "visit stack root: %p -> %p\n", o, *root); + root++; + } } static void mark_all_stack_roots(void) @@ -354,8 +364,13 @@ case that obj->h_revision doesn't have GCFLAG_VISITED, but just removing it is very wrong --- we want 'd' to abort. */ + if (obj->h_tid & GCFLAG_PRIVATE_FROM_PROTECTED) { + assert(IS_POINTER(obj->h_revision)); + obj = (gcptr)obj->h_revision; + } + revision_t v = obj->h_revision; - if (IS_POINTER(v) && !(obj->h_tid & GCFLAG_PRIVATE_FROM_PROTECTED)) { + if (IS_POINTER(v)) { /* has a more recent revision. Oups. */ fprintf(stderr, "ABRT_COLLECT_MAJOR: %p was read but modified already\n", @@ -539,7 +554,8 @@ collection was not preceeded by a minor collection if the thread is busy in a system call for example. */ - if (stmgc_minor_collect_anything_to_do(d)) { + if (stmgc_minor_collect_anything_to_do(d) || + (d->public_descriptor->stolen_objects.size != 0)) { /* Hack: temporarily pretend that we "are" the other thread... */ thread_descriptor = d; diff --git a/c4/steal.c b/c4/steal.c --- a/c4/steal.c +++ b/c4/steal.c @@ -235,12 +235,13 @@ if (L == NULL) continue; assert(L->h_tid & GCFLAG_PRIVATE_FROM_PROTECTED); + assert(IS_POINTER(L->h_revision)); g2l_insert(&d->public_to_private, B, L); /* this is definitely needed: all keys in public_to_private must appear in list_of_read_objects */ - fprintf(stderr, "n.readobj: %p\n", B); + fprintf(stderr, "n.readobj: %p -> %p\n", B, L); assert(!(B->h_tid & GCFLAG_STUB)); gcptrlist_insert(&d->list_of_read_objects, B); diff --git a/c4/test/support.py b/c4/test/support.py --- a/c4/test/support.py +++ b/c4/test/support.py @@ -487,7 +487,9 @@ return p.h_tid & GCFLAG_STUB def check_not_free(p): + print >> sys.stderr, "[checking %r..." % p, assert 42 < (p.h_tid & 0xFFFF) < 521 + print >> sys.stderr, "ok]" def check_nursery_free(p): #assert p.h_tid == p.h_revision == 0 diff --git a/c4/test/test_gcpage.py b/c4/test/test_gcpage.py --- a/c4/test/test_gcpage.py +++ b/c4/test/test_gcpage.py @@ -315,10 +315,12 @@ assert follow_revision(p1).h_tid & GCFLAG_BACKUP_COPY def test_backup_stolen(): - py.test.skip("in-progress") p = palloc(HDR) def f1(r): p1 = lib.stm_write_barrier(p) # private copy + lib.stm_push_root(p1) + minor_collect() + p1 = lib.stm_pop_root() lib.stm_commit_transaction() lib.stm_begin_inevitable_transaction() assert classify(p) == "public" @@ -329,9 +331,13 @@ assert c == 0 p1b = lib.stm_write_barrier(p1) assert p1b == p1 + assert not lib.in_nursery(p1) assert classify(p1) == "private_from_protected" assert classify(follow_revision(p1)) == "backup" + lib.stm_push_root(p1) r.wait_while_in_parallel() + p1b = lib.stm_pop_root() + assert p1b == p1 check_not_free(p1) assert classify(p1) == "private_from_protected" assert classify(follow_revision(p1)) == "public" # has been stolen _______________________________________________ pypy-commit mailing list pypy-commit@python.org http://mail.python.org/mailman/listinfo/pypy-commit