Author: Remi Meier <[email protected]>
Branch:
Changeset: r1636:49aadef69fd0
Date: 2015-02-18 16:05 +0100
http://bitbucket.org/pypy/stmgc/changeset/49aadef69fd0/
Log: phew, ensure that nobody applies our old backup copies after we just
committed
diff --git a/c8/stm/core.c b/c8/stm/core.c
--- a/c8/stm/core.c
+++ b/c8/stm/core.c
@@ -79,9 +79,9 @@
assert((get_page_status_in(STM_SEGMENT->segment_num,
current_page_num) != PAGE_NO_ACCESS));
- dprintf(("import slice seg=%d obj=%p off=%lu sz=%d pg=%lu\n",
- from_segnum, obj, SLICE_OFFSET(undo->slice),
- SLICE_SIZE(undo->slice), current_page_num));
+ /* dprintf(("import slice seg=%d obj=%p off=%lu sz=%d pg=%lu\n", */
+ /* from_segnum, obj, SLICE_OFFSET(undo->slice), */
+ /* SLICE_SIZE(undo->slice), current_page_num)); */
char *src, *dst;
if (src_segment_base != NULL)
src = REAL_ADDRESS(src_segment_base, oslice);
@@ -232,6 +232,7 @@
}
int segnum = get_segment_of_linear_address(addr);
+ OPT_ASSERT(segnum != 0);
if (segnum != STM_SEGMENT->segment_num) {
fprintf(stderr, "Segmentation fault: accessing %p (seg %d) from"
" seg %d\n", addr, segnum, STM_SEGMENT->segment_num);
@@ -263,11 +264,7 @@
struct stm_commit_log_entry_s *cl = &commit_log_root;
fprintf(stderr, "commit log:\n");
- while ((cl = cl->next)) {
- if (cl == INEV_RUNNING) {
- fprintf(stderr, " INEVITABLE\n");
- return;
- }
+ while (cl) {
fprintf(stderr, " entry at %p: seg %d, rev %lu\n", cl,
cl->segment_num, cl->rev_num);
struct stm_undo_s *undo = cl->written;
struct stm_undo_s *end = undo + cl->written_count;
@@ -279,6 +276,12 @@
/* fprintf(stderr, " 0x%016lx", *(long *)(undo->backup + i));
*/
fprintf(stderr, "\n");
}
+
+ cl = cl->next;
+ if (cl == INEV_RUNNING) {
+ fprintf(stderr, " INEVITABLE\n");
+ return;
+ }
}
}
@@ -477,6 +480,12 @@
reset_wb_executed_flags();
check_all_write_barrier_flags(STM_SEGMENT->segment_base,
STM_PSEGMENT->modified_old_objects);
+
+ /* need to remove the entries in modified_old_objects "at the same
+ time" as the attach to commit log. Otherwise, another thread may
+ see the new CL entry, import it, look for backup copies in this
+ segment and find the old backup copies! */
+ acquire_modification_lock(STM_SEGMENT->segment_num);
}
/* try to attach to commit log: */
@@ -493,6 +502,7 @@
}
if (is_commit) {
+ release_modification_lock(STM_SEGMENT->segment_num);
/* XXX: unfortunately, if we failed to attach our CL entry,
we have to re-add the WB_EXECUTED flags before we try to
validate again because of said condition (s.a) */
@@ -511,6 +521,16 @@
in major_do_validation_and_minor_collections, and don't free 'new'
*/
_stm_collectable_safe_point();
}
+
+ if (is_commit) {
+ /* compare with _validate_and_add_to_commit_log */
+ STM_PSEGMENT->transaction_state = TS_NONE;
+ STM_PSEGMENT->safe_point = SP_NO_TRANSACTION;
+
+ list_clear(STM_PSEGMENT->modified_old_objects);
+ STM_PSEGMENT->last_commit_log_entry = new;
+ release_modification_lock(STM_SEGMENT->segment_num);
+ }
}
static void _validate_and_turn_inevitable(void)
@@ -533,20 +553,19 @@
check_all_write_barrier_flags(STM_SEGMENT->segment_base,
STM_PSEGMENT->modified_old_objects);
+ /* compare with _validate_and_attach: */
+ STM_PSEGMENT->transaction_state = TS_NONE;
+ STM_PSEGMENT->safe_point = SP_NO_TRANSACTION;
+ list_clear(STM_PSEGMENT->modified_old_objects);
+ STM_PSEGMENT->last_commit_log_entry = new;
+
+ /* do it: */
bool yes = __sync_bool_compare_and_swap(&old->next, INEV_RUNNING, new);
OPT_ASSERT(yes);
}
else {
_validate_and_attach(new);
}
-
- STM_PSEGMENT->transaction_state = TS_NONE;
- STM_PSEGMENT->safe_point = SP_NO_TRANSACTION;
-
- acquire_modification_lock(STM_SEGMENT->segment_num);
- list_clear(STM_PSEGMENT->modified_old_objects);
- STM_PSEGMENT->last_commit_log_entry = new;
- release_modification_lock(STM_SEGMENT->segment_num);
}
/* ############# STM ############# */
@@ -1140,7 +1159,7 @@
if (get_page_status_in(i, page) != PAGE_NO_ACCESS) {
/* shared or private, but never segfault */
char *dst = REAL_ADDRESS(get_segment_base(i), frag);
- //dprintf(("-> flush %p to seg %lu, sz=%lu\n", frag, i,
frag_size));
+ dprintf(("-> flush %p to seg %lu, sz=%lu\n", frag, i,
frag_size));
memcpy(dst, src, frag_size);
}
}
diff --git a/c8/stm/gcpage.c b/c8/stm/gcpage.c
--- a/c8/stm/gcpage.c
+++ b/c8/stm/gcpage.c
@@ -482,6 +482,7 @@
This is the case for transactions where
MINOR_NOTHING_TO_DO() == true
but they still did write-barriers on objects
+ (the objs are still in modified_old_objects list)
*/
lst = pseg->objects_pointing_to_nursery;
if (!list_is_empty(lst)) {
@@ -516,6 +517,7 @@
#pragma pop_macro("STM_PSEGMENT")
}
+
static inline bool largemalloc_keep_object_at(char *data)
{
/* this is called by _stm_largemalloc_sweep() */
diff --git a/c8/stm/largemalloc.c b/c8/stm/largemalloc.c
--- a/c8/stm/largemalloc.c
+++ b/c8/stm/largemalloc.c
@@ -616,6 +616,7 @@
/* use the callback to know if 'chunk' contains an object that
survives or dies */
if (!_largemalloc_sweep_keep(chunk)) {
+ dprintf(("dies: %p\n", (char*)((char*)&chunk->d -
stm_object_pages)));
_large_free(chunk); /* dies */
}
chunk = mnext;
_______________________________________________
pypy-commit mailing list
[email protected]
https://mail.python.org/mailman/listinfo/pypy-commit