[pypy-commit] pypy gc-del: Port again the changes from default to enable both a destructor and a

arigo noreply at buildbot.pypy.org
Fri Apr 26 19:03:42 CEST 2013


Author: Armin Rigo <arigo at tunes.org>
Branch: gc-del
Changeset: r63657:01e4d6fbc769
Date: 2013-04-26 19:03 +0200
http://bitbucket.org/pypy/pypy/changeset/01e4d6fbc769/

Log:	Port again the changes from default to enable both a destructor and
	a customtrace. Used in gctransform/shadowstack.py.

diff --git a/rpython/memory/gc/minimark.py b/rpython/memory/gc/minimark.py
--- a/rpython/memory/gc/minimark.py
+++ b/rpython/memory/gc/minimark.py
@@ -1949,7 +1949,7 @@
             if not self.is_forwarded(obj):
                 destructor = self.getdestructor(self.get_type_id(obj))
                 ll_assert(bool(destructor), "destructor missing")
-                destructor(obj, NULL)
+                destructor(obj)
             else:
                 obj = self.get_forwarding_address(obj)
                 self.old_objects_with_destructors.append(obj)
@@ -1967,8 +1967,8 @@
             else:
                 # dying
                 destructor = self.getdestructor(self.get_type_id(obj))
-                ll_assert(bool(destructor), "no light finalizer found")
-                destructor(obj, NULL)
+                ll_assert(bool(destructor), "[2] destructor missing")
+                destructor(obj)
         self.old_objects_with_destructors.delete()
         self.old_objects_with_destructors = new_objects
 
diff --git a/rpython/memory/gctransform/framework.py b/rpython/memory/gctransform/framework.py
--- a/rpython/memory/gctransform/framework.py
+++ b/rpython/memory/gctransform/framework.py
@@ -666,9 +666,8 @@
         c_type_id = rmodel.inputconst(TYPE_ID, type_id)
         info = self.layoutbuilder.get_info(type_id)
         c_size = rmodel.inputconst(lltype.Signed, info.fixedsize)
-        kind_and_fptr = self.special_funcptr_for_type(TYPE)
-        has_destructor = (kind_and_fptr is not None and
-                          kind_and_fptr[0] == "destructor")
+        fptrs = self.special_funcptr_for_type(TYPE)
+        has_destructor = "destructor" in fptrs
         c_has_destructor = rmodel.inputconst(lltype.Bool, has_destructor)
 
         if not op.opname.endswith('_varsize') and not flags.get('varsize'):
@@ -1241,15 +1240,16 @@
         destrptr = rtti._obj.destructor_funcptr
         DESTR_ARG = lltype.typeOf(destrptr).TO.ARGS[0]
         typename = TYPE.__name__
-        def ll_destructor(addr, ignored):
+        def ll_destructor(addr):
             v = llmemory.cast_adr_to_ptr(addr, DESTR_ARG)
             ll_call_destructor(destrptr, v, typename)
-            return llmemory.NULL
         fptr = self.transformer.annotate_finalizer(ll_destructor,
-                [llmemory.Address, llmemory.Address], llmemory.Address)
-        g = destrptr._obj.graph
-        # XXX should catch and ignore DelayedPointer here?
-        DestructorAnalyzer(self.translator).check_destructor(g)
+                [llmemory.Address], lltype.Void)
+        try:
+            g = destrptr._obj.graph
+            DestructorAnalyzer(self.translator).check_destructor(g)
+        except lltype.DelayedPointer:
+            pass             # XXX bah, too bad
         return fptr
 
     def make_custom_trace_funcptr_for_type(self, TYPE):
diff --git a/rpython/memory/gctypelayout.py b/rpython/memory/gctypelayout.py
--- a/rpython/memory/gctypelayout.py
+++ b/rpython/memory/gctypelayout.py
@@ -23,16 +23,20 @@
     # A custom tracer (CT), enumerates the addresses that contain GCREFs.
     # It is called with the object as first argument, and the previous
     # returned address (or NULL the first time) as the second argument.
-    DESTRUCTOR_OR_CT_FUNC = lltype.FuncType([llmemory.Address,
-                                            llmemory.Address],
-                                           llmemory.Address)
-    DESTRUCTOR_OR_CT = lltype.Ptr(DESTRUCTOR_OR_CT_FUNC)
-    FINALIZER = lltype.Ptr(lltype.FuncType([llmemory.Address], lltype.Void))
+    DESTRUCTOR_FUNC = lltype.FuncType([llmemory.Address], lltype.Void)
+    CUSTOMTRACER_FUNC = lltype.FuncType([llmemory.Address, llmemory.Address],
+                                        llmemory.Address)
+    DESTRUCTOR = lltype.Ptr(DESTRUCTOR_FUNC)
+    FINALIZER = DESTRUCTOR
+    CUSTOMTRACER = lltype.Ptr(CUSTOMTRACER_FUNC)
+    EXTRA = lltype.Struct("type_info_extra",
+                          ('destructor', DESTRUCTOR),
+                          ('customtracer', CUSTOMTRACER))
 
     # structure describing the layout of a typeid
     TYPE_INFO = lltype.Struct("type_info",
         ("infobits",       lltype.Signed),    # combination of the T_xxx consts
-        ("destructor_or_customtrace", DESTRUCTOR_OR_CT),
+        ("extra",          lltype.Ptr(EXTRA)),
         ("fixedsize",      lltype.Signed),
         ("ofstoptrs",      lltype.Ptr(OFFSETS_TO_GC_PTR)),
         hints={'immutable': True},
@@ -82,9 +86,9 @@
     def q_getdestructor(self, typeid):
         typeinfo = self.get(typeid)
         if typeinfo.infobits & T_HAS_DESTRUCTOR:
-            return typeinfo.destructor_or_customtrace
+            return typeinfo.extra.destructor
         else:
-            return lltype.nullptr(GCData.DESTRUCTOR_OR_CT_FUNC)
+            return lltype.nullptr(GCData.DESTRUCTOR_FUNC)
 
     def q_offsets_to_gc_pointers(self, typeid):
         return self.get(typeid).ofstoptrs
@@ -126,7 +130,7 @@
         ll_assert(self.q_has_custom_trace(typeid),
                   "T_HAS_CUSTOM_TRACE missing")
         typeinfo = self.get(typeid)
-        return typeinfo.destructor_or_customtrace
+        return typeinfo.extra.customtracer
 
     def q_fast_path_tracing(self, typeid):
         # return True if none of the flags T_HAS_GCPTR_IN_VARSIZE,
@@ -224,16 +228,17 @@
     infobits = index
     info.ofstoptrs = builder.offsets2table(offsets, TYPE)
     #
-    kind_and_fptr = builder.special_funcptr_for_type(TYPE)
-    if kind_and_fptr is not None:
-        kind, fptr = kind_and_fptr
-        info.destructor_or_customtrace = fptr
-        if kind == "destructor":
+    fptrs = builder.special_funcptr_for_type(TYPE)
+    if fptrs:
+        extra = lltype.malloc(GCData.EXTRA, zero=True, immortal=True,
+                              flavor='raw')
+        if "destructor" in fptrs:
+            extra.destructor = fptrs["destructor"]
             infobits |= T_HAS_DESTRUCTOR
-        elif kind == "custom_trace":
+        if "custom_trace" in fptrs:
+            extra.customtracer = fptrs["custom_trace"]
             infobits |= T_HAS_CUSTOM_TRACE
-        else:
-            assert 0, kind
+        info.extra = extra
     #
     if not TYPE._is_varsize():
         info.fixedsize = llarena.round_up_for_allocation(
@@ -407,13 +412,11 @@
         fptr2 = self.make_custom_trace_funcptr_for_type(TYPE)
         result = {}
         if fptr1:
-            kind_and_fptr = "destructor", fptr1
-        elif fptr2:
-            kind_and_fptr = "custom_trace", fptr2
-        else:
-            kind_and_fptr = None
-        self._special_funcptrs[TYPE] = kind_and_fptr
-        return kind_and_fptr
+            result["destructor"] = fptr1
+        if fptr2:
+            result["custom_trace"] = fptr2
+        self._special_funcptrs[TYPE] = result
+        return result
 
     def make_destructor_funcptr_for_type(self, TYPE):
         # must be overridden for proper finalizer support
diff --git a/rpython/memory/gcwrapper.py b/rpython/memory/gcwrapper.py
--- a/rpython/memory/gcwrapper.py
+++ b/rpython/memory/gcwrapper.py
@@ -220,16 +220,14 @@
 
         t = self.llinterp.typer.annotator.translator
         DestructorAnalyzer(t).check_destructor(destrgraph)
-        def ll_destructor(addr, dummy):
-            assert dummy == llmemory.NULL
+        def ll_destructor(addr):
             try:
                 v = llmemory.cast_adr_to_ptr(addr, DESTR_ARG)
                 self.llinterp.eval_graph(destrgraph, [v], recursive=True)
             except llinterp.LLException:
                 raise RuntimeError(
                     "a destructor raised an exception, shouldn't happen")
-            return llmemory.NULL
-        return llhelper(gctypelayout.GCData.DESTRUCTOR_OR_CT, ll_destructor)
+        return llhelper(gctypelayout.GCData.DESTRUCTOR, ll_destructor)
 
     def make_custom_trace_funcptr_for_type(self, TYPE):
         from rpython.memory.gctransform.support import get_rtti


More information about the pypy-commit mailing list