summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSimon Feltman <sfeltman@src.gnome.org>2013-09-26 19:05:20 -0700
committerSimon Feltman <sfeltman@src.gnome.org>2013-10-07 16:18:09 -0700
commit73c6213e8b47fa7c4c2c7a517fe7b56126145888 (patch)
tree820cd31f702734d165007dde237e55eb5fcc0583
parenta76b06179cdca43f1c7d1feb8e2563e3d884a8ff (diff)
downloadpygobject-73c6213e8b47fa7c4c2c7a517fe7b56126145888.tar.gz
Don't pass None to callbacks when user data is not specified
For APIs which support a callback and optional user data, don't pass the user data to the callback if it was not explicitly specified when the callback was connected. https://bugzilla.gnome.org/show_bug.cgi?id=640812
-rw-r--r--gi/pygi-closure.c17
-rw-r--r--gi/pygi-marshal-from-py.c5
-rw-r--r--tests/test_everything.py7
3 files changed, 16 insertions, 13 deletions
diff --git a/gi/pygi-closure.c b/gi/pygi-closure.c
index 2f5548a9..bfd6d0df 100644
--- a/gi/pygi-closure.c
+++ b/gi/pygi-closure.c
@@ -368,7 +368,18 @@ _pygi_closure_convert_arguments (GICallableInfo *callable_info, void **args,
if (direction == GI_DIRECTION_IN && arg_tag == GI_TYPE_TAG_VOID &&
g_type_info_is_pointer (&arg_type)) {
- if (user_data == NULL) {
+ if (user_data == _PyGIDefaultArgPlaceholder) {
+ /* When user data is a place holder, skip handing anything to the callback.
+ * This happens when the callback connect function accepts user data
+ * but nothing was passed in.
+ */
+ continue;
+ } else if (user_data == NULL) {
+ /* user data can be NULL for connect functions which don't accept
+ * user data but we still need to pass None to the callbacks for
+ * compatibility of setups prior to _PyGIDefaultArgPlaceholder.
+ * For example: Regress.test_async_ready_callback
+ */
Py_INCREF (Py_None);
value = Py_None;
} else {
@@ -631,10 +642,10 @@ _pygi_make_native_closure (GICallableInfo* info,
closure = g_slice_new0 (PyGICClosure);
closure->info = (GICallableInfo *) g_base_info_ref ( (GIBaseInfo *) info);
closure->function = py_function;
- closure->user_data = py_user_data ? py_user_data : Py_None;
+ closure->user_data = py_user_data;
Py_INCREF (py_function);
- Py_INCREF (closure->user_data);
+ Py_XINCREF (closure->user_data);
fficlosure =
g_callable_info_prepare_closure (info, &closure->cif, _pygi_closure_handle,
diff --git a/gi/pygi-marshal-from-py.c b/gi/pygi-marshal-from-py.c
index 22571ef7..73356b1a 100644
--- a/gi/pygi-marshal-from-py.c
+++ b/gi/pygi-marshal-from-py.c
@@ -1255,11 +1255,6 @@ _pygi_marshal_from_py_interface_callback (PyGIInvokeState *state,
py_user_data = PyTuple_GetItem (state->py_in_args, user_data_cache->py_arg_index);
if (!py_user_data)
return FALSE;
- /* NULL out user_data if it was not supplied and the default arg placeholder
- * was used instead.
- */
- if (py_user_data == _PyGIDefaultArgPlaceholder)
- py_user_data = NULL;
}
}
diff --git a/tests/test_everything.py b/tests/test_everything.py
index 0c6533a8..ab1fc487 100644
--- a/tests/test_everything.py
+++ b/tests/test_everything.py
@@ -717,12 +717,10 @@ class TestCallbacks(unittest.TestCase):
self.assertEqual(TestCallbacks.called, 100)
- def test_callback_userdata_none_default_arg(self):
+ def test_callback_userdata_no_user_data(self):
TestCallbacks.called = 0
- userdata_list = []
- def callback(userdata):
- userdata_list.append(userdata)
+ def callback():
TestCallbacks.called += 1
return TestCallbacks.called
@@ -731,7 +729,6 @@ class TestCallbacks(unittest.TestCase):
self.assertEqual(val, i + 1)
self.assertEqual(TestCallbacks.called, 100)
- self.assertSequenceEqual(userdata_list, [None] * 100)
def test_async_ready_callback(self):
TestCallbacks.called = False