Author: Remi Meier <[email protected]>
Branch:
Changeset: r1969:e3071642fd5c
Date: 2015-11-19 16:42 +0100
http://bitbucket.org/pypy/stmgc/changeset/e3071642fd5c/
Log: free large overflow objs on abort
Benchmarks show (e.g. lee routing) that the more threads we run, the
longer major GCs take (bc. there is more memory to look at). E.g.
Lee on 1 thread spends 12% of its time doing GC; on 4 threads, the
ratio goes up to 39%.
This patch tries to lower the work to be done during major GCs by
freeing overflow objects if the transaction aborted. For now, only
large ones bc. we miss a smallmalloc_free() function (and it's also
not clear if freeing small overflow objs should be done early).
This change improves performance by 5-15% on 4 threads.
diff --git a/c8/stm/core.c b/c8/stm/core.c
--- a/c8/stm/core.c
+++ b/c8/stm/core.c
@@ -1561,6 +1561,14 @@
list_clear(pseg->objects_pointing_to_nursery);
list_clear(pseg->old_objects_with_cards_set);
+ LIST_FOREACH_R(pseg->large_overflow_objects, uintptr_t /*item*/,
+ {
+ if (is_small_uniform((object_t*)item)) {
+ //_stm_small_free()
+ } else {
+ _stm_large_free(stm_object_pages + item);
+ }
+ });
list_clear(pseg->large_overflow_objects);
list_clear(pseg->young_weakrefs);
#pragma pop_macro("STM_SEGMENT")
diff --git a/c8/stm/detach.c b/c8/stm/detach.c
--- a/c8/stm/detach.c
+++ b/c8/stm/detach.c
@@ -127,6 +127,7 @@
// XXX: not sure if the next line is a good idea
tl->last_associated_segment_num = remote_seg_num;
ensure_gs_register(remote_seg_num);
+ assert(old_tl == STM_SEGMENT->running_thread);
timing_event(STM_SEGMENT->running_thread, STM_TRANSACTION_REATTACH);
commit_external_inevitable_transaction();
}
@@ -186,6 +187,7 @@
assert(segnum > 0);
ensure_gs_register(segnum);
+ assert(((stm_thread_local_t *)old) == STM_SEGMENT->running_thread);
timing_event(STM_SEGMENT->running_thread, STM_TRANSACTION_REATTACH);
commit_external_inevitable_transaction();
ensure_gs_register(mysegnum);
diff --git a/c8/test/test_basic.py b/c8/test/test_basic.py
--- a/c8/test/test_basic.py
+++ b/c8/test/test_basic.py
@@ -638,6 +638,21 @@
self.start_transaction()
assert stm_get_char(lp1) == 'a'
+ def test_overflow_freed_on_abort(self):
+ self.start_transaction()
+ big = stm_allocate(GC_LAST_SMALL_SIZE + FAST_ALLOC) # large, outside,
young obj
+ self.push_root(big)
+ stm_minor_collect() # now 'big' is overflow
+ big = self.pop_root()
+ self.abort_transaction()
+
+ self.start_transaction()
+ big2 = stm_allocate(GC_LAST_SMALL_SIZE + FAST_ALLOC)
+ assert big == big2 # reused slot
+ self.abort_transaction()
+
+
+
def test_inevitable_transaction_has_priority(self):
self.start_transaction()
assert self.is_inevitable() == 0
_______________________________________________
pypy-commit mailing list
[email protected]
https://mail.python.org/mailman/listinfo/pypy-commit