[pypy-svn] r65752 - in pypy/branch/pyjitpl5/pypy: jit/backend/x86 rpython/memory rpython/memory/gctransform rpython/memory/test

arigo at codespeak.net arigo at codespeak.net
Fri Jun 12 19:23:31 CEST 2009


Author: arigo
Date: Fri Jun 12 19:23:30 2009
New Revision: 65752

Modified:
   pypy/branch/pyjitpl5/pypy/jit/backend/x86/gc.py
   pypy/branch/pyjitpl5/pypy/rpython/memory/gctransform/framework.py
   pypy/branch/pyjitpl5/pypy/rpython/memory/gctypelayout.py
   pypy/branch/pyjitpl5/pypy/rpython/memory/test/test_transformed_gc.py
Log:
(pedronis, arigo)
A fix -- including a test, for once -- for pushing and popping roots
around the direct_call introduced by llop.do_malloc_xxx_clear().


Modified: pypy/branch/pyjitpl5/pypy/jit/backend/x86/gc.py
==============================================================================
--- pypy/branch/pyjitpl5/pypy/jit/backend/x86/gc.py	(original)
+++ pypy/branch/pyjitpl5/pypy/jit/backend/x86/gc.py	Fri Jun 12 19:23:30 2009
@@ -282,8 +282,7 @@
         # make a TransformerLayoutBuilder and save it on the translator
         # where it can be fished and reused by the FrameworkGCTransformer
         self.layoutbuilder = framework.TransformerLayoutBuilder()
-        self.layoutbuilder._pending_type_shapes = []
-        self.layoutbuilder.can_encode_type_shape = False
+        self.layoutbuilder.delay_encoding()
         self.translator._jit2gc = {
             'layoutbuilder': self.layoutbuilder,
             'gcmapstart': lambda: gcrootmap.gcmapstart(),

Modified: pypy/branch/pyjitpl5/pypy/rpython/memory/gctransform/framework.py
==============================================================================
--- pypy/branch/pyjitpl5/pypy/rpython/memory/gctransform/framework.py	(original)
+++ pypy/branch/pyjitpl5/pypy/rpython/memory/gctransform/framework.py	Fri Jun 12 19:23:30 2009
@@ -611,22 +611,26 @@
         op = hop.spaceop
         [v_typeid, v_size, v_can_collect,
          v_has_finalizer, v_contains_weakptr] = op.args
+        livevars = self.push_roots(hop)
         hop.genop("direct_call",
                   [self.malloc_fixedsize_clear_ptr, self.c_const_gc,
                    v_typeid, v_size, v_can_collect,
                    v_has_finalizer, v_contains_weakptr],
                   resultvar=op.result)
+        self.pop_roots(hop, livevars)
 
     def gct_do_malloc_varsize_clear(self, hop):
         # used by the JIT (see the x86 backend)
         op = hop.spaceop
         [v_typeid, v_length, v_size, v_itemsize,
          v_offset_to_length, v_can_collect, v_has_finalizer] = op.args
+        livevars = self.push_roots(hop)
         hop.genop("direct_call",
                   [self.malloc_varsize_clear_ptr, self.c_const_gc,
                    v_typeid, v_length, v_size, v_itemsize,
                    v_offset_to_length, v_can_collect, v_has_finalizer],
                   resultvar=op.result)
+        self.pop_roots(hop, livevars)
 
     def gct_get_write_barrier_failing_case(self, hop):
         op = hop.spaceop

Modified: pypy/branch/pyjitpl5/pypy/rpython/memory/gctypelayout.py
==============================================================================
--- pypy/branch/pyjitpl5/pypy/rpython/memory/gctypelayout.py	(original)
+++ pypy/branch/pyjitpl5/pypy/rpython/memory/gctypelayout.py	Fri Jun 12 19:23:30 2009
@@ -242,6 +242,11 @@
                 encode_type_shape(self, info, TYPE)
             del self._pending_type_shapes
 
+    def delay_encoding(self):
+        # used by the JIT
+        self._pending_type_shapes = []
+        self.can_encode_type_shape = False
+
     def offsets2table(self, offsets, TYPE):
         if len(offsets) == 0:
             TYPE = lltype.Void    # we can share all zero-length arrays

Modified: pypy/branch/pyjitpl5/pypy/rpython/memory/test/test_transformed_gc.py
==============================================================================
--- pypy/branch/pyjitpl5/pypy/rpython/memory/test/test_transformed_gc.py	(original)
+++ pypy/branch/pyjitpl5/pypy/rpython/memory/test/test_transformed_gc.py	Fri Jun 12 19:23:30 2009
@@ -41,7 +41,7 @@
     GC_CANNOT_MALLOC_NONMOVABLE = False
 
     def runner(self, f, nbargs=0, statistics=False, transformer=False,
-               **extraconfigopts):
+               mixlevelstuff=None, **extraconfigopts):
         if nbargs == 2:
             def entrypoint(args):
                 x = args[0]
@@ -62,6 +62,8 @@
         t = rtype(entrypoint, [s_args], gcname=self.gcname,
                                         stacklessgc=self.stacklessgc,
                                         **extraconfigopts)
+        if mixlevelstuff:
+            mixlevelstuff(t)
         cbuild = CStandaloneBuilder(t, entrypoint, config=t.config,
                                     gcpolicy=self.gcpolicy)
         db = cbuild.generate_graphs_for_llinterp()
@@ -560,6 +562,47 @@
         run = self.runner(f)
         run([])
 
+    def test_do_malloc_operations(self):
+        P = lltype.GcStruct('P', ('x', lltype.Signed))
+        def g():
+            r = lltype.malloc(P)
+            r.x = 1
+            p = llop.do_malloc_fixedsize_clear(llmemory.GCREF)  # placeholder
+            p = lltype.cast_opaque_ptr(lltype.Ptr(P), p)
+            p.x = r.x
+            return p.x
+        def f():
+            q = lltype.malloc(P)
+            q.x = 0
+            i = 0
+            while i < 40:
+                g()
+                i += 1
+        def fix_graph_of_g(translator):
+            from pypy.translator.translator import graphof
+            from pypy.objspace.flow.model import Constant
+            layoutbuilder = framework.TransformerLayoutBuilder()
+            layoutbuilder.delay_encoding()
+            translator._jit2gc = {
+                'layoutbuilder': layoutbuilder,
+                }
+            type_id = layoutbuilder.get_type_id(P)
+            #
+            # now fix the do_malloc_fixedsize_clear in the graph of g
+            graph = graphof(translator, g)
+            for op in graph.startblock.operations:
+                if op.opname == 'do_malloc_fixedsize_clear':
+                    op.args = [Constant(type_id, lltype.Signed),
+                               Constant(llmemory.sizeof(P), lltype.Signed),
+                               Constant(True, lltype.Bool),  # can_collect
+                               Constant(False, lltype.Bool), # has_finalizer
+                               Constant(False, lltype.Bool)] # contains_weakptr
+                    break
+            else:
+                assert 0, "oups, not found"
+        run = self.runner(f, mixlevelstuff=fix_graph_of_g)
+        run([])
+
 class TestMarkSweepGC(GenericGCTests):
     gcname = "marksweep"
     class gcpolicy(gc.FrameworkGcPolicy):



More information about the Pypy-commit mailing list