[pypy-svn] r27380 - in pypy/dist/pypy/rpython/memory: . test

pedronis at codespeak.net pedronis at codespeak.net
Thu May 18 02:12:15 CEST 2006


Author: pedronis
Date: Thu May 18 02:12:13 2006
New Revision: 27380

Modified:
   pypy/dist/pypy/rpython/memory/gc.py
   pypy/dist/pypy/rpython/memory/gcheader.py
   pypy/dist/pypy/rpython/memory/gclltype.py
   pypy/dist/pypy/rpython/memory/gcwrapper.py
   pypy/dist/pypy/rpython/memory/test/test_gc.py
   pypy/dist/pypy/rpython/memory/test/test_transformed_gc.py
Log:
ah ah. too funny.

started working on making the semispace gc tested with the transformer. tried to use test_gc to see
if I broke something. there were some perplexing problems, discovered that the maze of setup and teardown
in test_gc made it so that mark and sweep was not tested by it at all anymore and it shared some
of the tweaked semispace problems. ah ah, that's why no prints.
of course mark and sweep was broken in test_gc: gcwrapper trying to annotate the __init__ which is not rpython
anymore, to shallow typos, to the os.write and strings requiring in theory that the gc function graphs
be converted too.

after quite a bit of pushing and pulling test_gc is testing successfully mark and sweep again. 
Of course accumulated more reasons for wanting to kill it and gcwrapper.

ah ah. too funny. not much progress on the semispace transformer testing tough :(



Modified: pypy/dist/pypy/rpython/memory/gc.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/gc.py	(original)
+++ pypy/dist/pypy/rpython/memory/gc.py	Thu May 18 02:12:13 2006
@@ -15,9 +15,8 @@
 class GCError(Exception):
     pass
 
-def get_dummy_annotate(gc_class, AddressLinkedList):
+def get_dummy_annotate(gc, AddressLinkedList):
     def dummy_annotate():
-        gc = gc_class(AddressLinkedList)
         gc.setup()
         gc.get_roots = dummy_get_roots1 #prevent the get_roots attribute to 
         gc.get_roots = dummy_get_roots2 #be constants
@@ -99,7 +98,8 @@
     def init_gc_object(self, addr, typeid):
         return
     init_gc_object_immortal = init_gc_object
-   
+
+DEBUG_PRINT = True
 
 class MarkSweepGC(GCBase):
     _alloc_flavor_ = "raw"
@@ -133,7 +133,7 @@
             ref = self.malloc_fixedsize(typeid, size, True)
         # XXX lots of cast and reverse-cast around, but this malloc()
         # should eventually be killed
-        return lltype.cast_ptr_to_adr(ref)
+        return llmemory.cast_ptr_to_adr(ref)
 
     def malloc_fixedsize(self, typeid, size, can_collect):
         if can_collect and self.bytes_malloced > self.bytes_malloced_threshold:
@@ -171,7 +171,8 @@
 
     def collect(self):
         import os, time
-        os.write(2, 'collecting...\n')
+        if DEBUG_PRINT:
+            os.write(2, 'collecting...\n')
         start_time = time.time()
         roots = self.get_roots()
         size_gc_header = self.gcheaderbuilder.size_gc_header
@@ -253,16 +254,17 @@
         self.total_collection_time += end_time - start_time
         # warning, the following debug print allocates memory to manipulate
         # the strings!  so it must be at the end
-        os.write(2, "  malloced since previous collection: %s bytes\n" %
-                 old_malloced)
-        os.write(2, "  heap usage at start of collection:  %s bytes\n" %
-                 (self.heap_usage + old_malloced))
-        os.write(2, "  freed:                              %s bytes\n" %
-                 freed_size)
-        os.write(2, "  new heap usage:                     %s bytes\n" %
-                 curr_heap_size)
-        os.write(2, "  total time spent collecting:        %s seconds\n" %
-                 self.total_collection_time)
+        if DEBUG_PRINT:
+            os.write(2, "  malloced since previous collection: %s bytes\n" %
+                     old_malloced)
+            os.write(2, "  heap usage at start of collection:  %s bytes\n" %
+                     (self.heap_usage + old_malloced))
+            os.write(2, "  freed:                              %s bytes\n" %
+                     freed_size)
+            os.write(2, "  new heap usage:                     %s bytes\n" %
+                     curr_heap_size)
+            os.write(2, "  total time spent collecting:        %s seconds\n" %
+                     self.total_collection_time)
         assert self.heap_usage + old_malloced == curr_heap_size + freed_size
         self.heap_usage = curr_heap_size
 
@@ -282,6 +284,9 @@
 class SemiSpaceGC(GCBase):
     _alloc_flavor_ = "raw"
 
+    HDR = lltype.Struct('header', ('forw', lltype.Signed),
+                                  ('typeid', lltype.Signed))
+
     def __init__(self, AddressLinkedList, space_size=1024*int_size,
                  get_roots=None):
         self.bytes_malloced = 0
@@ -291,6 +296,7 @@
         self.fromspace = NULL
         self.free = NULL
         self.get_roots = get_roots
+        self.gcheaderbuilder = GCHeaderBuilder(self.HDR)
 
     def setup(self):
         self.tospace = raw_malloc(self.space_size)
@@ -308,9 +314,20 @@
     def malloc(self, typeid, length=0):
         size = self.fixed_size(typeid)
         if self.is_varsize(typeid):
-            size += length * self.varsize_item_sizes(typeid)
-        totalsize = size + self.size_gc_header()
-        if self.free + totalsize > self.top_of_space:
+            itemsize = self.varsize_item_sizes(typeid)
+            offset_to_length = self.varsize_offset_to_length(typeid)
+            ref = self.malloc_varsize(typeid, length, size, itemsize,
+                                      offset_to_length, True)
+        else:
+            ref = self.malloc_fixedsize(typeid, size, True)
+        # XXX lots of cast and reverse-cast around, but this malloc()
+        # should eventually be killed
+        return llmemory.cast_ptr_to_adr(ref)
+    
+    def malloc_fixedsize(self, typeid, size, can_collect):
+        size_gc_header = self.gcheaderbuilder.size_gc_header
+        totalsize = size_gc_header + size
+        if can_collect and self.free + totalsize > self.top_of_space:
             self.collect()
             #XXX need to increase the space size if the object is too big
             #for bonus points do big objects differently
@@ -318,9 +335,30 @@
                 raise MemoryError
         result = self.free
         self.init_gc_object(result, typeid)
-##         print "mallocing %s, size %s at %s" % (typeid, size, result)
         self.free += totalsize
-        return result + self.size_gc_header()
+        return llmemory.cast_adr_to_ptr(result+size_gc_header, llmemory.GCREF)
+
+    def malloc_varsize(self, typeid, length, size, itemsize, offset_to_length,
+                       can_collect):
+        try:
+            varsize = rarithmetic.ovfcheck(itemsize * length)
+        except OverflowError:
+            raise MemoryError
+        # XXX also check for overflow on the various '+' below!
+        size += varsize
+        size_gc_header = self.gcheaderbuilder.size_gc_header
+        totalsize = size_gc_header + size
+        if can_collect and self.free + totalsize > self.top_of_space:
+            self.collect()
+            #XXX need to increase the space size if the object is too big
+            #for bonus points do big objects differently
+            if self.free + totalsize > self.top_of_space:
+                raise MemoryError
+        result = self.free
+        self.init_gc_object(result, typeid)
+        (result + size_gc_header + offset_to_length).signed[0] = length
+        self.free += totalsize
+        return llmemory.cast_adr_to_ptr(result+size_gc_header, llmemory.GCREF)
 
     def collect(self):
 ##         print "collecting"
@@ -414,9 +452,8 @@
             size += length * self.varsize_item_sizes(typeid)
         return size
 
-
     def size_gc_header(self, typeid=0):
-        return gc_header_two_ints
+        return self.gcheaderbuilder.size_gc_header
 
     def init_gc_object(self, addr, typeid):
         addr.signed[0] = 0

Modified: pypy/dist/pypy/rpython/memory/gcheader.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/gcheader.py	(original)
+++ pypy/dist/pypy/rpython/memory/gcheader.py	Thu May 18 02:12:13 2006
@@ -5,6 +5,7 @@
 class GCHeaderBuilder(object):
 
     def __init__(self, HDR):
+        """NOT_RPYTHON"""
         self.HDR = HDR
         self.obj2header = weakref.WeakKeyDictionary()
         self.header2obj = weakref.WeakKeyDictionary()

Modified: pypy/dist/pypy/rpython/memory/gclltype.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/gclltype.py	(original)
+++ pypy/dist/pypy/rpython/memory/gclltype.py	Thu May 18 02:12:13 2006
@@ -5,6 +5,9 @@
 from pypy.rpython.memory.lltypesimulation import pyobjectptr
 from pypy.rpython.memory.lladdress import raw_malloc, raw_free, raw_memcopy
 
+def raw_malloc_usage(sz):
+    return sz
+
 def notimplemented(*args, **kwargs):
     raise NotImplemented
 

Modified: pypy/dist/pypy/rpython/memory/gcwrapper.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/gcwrapper.py	(original)
+++ pypy/dist/pypy/rpython/memory/gcwrapper.py	Thu May 18 02:12:13 2006
@@ -13,8 +13,10 @@
         self.types = []
         self.type_to_typeid = {}
 
-    def get_typeid(self, TYPE):
+    def get_typeid(self, TYPE, nonewtype=False):
         if TYPE not in self.type_to_typeid:
+            if nonewtype:
+                raise Exception, "unknown type: %s" % TYPE
             index = len(self.types)
             self.type_to_typeid[TYPE] = index
             self.types.append(TYPE)
@@ -23,6 +25,7 @@
         return typeid
 
     def create_query_functions(self):
+        from pypy.rpython.lltypesystem import rstr
         _is_varsize = []
         _offsets_to_gc_pointers = []
         _fixed_size = []
@@ -193,7 +196,7 @@
 
 
     def get_arg_malloc(self, TYPE, size=0):
-        typeid = self.query_types.get_typeid(TYPE)
+        typeid = self.query_types.get_typeid(TYPE, nonewtype=True)
         return [typeid, size]
 
     def get_funcptr_malloc(self):
@@ -274,13 +277,13 @@
         def instantiate_linked_list():
             return AddressLinkedList()
         f1, f2, f3, f4, f5, f6, f7 = self.query_types.create_query_functions()
+        the_gc = gc_class(AddressLinkedList)
         def instantiate_gc():
-            gc = gc_class(AddressLinkedList)
-            gc.set_query_functions(f1, f2, f3, f4, f5, f6, f7)
-            gc.setup()
-            return gc
+            the_gc.set_query_functions(f1, f2, f3, f4, f5, f6, f7)
+            the_gc.setup()
+            return the_gc
         func, dummy_get_roots1, dummy_get_roots2 = gc.get_dummy_annotate(
-            self.gc.__class__, self.AddressLinkedList)
+            the_gc, self.AddressLinkedList)
         self.gc.get_roots = dummy_get_roots1
         a = RPythonAnnotator()
         a.build_types(instantiate_gc, [])
@@ -316,7 +319,7 @@
 ##         a.translator.view()
 
     def get_arg_malloc(self, TYPE, size=0):
-        typeid = self.query_types.get_typeid(TYPE)
+        typeid = self.query_types.get_typeid(TYPE, nonewtype=True)
         return [self.gcptr, typeid, size]
 
     def get_funcptr_malloc(self):

Modified: pypy/dist/pypy/rpython/memory/test/test_gc.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/test/test_gc.py	(original)
+++ pypy/dist/pypy/rpython/memory/test/test_gc.py	Thu May 18 02:12:13 2006
@@ -25,20 +25,21 @@
     py.log.setconsumer("llinterp", py.log.STDOUT)
     py.log.setconsumer("llinterp frame", stdout_ignore_ll_functions)
     py.log.setconsumer("llinterp operation", None)
-    gclltype.prepare_graphs_and_create_gc = gclltype.create_gc
 
-def teardown_module(mod):
-    gclltype.prepare_graphs_and_create_gc = gclltype.create_no_gc
 
-class TestMarkSweepGC(object):
-    def setup_class(cls):
-        cls.prep_old = gclltype.prepare_graphs_and_create_gc
-        cls.old = gclltype.use_gc
-        gclltype.use_gc = MarkSweepGC
+class GCTest(object):
 
+    def setup_class(cls):
+        gclltype.prepare_graphs_and_create_gc = gclltype.create_gc
+        gclltype.use_gc = cls.GCClass
+        from pypy.rpython.memory import gc as gcimpl
+        gcimpl.DEBUG_PRINT = False
+        
     def teardown_class(cls):
-        gclltype.prepare_graphs_and_create_gc = cls.prep_old.im_func
-        gclltype.use_gc = cls.old
+        gclltype.prepare_graphs_and_create_gc =  gclltype.create_no_gc
+        gclltype.use_gc = MarkSweepGC
+        from pypy.rpython.memory import gc as gcimpl
+        gcimpl.DEBUG_PRINT = True
 
     def test_llinterp_lists(self):
         curr = simulator.current_size
@@ -93,65 +94,30 @@
         assert res == concat(100)
         assert simulator.current_size - curr < 16000 * INT_SIZE / 4
 
-class TestMarkSweepGCRunningOnLLinterp(TestMarkSweepGC):
-    def setup_class(cls):
-        cls.prep_old = gclltype.prepare_graphs_and_create_gc
-        gclltype.prepare_graphs_and_create_gc = gclltype.create_gc_run_on_llinterp
-    def teardown_class(cls):
-        gclltype.prepare_graphs_and_create_gc = cls.prep_old.im_func
 
-class TestSemiSpaceGC(TestMarkSweepGC):
-    def setup_class(cls):
-        gclltype.use_gc = SemiSpaceGC
-        cls.old = gclltype.use_gc
-    def teardown_class(cls):
-        gclltype.use_gc = cls.old
+class GCTestOnLLInterp(GCTest):
 
-class TestSemiSpaceGCRunningOnLLinterp(TestMarkSweepGC):
     def setup_class(cls):
-        cls.prep_old = gclltype.prepare_graphs_and_create_gc
         gclltype.prepare_graphs_and_create_gc = gclltype.create_gc_run_on_llinterp
-        gclltype.use_gc = SemiSpaceGC
-        cls.old = gclltype.use_gc
-
-    def teardown_class(cls):
-        gclltype.prepare_graphs_and_create_gc = cls.prep_old.im_func
-        gclltype.use_gc = cls.old
+        gclltype.use_gc = cls.GCClass
+        from pypy.rpython.memory import gc as gcimpl
+        gcimpl.DEBUG_PRINT = False
 
-class TestDeferredRefcountingGC(TestMarkSweepGC):
-    def setup_class(cls):
-        gclltype.use_gc = DeferredRefcountingGC
-        cls.old = gclltype.use_gc
-    def teardown_class(cls):
-        gclltype.use_gc = cls.old
+class TestMarkSweepGC(GCTest):
+    GCClass = MarkSweepGC
 
+class TestMarkSweepGCRunningOnLLinterp(GCTestOnLLInterp):
+    GCClass = MarkSweepGC
 
-class TestDeferredRefcountingGCRunningOnLLinterp(TestMarkSweepGC):
-    def setup_class(cls):
-        cls.prep_old = gclltype.prepare_graphs_and_create_gc
-        gclltype.prepare_graphs_and_create_gc = gclltype.create_gc_run_on_llinterp
-        gclltype.use_gc = DeferredRefcountingGC
-        cls.old = gclltype.use_gc
+class TestSemiSpaceGC(GCTest):
+    GCClass = SemiSpaceGC
 
-    def teardown_class(cls):
-        gclltype.prepare_graphs_and_create_gc = cls.prep_old.im_func
-        gclltype.use_gc = cls.old
+class TestSemiSpaceGCRunningOnLLinterp(GCTestOnLLInterp):
+    GCClass = SemiSpaceGC
 
-class TestDummyGC(TestMarkSweepGC):
-    def setup_class(cls):
-        gclltype.use_gc = DummyGC
-        cls.old = gclltype.use_gc
-    def teardown_class(cls):
-        gclltype.use_gc = cls.old
+class TestDeferredRefcountingGC(GCTest):
+    GCClass = DeferredRefcountingGC
 
-class TestDummyGCRunningOnLLinterp(TestMarkSweepGC):
-    def setup_class(cls):
-        cls.prep_old = gclltype.prepare_graphs_and_create_gc
-        gclltype.prepare_graphs_and_create_gc = gclltype.create_gc_run_on_llinterp
-        gclltype.use_gc = DummyGC
-        cls.old = gclltype.use_gc
-
-    def teardown_class(cls):
-        gclltype.prepare_graphs_and_create_gc = cls.prep_old.im_func
-        gclltype.use_gc = cls.old
+class TestDeferredRefcountingGCRunningOnLLinterp(GCTestOnLLInterp):
+    GCClass = DeferredRefcountingGC
 

Modified: pypy/dist/pypy/rpython/memory/test/test_transformed_gc.py
==============================================================================
--- pypy/dist/pypy/rpython/memory/test/test_transformed_gc.py	(original)
+++ pypy/dist/pypy/rpython/memory/test/test_transformed_gc.py	Thu May 18 02:12:13 2006
@@ -298,3 +298,13 @@
     class gcpolicy(gc.StacklessFrameworkGcPolicy):
         class transformerclass(gctransform.StacklessFrameworkGCTransformer):
             GC_PARAMS = {'start_heap_size': 4096 }
+
+class TestSemiSpaceGC(TestMarkSweepGC):
+
+    def setup_class(cls):
+        py.test.skip("in-progress")
+
+    class gcpolicy(gc.StacklessFrameworkGcPolicy):
+        class transformerclass(gctransform.FrameworkGCTransformer):
+            from pypy.rpython.memory.gc import SemiSpaceGC as GCClass
+            GC_PARAMS = {'space_size': 4096 }



More information about the Pypy-commit mailing list