[pypy-svn] r26585 - in pypy/dist/pypy: . translator translator/c translator/goal

cfbolz at codespeak.net cfbolz at codespeak.net
Sat Apr 29 23:31:25 CEST 2006


Author: cfbolz
Date: Sat Apr 29 23:31:23 2006
New Revision: 26585

Modified:
   pypy/dist/pypy/conftest.py
   pypy/dist/pypy/translator/c/database.py
   pypy/dist/pypy/translator/c/gc.py
   pypy/dist/pypy/translator/c/node.py
   pypy/dist/pypy/translator/driver.py
   pypy/dist/pypy/translator/goal/translate.py
Log:
add a new gc policy which tries to give boehm some information which fields of
a structure are pointers. Annoyingly this makes boehm slower :-(. On the other
hand, something like this is needed to make _weakref work on boehm.


Modified: pypy/dist/pypy/conftest.py
==============================================================================
--- pypy/dist/pypy/conftest.py	(original)
+++ pypy/dist/pypy/conftest.py	Sat Apr 29 23:31:23 2006
@@ -43,7 +43,7 @@
                help="view translation tests' flow graphs with Pygame"),
         Option('--gc', action="store", default=None, 
                type="choice", dest="gcpolicy",
-               choices=['ref', 'boehm', 'none', 'framework'],
+               choices=['ref', 'boehm', 'none', 'framework', 'exact_boehm'],
                help="GcPolicy class to use for genc tests"),
     )
 

Modified: pypy/dist/pypy/translator/c/database.py
==============================================================================
--- pypy/dist/pypy/translator/c/database.py	(original)
+++ pypy/dist/pypy/translator/c/database.py	Sat Apr 29 23:31:23 2006
@@ -44,6 +44,8 @@
             if polname is not None:
                 if polname == 'boehm':
                     gcpolicy = gc.BoehmGcPolicy
+                elif polname == 'exact_boehm':
+                    gcpolicy = gc.MoreExactBoehmGcPolicy
                 elif polname == 'ref':
                     gcpolicy = gc.RefcountingGcPolicy
                 elif polname == 'none':

Modified: pypy/dist/pypy/translator/c/gc.py
==============================================================================
--- pypy/dist/pypy/translator/c/gc.py	(original)
+++ pypy/dist/pypy/translator/c/gc.py	Sat Apr 29 23:31:23 2006
@@ -9,7 +9,7 @@
 
 PyObjPtr = Ptr(PyObject)
 
-class BasicGcPolicy:
+class BasicGcPolicy(object):
     
     def __init__(self, db, thread_enabled=False):
         self.db = db
@@ -33,6 +33,9 @@
     def array_gcheader_initdata(self, defnode):
         return self.common_gcheader_initdata(defnode)
 
+    def struct_after_definition(self, defnode):
+        return []
+
     def gc_libraries(self):
         return []
 
@@ -155,6 +158,9 @@
 class BoehmInfo:
     finalizer = None
 
+    # for MoreExactBoehmGcPolicy
+    malloc_exact = False
+
 class BoehmGcPolicy(BasicGcPolicy):
     transformerclass = gctransform.BoehmGCTransformer
 
@@ -250,6 +256,78 @@
     def implementation(self):
         yield 'char %s  /* uninitialized */;' % self.name
 
+
+class MoreExactBoehmGcPolicy(BoehmGcPolicy):
+    """ policy to experiment with giving some layout information to boehm. Use
+    new class to prevent breakage. """
+
+    def __init__(self, db, thread_enabled=False):
+        super(MoreExactBoehmGcPolicy, self).__init__(db, thread_enabled)
+        self.exactly_typed_structs = {}
+
+    def get_descr_name(self, defnode):
+        # XXX somewhat illegal way of introducing a name
+        return '%s__gc_descr__' % (defnode.name, )
+
+    def pre_pre_gc_code(self):
+        for line in super(MoreExactBoehmGcPolicy, self).pre_pre_gc_code():
+            yield line
+        yield "#include <gc/gc_typed.h>"
+
+    def struct_setup(self, structdefnode, rtti):
+        self.setup_gcinfo(structdefnode)
+        T = structdefnode.STRUCT
+        if T._is_varsize():
+            malloc_exact = T._flds[T._arrayfld]._is_atomic()
+        else:
+            malloc_exact = True
+        if malloc_exact:
+            if structdefnode.gcinfo is None:
+                structdefnode.gcinfo = BoehmInfo()
+            structdefnode.gcinfo.malloc_exact = True
+            self.exactly_typed_structs[structdefnode.STRUCT] = structdefnode
+
+    def struct_after_definition(self, defnode):
+        if defnode.gcinfo and defnode.gcinfo.malloc_exact:
+            yield 'GC_descr %s;' % (self.get_descr_name(defnode), )
+
+    def gc_startup_code(self):
+        for line in super(MoreExactBoehmGcPolicy, self).gc_startup_code():
+            yield line
+        for TYPE, defnode in self.exactly_typed_structs.iteritems():
+            T = defnode.gettype().replace("@", "")
+            yield "{"
+            yield "GC_word T_bitmap[GC_BITMAP_SIZE(%s)] = {0};" % (T, )
+            for field in TYPE._flds:
+                if getattr(TYPE, field) == lltype.Void:
+                    continue
+                yield "GC_set_bit(T_bitmap, GC_WORD_OFFSET(%s, %s));" % (
+                    T, defnode.c_struct_field_name(field))
+            yield "%s = GC_make_descriptor(T_bitmap, GC_WORD_LEN(%s));" % (
+                self.get_descr_name(defnode), T)
+            yield "}"
+
+    def zero_malloc(self, TYPE, esize, eresult):
+        defnode = self.db.gettypedefnode(TYPE)
+        gcinfo = defnode.gcinfo
+        if gcinfo:
+            if not gcinfo.malloc_exact:
+                assert TYPE._gcstatus()   # _is_atomic() depends on this!
+                is_atomic = TYPE._is_atomic()
+                is_varsize = TYPE._is_varsize()
+                result = 'OP_BOEHM_ZERO_MALLOC(%s, %s, %d, %d);' % (
+                    esize, eresult, is_atomic, is_varsize)
+            else:
+                result = '%s = GC_MALLOC_EXPLICITLY_TYPED(%s, %s);' % (
+                    eresult, esize, self.get_descr_name(defnode))
+            if gcinfo.finalizer:
+                result += ('\nGC_REGISTER_FINALIZER(%s, (GC_finalization_proc)%s, NULL, NULL, NULL);'
+                       % (eresult, gcinfo.finalizer))
+        else:
+            return super(MoreExactBoehmGcPolicy, self).zero_malloc(
+                TYPE, esize, eresult)
+        return result
+
 # to get an idea how it looks like with no refcount/gc at all
 
 class NoneGcPolicy(BoehmGcPolicy):

Modified: pypy/dist/pypy/translator/c/node.py
==============================================================================
--- pypy/dist/pypy/translator/c/node.py	(original)
+++ pypy/dist/pypy/translator/c/node.py	Sat Apr 29 23:31:23 2006
@@ -117,7 +117,6 @@
             return
         yield 'struct %s {' % self.name
         is_empty = True
-
         for name, typename in self.fields:
             line = '%s;' % cdecl(typename, name)
             if typename == PrimitiveType[Void]:
@@ -128,6 +127,8 @@
         if is_empty:
             yield '\t' + 'int _dummy; /* this struct is empty */'
         yield '};'
+        for line in self.db.gcpolicy.struct_after_definition(self):
+            yield line
 
     def visitor_lines(self, prefix, on_field):
         STRUCT = self.STRUCT

Modified: pypy/dist/pypy/translator/driver.py
==============================================================================
--- pypy/dist/pypy/translator/driver.py	(original)
+++ pypy/dist/pypy/translator/driver.py	Sat Apr 29 23:31:23 2006
@@ -227,6 +227,9 @@
         if opt.gc =='boehm':
             from pypy.translator.c import gc
             gcpolicy = gc.BoehmGcPolicy
+        if opt.gc =='exact_boehm':
+            from pypy.translator.c import gc
+            gcpolicy = gc.MoreExactBoehmGcPolicy
         if opt.gc == 'none':
             from pypy.translator.c import gc
             gcpolicy = gc.NoneGcPolicy

Modified: pypy/dist/pypy/translator/goal/translate.py
==============================================================================
--- pypy/dist/pypy/translator/goal/translate.py	(original)
+++ pypy/dist/pypy/translator/goal/translate.py	Sat Apr 29 23:31:23 2006
@@ -48,7 +48,7 @@
 
     '1_backend': [OPT(('-b', '--backend'), "Backend", ['c', 'llvm', 'cl', 'squeak'])],
 
-    '2_gc': [OPT(('--gc',), "Garbage collector", ['boehm', 'ref', 'framework', 'none'])],
+    '2_gc': [OPT(('--gc',), "Garbage collector", ['boehm', 'ref', 'framework', 'none', 'exact_boehm'])],
     '3_stackless': [OPT(('--stackless',), "Stackless code generation", True)],
     '4_merge_if_blocks': [OPT(('--no-if-blocks-merge',), "Do not merge if ... elif ... chains and use a switch statement for them.", False)],
     },



More information about the Pypy-commit mailing list