[pygobject] Handle multiple deinit of callable cache



commit 54c623ba639654716ca475f75c92cc8ed673d9f5
Author: Dan Nicholson <nicholson endlessm com>
Date:   Wed Dec 21 11:50:08 2016 -0600

    Handle multiple deinit of callable cache
    
    In python3, it seems that the callable cache deinit can be called
    multiple times when the program is exiting. Make that safer by clearing
    the various pointers in the structure using g_clear_pointer and
    Py_CLEAR. A subsequent call will skip all the deinit by seeing NULL
    pointers for the members.
    
    This was causing a critical warning when destroying the arg name hash
    table multiple times with the following trivial program:
    
    $ python3 -c 'from gi.repository import GLib; v = GLib.Variant("s", "foo")'
    
    (process:32378): GLib-CRITICAL **: g_hash_table_destroy: assertion 'hash_table != NULL' failed
    
    (process:32378): GLib-CRITICAL **: g_hash_table_destroy: assertion 'hash_table != NULL' failed
    
    https://bugzilla.gnome.org/show_bug.cgi?id=776092

 gi/pygi-cache.c |   15 +++++++--------
 1 files changed, 7 insertions(+), 8 deletions(-)
---
diff --git a/gi/pygi-cache.c b/gi/pygi-cache.c
index 5080b66..170b242 100644
--- a/gi/pygi-cache.c
+++ b/gi/pygi-cache.c
@@ -684,14 +684,13 @@ _callable_cache_generate_args_cache_real (PyGICallableCache *callable_cache,
 static void
 _callable_cache_deinit_real (PyGICallableCache *cache)
 {
-    g_slist_free (cache->to_py_args);
-    g_slist_free (cache->arg_name_list);
-    g_hash_table_destroy (cache->arg_name_hash);
-    g_ptr_array_unref (cache->args_cache);
-    Py_XDECREF (cache->resulttuple_type);
-
-    if (cache->return_cache != NULL)
-        pygi_arg_cache_free (cache->return_cache);
+    g_clear_pointer (&cache->to_py_args, g_slist_free);
+    g_clear_pointer (&cache->arg_name_list, g_slist_free);
+    g_clear_pointer (&cache->arg_name_hash, g_hash_table_unref);
+    g_clear_pointer (&cache->args_cache, g_ptr_array_unref);
+    Py_CLEAR (cache->resulttuple_type);
+
+    g_clear_pointer (&cache->return_cache, pygi_arg_cache_free);
 }
 
 static gboolean


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