[gjs/gnome-3-28] object: properly disassociate wrappers



commit 79cd92c9c73acb0c7605c85896fd1aab5a46a1a3
Author: Georges Basile Stavracas Neto <georges stavracas gmail com>
Date:   Sat Mar 31 18:22:00 2018 -0300

    object: properly disassociate wrappers
    
    Now that we allow different JS wrappers during the lifetime of
    a single GObject, the code must be extra careful to really
    disassociate wrapper and wrapped objects.
    
    The current code, however, was not really disassociating the
    wrapper from the GObject it wraps, causing a segfault when
    the first wrapper is destroyed and the second is created.
    
    (cherry picked from commit 72d970b4d199982979bb879c409f4c08619798e4)

 gi/object.cpp | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)
---
diff --git a/gi/object.cpp b/gi/object.cpp
index a023fe63..4b2ec109 100644
--- a/gi/object.cpp
+++ b/gi/object.cpp
@@ -219,7 +219,7 @@ get_object_qdata(GObject *gobj)
     auto priv = static_cast<ObjectInstance *>(g_object_get_qdata(gobj,
                                                                  gjs_object_priv_quark()));
 
-    if (priv && G_UNLIKELY(priv->js_object_finalized)) {
+    if (priv && priv->uses_toggle_ref && G_UNLIKELY(priv->js_object_finalized)) {
         g_critical("Object %p (a %s) resurfaced after the JS wrapper was finalized. "
                    "This is some library doing dubious memory management inside dispose()",
                    gobj, g_type_name(G_TYPE_FROM_INSTANCE(gobj)));
@@ -1432,11 +1432,16 @@ disassociate_js_gobject(GObject *gobj)
                    gobj, G_OBJECT_TYPE_NAME(gobj));
     }
 
+    /* Fist, remove the wrapper pointer from the wrapped GObject */
+    set_object_qdata(gobj, nullptr);
+
+    /* Now release all the resources the current wrapper has */
     invalidate_all_closures(priv);
     release_native_object(priv);
 
     /* Mark that a JS object once existed, but it doesn't any more */
     priv->js_object_finalized = true;
+    priv->keep_alive = nullptr;
 }
 
 static void
@@ -1653,6 +1658,9 @@ object_instance_finalize(JSFreeOp  *fop,
     GJS_DEC_COUNTER(object);
     priv->~ObjectInstance();
     g_slice_free(ObjectInstance, priv);
+
+    /* Remove the ObjectInstance pointer from the JSObject */
+    JS_SetPrivate(obj, nullptr);
 }
 
 static JSObject *


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]