Author: Alex Gaynor <[email protected]>
Branch: erase-raw-mem
Changeset: r53409:216539421090
Date: 2012-03-12 21:51 -0700
http://bitbucket.org/pypy/pypy/changeset/216539421090/

Log:    added gc support for untyped stuff via new gc_writebarrier llop

diff --git a/pypy/rpython/memory/gctransform/framework.py 
b/pypy/rpython/memory/gctransform/framework.py
--- a/pypy/rpython/memory/gctransform/framework.py
+++ b/pypy/rpython/memory/gctransform/framework.py
@@ -233,7 +233,7 @@
         # for tests
         self.frameworkgc__teardown_ptr = getfn(frameworkgc__teardown, [],
                                                annmodel.s_None)
-        
+
         if root_walker.need_root_stack:
             self.incr_stack_ptr = getfn(root_walker.incr_stack,
                                        [annmodel.SomeInteger()],
@@ -248,7 +248,7 @@
             self.decr_stack_ptr = None
         self.weakref_deref_ptr = self.inittime_helper(
             ll_weakref_deref, [llmemory.WeakRefPtr], llmemory.Address)
-        
+
         classdef = bk.getuniqueclassdef(GCClass)
         s_gc = annmodel.SomeInstance(classdef)
         s_gcref = annmodel.SomePtr(llmemory.GCREF)
@@ -313,6 +313,13 @@
                 [s_gc, annmodel.SomeInteger(knowntype=llgroup.r_halfword)],
                 annmodel.SomeInteger())
 
+        if hasattr(GCClass, 'write_barrier'):
+            self.wb_ptr = getfn(GCClass.write_barrier.im_func,
+                                [s_gc] + [annmodel.SomeAddress()] * 2,
+                                annmodel.s_None)
+        elif GCClass.needs_write_barrier:
+            raise NotImplementedError("Add a write_barrier")
+
         if hasattr(GCClass, 'writebarrier_before_copy'):
             self.wb_before_copy_ptr = \
                     getfn(GCClass.writebarrier_before_copy.im_func,
@@ -638,7 +645,7 @@
             if self.collect_analyzer.analyze_direct_call(graph):
                 raise Exception("'no_collect' function can trigger collection:"
                                 " %s" % func)
-            
+
         if self.write_barrier_ptr:
             self.clean_sets = (
                 find_initializing_stores(self.collect_analyzer, graph))
@@ -905,6 +912,19 @@
             TYPE = v_ob.concretetype.TO
             gen_zero_gc_pointers(TYPE, v_ob, hop.llops)
 
+    def gct_gc_writebarrier(self, hop):
+        op = hop.spaceop
+        if not hasattr(self, "wb_ptr"):
+            return
+
+        newvalue_addr = hop.genop('cast_ptr_to_adr', [op.args[0]],
+                                  resulttype=llmemory.Address)
+        struct_addr = hop.genop('cast_ptr_to_adr', [op.args[1]],
+                                resulttype=llmemory.Address)
+        hop.genop('direct_call',
+                  [self.wb_ptr, self.c_const_gc, newvalue_addr, struct_addr])
+
+
     def gct_gc_writebarrier_before_copy(self, hop):
         op = hop.spaceop
         if not hasattr(self, 'wb_before_copy_ptr'):
diff --git a/pypy/rpython/memory/gctransform/transform.py 
b/pypy/rpython/memory/gctransform/transform.py
--- a/pypy/rpython/memory/gctransform/transform.py
+++ b/pypy/rpython/memory/gctransform/transform.py
@@ -377,6 +377,9 @@
     def gct_zero_gc_pointers_inside(self, hop):
         pass
 
+    def gct_gc_writebarrier(self, hop):
+        pass
+
     def gct_gc_writebarrier_before_copy(self, hop):
         # We take the conservative default and return False here, meaning
         # that rgc.ll_arraycopy() will do the copy by hand (i.e. with a
@@ -520,11 +523,11 @@
         flags = hop.spaceop.args[1].value
         flavor = flags['flavor']
         meth = getattr(self, 'gct_fv_%s_malloc' % flavor, None)
-        assert meth, "%s has no support for malloc with flavor %r" % (self, 
flavor) 
+        assert meth, "%s has no support for malloc with flavor %r" % (self, 
flavor)
         c_size = rmodel.inputconst(lltype.Signed, llmemory.sizeof(TYPE))
         v_raw = meth(hop, flags, TYPE, c_size)
         hop.cast_result(v_raw)
- 
+
     def gct_fv_raw_malloc(self, hop, flags, TYPE, c_size):
         v_raw = hop.genop("direct_call", [self.raw_malloc_fixedsize_ptr, 
c_size],
                           resulttype=llmemory.Address)
@@ -548,7 +551,7 @@
         flavor = flags['flavor']
         assert flavor != 'cpy', "cannot malloc CPython objects directly"
         meth = getattr(self, 'gct_fv_%s_malloc_varsize' % flavor, None)
-        assert meth, "%s has no support for malloc_varsize with flavor %r" % 
(self, flavor) 
+        assert meth, "%s has no support for malloc_varsize with flavor %r" % 
(self, flavor)
         return self.varsize_malloc_helper(hop, flags, meth, [])
 
     def gct_malloc_nonmovable(self, *args, **kwds):
diff --git a/pypy/rpython/memory/test/test_transformed_gc.py 
b/pypy/rpython/memory/test/test_transformed_gc.py
--- a/pypy/rpython/memory/test/test_transformed_gc.py
+++ b/pypy/rpython/memory/test/test_transformed_gc.py
@@ -13,6 +13,7 @@
 from pypy import conftest
 from pypy.rlib.rstring import StringBuilder
 from pypy.rlib.rarithmetic import LONG_BIT
+from pypy.rlib.rerased_raw import UntypedStorage
 
 WORD = LONG_BIT // 8
 
@@ -834,7 +835,7 @@
             from pypy.translator.translator import graphof
             from pypy.objspace.flow.model import Constant
             from pypy.rpython.lltypesystem import rffi
-            layoutbuilder = cls.ensure_layoutbuilder(translator)            
+            layoutbuilder = cls.ensure_layoutbuilder(translator)
             type_id = layoutbuilder.get_type_id(P)
             #
             # now fix the do_malloc_fixedsize_clear in the graph of g
@@ -928,6 +929,25 @@
         run = self.runner("writebarrier_before_copy")
         run([])
 
+    def define_untyped_storage(cls):
+        class A(object):
+            def __init__(self, v):
+                self.v = v
+
+        def fn():
+            s = UntypedStorage("io")
+            s.setint(0, 10)
+            s.setinstance(1, A(10))
+            rgc.collect()
+            return s.getint(0) + s.getinstance(1, A).v
+        return fn
+
+    def test_untyped_storage(self):
+        run = self.runner("untyped_storage")
+        res = run([])
+        assert res == 20
+
+
 # ________________________________________________________________
 
 class TestMarkSweepGC(GenericGCTests):
@@ -1152,7 +1172,7 @@
 
     def test_adr_of_nursery(self):
         run = self.runner("adr_of_nursery")
-        res = run([])        
+        res = run([])
 
 class TestGenerationalNoFullCollectGC(GCTest):
     # test that nursery is doing its job and that no full collection
diff --git a/pypy/translator/c/test/test_newgc.py 
b/pypy/translator/c/test/test_newgc.py
--- a/pypy/translator/c/test/test_newgc.py
+++ b/pypy/translator/c/test/test_newgc.py
@@ -12,6 +12,7 @@
 from pypy.translator.interactive import Translation
 from pypy.annotation import policy as annpolicy
 from pypy import conftest
+from pypy.rlib.rerased_raw import UntypedStorage
 
 class TestUsingFramework(object):
     gcpolicy = "marksweep"
@@ -80,7 +81,7 @@
                 funcsstr.append(func)
                 funcs0.append(None)
                 funcs1.append(None)
-            else:            
+            else:
                 numargs = len(inspect.getargspec(func)[0])
                 funcsstr.append(None)
                 if numargs == 0:
@@ -1185,6 +1186,24 @@
         assert data.startswith('member0')
         assert 'GcArray of * GcStruct S {' in data
 
+    def define_untyped_storage(cls):
+        class A(object):
+            def __init__(self, v):
+                self.v = v
+
+        def fn():
+            s = UntypedStorage("io")
+            s.setint(0, 10)
+            s.setinstance(1, A(10))
+            rgc.collect()
+            return s.getint(0) + s.getinstance(1, A).v
+        return fn
+
+    def test_untyped_storage(self):
+        res = self.run("untyped_storage")
+        assert res == 20
+
+
 class TestSemiSpaceGC(TestUsingFramework, snippet.SemiSpaceGCTestDefines):
     gcpolicy = "semispace"
     should_be_moving = True
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to