Author: Maciej Fijalkowski <fij...@gmail.com> Branch: optresult Changeset: r77911:d217ec5f41a7 Date: 2015-06-05 16:35 +0200 http://bitbucket.org/pypy/pypy/changeset/d217ec5f41a7/
Log: an attempt to make heapcache use new mechanism of tracking stuff diff --git a/rpython/jit/metainterp/compile.py b/rpython/jit/metainterp/compile.py --- a/rpython/jit/metainterp/compile.py +++ b/rpython/jit/metainterp/compile.py @@ -129,6 +129,8 @@ metainterp_sd = metainterp.staticdata jitdriver_sd = metainterp.jitdriver_sd history = metainterp.history + forget_optimization_info(inputargs) + forget_optimization_info(history.operations) enable_opts = jitdriver_sd.warmstate.enable_opts if try_disabling_unroll: @@ -905,6 +907,8 @@ # # Attempt to use optimize_bridge(). This may return None in case # it does not work -- i.e. none of the existing old_loop_tokens match. + forget_optimization_info(metainterp.history.inputargs) + forget_optimization_info(metainterp.history.operations) new_trace = create_empty_loop(metainterp) new_trace.inputargs = metainterp.history.inputargs[:] diff --git a/rpython/jit/metainterp/heapcache.py b/rpython/jit/metainterp/heapcache.py --- a/rpython/jit/metainterp/heapcache.py +++ b/rpython/jit/metainterp/heapcache.py @@ -1,4 +1,4 @@ -from rpython.jit.metainterp.history import ConstInt +from rpython.jit.metainterp.history import Const, ConstInt from rpython.jit.metainterp.resoperation import rop, OpHelpers class HeapCacheValue(object): @@ -62,11 +62,19 @@ class HeapCache(object): def __init__(self): - self.reset() + self.list_of_operations = [] + self._reset(None) def reset(self): + self._reset(self.list_of_operations) + + def _reset(self, lst): + if lst is not None: + for i in range(len(lst)): + lst[i].set_forwarded(None) + self.const_cache = {} # maps boxes to values - self.values = {} + #self.values = {} # store the boxes that contain newly allocated objects, this maps the # boxes to a bool, the bool indicates whether or not the object has # escaped the trace or not (True means the box never escaped, False @@ -93,16 +101,29 @@ self.heap_array_cache = {} def reset_keep_likely_virtuals(self): - for value in self.values.itervalues(): - value.reset_keep_likely_virtual() + for elem in self.list_of_operations: + value = self.getvalue(elem, False) + if value is not None: + assert isinstance(value, HeapCacheValue) + value.reset_keep_likely_virtual() self.heap_cache = {} self.heap_array_cache = {} - def getvalue(self, box): - value = self.values.get(box, None) - if not value: - value = self.values[box] = HeapCacheValue(box) - return value + def getvalue(self, box, create=True): + if isinstance(box, Const): + v = self.const_cache.get(box, None) + if v is None: + self.const_cache[box] = v = HeapCacheValue(box) + return v + v = box.get_forwarded() + if v is None: + if not create: + return None + v = HeapCacheValue(box) + self.list_of_operations.append(box) + box.set_forwarded(v) + assert isinstance(v, HeapCacheValue) + return v def getvalues(self, boxes): return [self.getvalue(box) for box in boxes] @@ -158,7 +179,7 @@ self._escape_box(box) def _escape_box(self, box): - value = self.values.get(box, None) + value = self.getvalue(box, False) if not value: return self._escape(value) @@ -267,31 +288,31 @@ self.reset_keep_likely_virtuals() def is_class_known(self, box): - value = self.values.get(box, None) - if value: - return value.known_class + v = self.getvalue(box, False) + if v: + return v.known_class return False def class_now_known(self, box): self.getvalue(box).known_class = True def is_nonstandard_virtualizable(self, box): - value = self.values.get(box, None) - if value: - return value.nonstandard_virtualizable + v = self.getvalue(box, False) + if v: + return v.nonstandard_virtualizable return False def nonstandard_virtualizables_now_known(self, box): self.getvalue(box).nonstandard_virtualizable = True def is_unescaped(self, box): - value = self.values.get(box, None) + value = self.getvalue(box, False) if value: return value.is_unescaped return False def is_likely_virtual(self, box): - value = self.values.get(box, None) + value = self.getvalue(box, False) if value: return value.likely_virtual return False @@ -307,11 +328,11 @@ self.arraylen_now_known(box, lengthbox) def getfield(self, box, descr): - value = self.values.get(box, None) - if value: + v = self.getvalue(box, False) + if v: cache = self.heap_cache.get(descr, None) if cache: - tovalue = cache.read(value) + tovalue = cache.read(v) if tovalue: return tovalue.box return None @@ -335,7 +356,7 @@ def getarrayitem(self, box, indexbox, descr): if not isinstance(indexbox, ConstInt): return None - value = self.values.get(box, None) + value = self.getvalue(box, False) if value is None: return None index = indexbox.getint() @@ -379,7 +400,7 @@ indexcache.do_write_with_aliasing(value, fieldvalue) def arraylen(self, box): - value = self.values.get(box, None) + value = self.getvalue(box, False) if value and value.length: return value.length.box return None @@ -389,8 +410,11 @@ value.length = self.getvalue(lengthbox) def replace_box(self, oldbox, newbox): - value = self.values.get(oldbox, None) + value = self.getvalue(oldbox, False) if value is None: return value.box = newbox - self.values[newbox] = value + if isinstance(newbox, Const): + self.const_cache[newbox] = value + else: + newbox.set_forwarded(value) diff --git a/rpython/jit/metainterp/pyjitpl.py b/rpython/jit/metainterp/pyjitpl.py --- a/rpython/jit/metainterp/pyjitpl.py +++ b/rpython/jit/metainterp/pyjitpl.py @@ -1907,6 +1907,7 @@ self.current_call_id = 0 def retrace_needed(self, trace, exported_state): + raise Exception("I dont want that function to exist") self.partial_trace = trace self.retracing_from = len(self.history.operations) - 1 self.exported_state = exported_state diff --git a/rpython/jit/metainterp/test/test_heapcache.py b/rpython/jit/metainterp/test/test_heapcache.py --- a/rpython/jit/metainterp/test/test_heapcache.py +++ b/rpython/jit/metainterp/test/test_heapcache.py @@ -2,14 +2,6 @@ from rpython.jit.metainterp.resoperation import rop, InputArgInt from rpython.jit.metainterp.history import ConstInt, BasicFailDescr -box1 = "box1" -box2 = "box2" -box3 = "box3" -box4 = "box4" -box5 = "box5" -lengthbox1 = object() -lengthbox2 = object() -lengthbox3 = object() descr1 = object() descr2 = object() descr3 = object() @@ -58,29 +50,37 @@ class TestHeapCache(object): def test_known_class_box(self): h = HeapCache() - assert not h.is_class_known(1) - assert not h.is_class_known(2) - h.class_now_known(1) - assert h.is_class_known(1) - assert not h.is_class_known(2) + i0 = InputArgInt(1) + i1 = InputArgInt(2) + assert not h.is_class_known(i0) + assert not h.is_class_known(i1) + h.class_now_known(i0) + assert h.is_class_known(i0) + assert not h.is_class_known(i1) h.reset() - assert not h.is_class_known(1) - assert not h.is_class_known(2) + assert not h.is_class_known(i0) + assert not h.is_class_known(i1) def test_nonstandard_virtualizable(self): h = HeapCache() - assert not h.is_nonstandard_virtualizable(1) - assert not h.is_nonstandard_virtualizable(2) - h.nonstandard_virtualizables_now_known(1) - assert h.is_nonstandard_virtualizable(1) - assert not h.is_nonstandard_virtualizable(2) + i0 = InputArgInt(1) + i1 = InputArgInt(2) + assert not h.is_nonstandard_virtualizable(i0) + assert not h.is_nonstandard_virtualizable(i1) + h.nonstandard_virtualizables_now_known(i0) + assert h.is_nonstandard_virtualizable(i0) + assert not h.is_nonstandard_virtualizable(i1) h.reset() - assert not h.is_nonstandard_virtualizable(1) - assert not h.is_nonstandard_virtualizable(2) + assert not h.is_nonstandard_virtualizable(i0) + assert not h.is_nonstandard_virtualizable(i1) def test_heapcache_fields(self): + + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) h = HeapCache() assert h.getfield(box1, descr1) is None assert h.getfield(box1, descr2) is None @@ -105,6 +105,11 @@ def test_heapcache_read_fields_multiple(self): h = HeapCache() + + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) h.getfield_now_known(box1, descr1, box2) h.getfield_now_known(box3, descr1, box4) assert h.getfield(box1, descr1) is box2 @@ -120,6 +125,10 @@ def test_heapcache_write_fields_multiple(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) h.setfield(box1, box2, descr1) assert h.getfield(box1, descr1) is box2 h.setfield(box3, box4, descr1) @@ -148,6 +157,10 @@ def test_heapcache_arrays(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) assert h.getarrayitem(box1, index1, descr1) is None assert h.getarrayitem(box1, index1, descr2) is None assert h.getarrayitem(box1, index2, descr1) is None @@ -190,6 +203,10 @@ def test_heapcache_array_nonconst_index(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) h.setarrayitem(box1, index1, box2, descr1) h.setarrayitem(box1, index2, box4, descr1) assert h.getarrayitem(box1, index1, descr1) is box2 @@ -200,6 +217,10 @@ def test_heapcache_read_fields_multiple_array(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) h.getarrayitem_now_known(box1, index1, box2, descr1) h.getarrayitem_now_known(box3, index1, box4, descr1) assert h.getarrayitem(box1, index1, descr1) is box2 @@ -215,6 +236,10 @@ def test_heapcache_write_fields_multiple_array(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) h.setarrayitem(box1, index1, box2, descr1) assert h.getarrayitem(box1, index1, descr1) is box2 h.setarrayitem(box3, index1, box4, descr1) @@ -243,6 +268,10 @@ def test_length_cache(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + lengthbox1 = InputArgInt(2) + lengthbox2 = InputArgInt(3) h.new_array(box1, lengthbox1) assert h.arraylen(box1) is lengthbox1 @@ -253,6 +282,9 @@ def test_invalidate_cache(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box4 = InputArgInt(3) h.setfield(box1, box2, descr1) h.setarrayitem(box1, index1, box2, descr1) h.setarrayitem(box1, index2, box4, descr1) @@ -286,6 +318,10 @@ def test_replace_box(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) h.setfield(box1, box2, descr1) h.setfield(box1, box3, descr2) h.setfield(box2, box3, descr3) @@ -307,6 +343,11 @@ def test_replace_box_twice(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) + box5 = InputArgInt(4) h.setfield(box1, box2, descr1) h.setfield(box1, box3, descr2) h.setfield(box2, box3, descr3) @@ -330,6 +371,12 @@ def test_replace_box_array(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) + lengthbox1 = InputArgInt(0) + lengthbox2 = InputArgInt(2) h.setarrayitem(box1, index1, box2, descr1) h.setarrayitem(box1, index1, box3, descr2) h.arraylen_now_known(box1, lengthbox1) @@ -349,6 +396,15 @@ def test_replace_box_array_twice(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) + box5 = InputArgInt(4) + lengthbox1 = InputArgInt(0) + lengthbox2 = InputArgInt(1) + lengthbox3 = InputArgInt(2) + h.setarrayitem(box1, index1, box2, descr1) h.setarrayitem(box1, index1, box3, descr2) h.arraylen_now_known(box1, lengthbox1) @@ -370,6 +426,12 @@ def test_ll_arraycopy(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) + box5 = InputArgInt(4) + lengthbox1 = InputArgInt(0) h.new_array(box1, lengthbox1) h.setarrayitem(box1, index1, box2, descr1) h.new_array(box2, lengthbox1) @@ -398,49 +460,68 @@ def test_ll_arraycopy_differing_descrs(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + lengthbox2 = InputArgInt(1) h.setarrayitem(box1, index1, box2, descr2) assert h.getarrayitem(box1, index1, descr2) is box2 h.new_array(box2, lengthbox2) h.invalidate_caches( rop.CALL_N, arraycopydescr1, - [None, box3, box2, index1, index1, index2] + [ConstInt(123), box3, box2, index1, index1, index2] ) assert h.getarrayitem(box1, index1, descr2) is box2 def test_ll_arraycopy_differing_descrs_nonconst_index(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) h.setarrayitem(box1, index1, box2, descr2) assert h.getarrayitem(box1, index1, descr2) is box2 h.invalidate_caches( rop.CALL_N, arraycopydescr1, - [None, box3, box2, index1, index1, InputArgInt()] + [ConstInt(123), box3, box2, index1, index1, InputArgInt()] ) assert h.getarrayitem(box1, index1, descr2) is box2 def test_ll_arraycopy_result_propogated(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) h.setarrayitem(box1, index1, box2, descr1) h.invalidate_caches( rop.CALL_N, arraycopydescr1, - [None, box1, box3, index1, index1, index2] + [ConstInt(13), box1, box3, index1, index1, index2] ) assert h.getarrayitem(box3, index1, descr1) is box2 def test_ll_arraycopy_dest_new(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) + box4 = InputArgInt(3) + lengthbox1 = InputArgInt(0) h.new_array(box1, lengthbox1) h.setarrayitem(box3, index1, box4, descr1) h.invalidate_caches( rop.CALL_N, arraycopydescr1, - [None, box2, box1, index1, index1, index2] + [ConstInt(13), box2, box1, index1, index1, index2] ) def test_ll_arraycopy_doesnt_escape_arrays(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + lengthbox1 = InputArgInt(1) + lengthbox2 = InputArgInt(2) h.new_array(box1, lengthbox1) h.new_array(box2, lengthbox2) h.invalidate_caches( @@ -453,13 +534,15 @@ h.invalidate_caches( rop.CALL_N, arraycopydescr1, - [None, box2, box1, index1, index1, InputArgInt()] + [ConstInt(123), box2, box1, index1, index1, InputArgInt()] ) assert not h.is_unescaped(box1) assert not h.is_unescaped(box2) def test_unescaped(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) assert not h.is_unescaped(box1) h.new(box2) assert h.is_unescaped(box2) @@ -470,6 +553,9 @@ def test_unescaped_testing(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) h.new(box1) h.new(box2) assert h.is_unescaped(box1) @@ -488,6 +574,8 @@ def test_ops_dont_escape(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) h.new(box1) h.new(box2) assert h.is_unescaped(box1) @@ -501,6 +589,9 @@ def test_circular_virtuals(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + box3 = InputArgInt(2) h.new(box1) h.new(box2) h.invalidate_caches(rop.SETFIELD_GC, None, [box1, box2]) @@ -509,6 +600,10 @@ def test_unescaped_array(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + lengthbox1 = InputArgInt(0) + lengthbox2 = InputArgInt(1) h.new_array(box1, lengthbox1) assert h.is_unescaped(box1) h.invalidate_caches(rop.SETARRAYITEM_GC, None, [box1, index1, box2]) @@ -532,6 +627,9 @@ def test_call_doesnt_invalidate_unescaped_boxes(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) + h.new(box1) assert h.is_unescaped(box1) h.setfield(box1, box2, descr1) @@ -543,6 +641,9 @@ def test_call_doesnt_invalidate_unescaped_array_boxes(self): h = HeapCache() + box1 = InputArgInt(0) + lengthbox1 = InputArgInt(2) + box3 = InputArgInt(1) h.new_array(box1, lengthbox1) assert h.is_unescaped(box1) h.setarrayitem(box1, index1, box3, descr1) @@ -554,6 +655,8 @@ def test_bug_missing_ignored_operations(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) h.new(box1) h.new(box2) h.setfield(box1, box2, descr1) @@ -576,6 +679,8 @@ # calling some residual code that changes the values on box3: then # the content of box2 is still cached at the old value. h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) h.new(box1) h.new(box2) h.setfield(box1, box2, descr1) @@ -588,6 +693,8 @@ def test_bug_heap_cache_is_cleared_but_not_is_unescaped_2(self): h = HeapCache() + box1 = InputArgInt(0) + box2 = InputArgInt(1) h.new(box1) h.new(box2) h.setfield(box1, box2, descr1) @@ -609,6 +716,8 @@ def test_is_likely_virtual(self): h = HeapCache() + box1 = InputArgInt(0) + h.new(box1) assert h.is_unescaped(box1) assert h.is_likely_virtual(box1) _______________________________________________ pypy-commit mailing list pypy-commit@python.org https://mail.python.org/mailman/listinfo/pypy-commit