summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSimon McVittie <simon.mcvittie@collabora.co.uk>2014-03-12 09:30:47 +0000
committerSimon McVittie <simon.mcvittie@collabora.co.uk>2014-03-13 14:25:14 +0000
commitbb9a39a0658a9e41e221b857fa7ccaf1d72242e1 (patch)
treeeb6cdc10c814a93506d1d42d5f7c6a3fd680f09a
parent0a8b1c9170c03f35562606acf32f11fabb23b96f (diff)
call-cancellation and disconnection tests: don't dispose DBusGProxy
Using g_object_run_dispose() to force the DBusGProxy to be disposed was really exploiting an implementation detail of dbus-glib, and GDBus doesn't have an equivalent. To keep this test working after porting to GDBus, we need to do it properly, by having a private D-Bus connection and closing it.
-rw-r--r--tests/dbus/call-cancellation.c83
-rw-r--r--tests/dbus/disconnection.c97
2 files changed, 120 insertions, 60 deletions
diff --git a/tests/dbus/call-cancellation.c b/tests/dbus/call-cancellation.c
index fca97d58a..8b4ab3245 100644
--- a/tests/dbus/call-cancellation.c
+++ b/tests/dbus/call-cancellation.c
@@ -1,5 +1,8 @@
#include "config.h"
+#include <dbus/dbus.h>
+#include <dbus/dbus-glib-lowlevel.h>
+
#include <telepathy-glib/cli-misc.h>
#include <telepathy-glib/dbus.h>
#include <telepathy-glib/debug.h>
@@ -18,7 +21,6 @@
#define PTR(ui) GUINT_TO_POINTER(ui)
/* state tracking */
-static GMainLoop *mainloop;
static TpIntset *method_ok;
static TpIntset *method_error;
static TpIntset *freed_user_data;
@@ -47,6 +49,12 @@ typedef struct {
TpDBusDaemon *dbus_daemon;
TpProxy *proxies[N_PROXIES];
GObject *cd_service;
+
+ DBusConnection *private_libdbus;
+ DBusGConnection *private_dbusglib;
+ TpDBusDaemon *private_dbus_daemon;
+
+ gboolean had_last_reply;
} Fixture;
static Fixture *f;
@@ -147,7 +155,7 @@ method_cb (TpProxy *proxy,
weak_object, want_object);
if (which == TEST_Z)
- g_main_loop_quit (mainloop);
+ f->had_last_reply = TRUE;
}
static void
@@ -173,6 +181,26 @@ setup (void)
TP_TESTS_TYPE_SIMPLE_CHANNEL_DISPATCHER,
NULL);
tp_dbus_daemon_register_object (f->dbus_daemon, "/", f->cd_service);
+
+ f->private_libdbus = dbus_bus_get_private (DBUS_BUS_STARTER, NULL);
+ g_assert (f->private_libdbus != NULL);
+ dbus_connection_setup_with_g_main (f->private_libdbus, NULL);
+ dbus_connection_set_exit_on_disconnect (f->private_libdbus, FALSE);
+ f->private_dbusglib = dbus_connection_get_g_connection (
+ f->private_libdbus);
+ dbus_g_connection_ref (f->private_dbusglib);
+ f->private_dbus_daemon = tp_dbus_daemon_new (f->private_dbusglib);
+ g_assert (f->private_dbus_daemon != NULL);
+}
+
+static void
+drop_private_connection (void)
+{
+ dbus_g_connection_unref (f->private_dbusglib);
+ f->private_dbusglib = NULL;
+ dbus_connection_close (f->private_libdbus);
+ dbus_connection_unref (f->private_libdbus);
+ f->private_libdbus = NULL;
}
static void
@@ -180,13 +208,22 @@ teardown (void)
{
tp_tests_assert_last_unref (&f->cd_service);
tp_tests_assert_last_unref (&f->dbus_daemon);
+
+ tp_tests_assert_last_unref (&f->private_dbus_daemon);
}
static TpProxy *
-new_proxy (void)
+new_proxy (int which)
{
+ TpDBusDaemon *local_dbus_daemon;
+
+ if (which == TEST_F)
+ local_dbus_daemon = f->private_dbus_daemon;
+ else
+ local_dbus_daemon = f->dbus_daemon;
+
return tp_tests_object_new_static_class (TP_TYPE_PROXY,
- "dbus-daemon", f->dbus_daemon,
+ "dbus-daemon", local_dbus_daemon,
"bus-name", tp_dbus_daemon_get_unique_name (f->dbus_daemon),
"object-path", "/",
NULL);
@@ -200,7 +237,6 @@ main (int argc,
GObject *b_stub, *i_stub, *j_stub, *k_stub;
GError err = { TP_ERROR, TP_ERROR_INVALID_ARGUMENT, "Because I said so" };
TpProxyPendingCall *pc;
- gpointer tmp_obj;
guint i;
tp_tests_abort_after (10);
@@ -210,8 +246,6 @@ main (int argc,
method_ok = tp_intset_sized_new (N_PROXIES);
method_error = tp_intset_sized_new (N_PROXIES);
- mainloop = g_main_loop_new (NULL, FALSE);
-
/* it's on the stack, but it's valid until we leave main(), which will
* do for now... one day this test should use GTest, but this might
* not be that day */
@@ -223,11 +257,11 @@ main (int argc,
for (i = TEST_A; i <= TEST_K; i++)
{
- f->proxies[i] = new_proxy ();
+ f->proxies[i] = new_proxy (i);
g_message ("%c=%p", 'a' + i, f->proxies[i]);
}
- f->proxies[TEST_Z] = new_proxy ();
+ f->proxies[TEST_Z] = new_proxy (TEST_Z);
g_message ("z=%p", f->proxies[TEST_Z]);
/* a survives */
@@ -293,25 +327,12 @@ main (int argc,
MYASSERT (!tp_intset_is_member (method_error, TEST_E), "");
/* f's method call fails with an error, because it's implicitly
- * invalidated by its DBusGProxy being destroyed.
- *
- * Note that this test case exploits implementation details of dbus-glib.
- * If it stops working after a dbus-glib upgrade, that's probably why. */
+ * invalidated by its own connection disconnecting. */
g_message ("Starting call on f");
tp_cli_dbus_properties_call_get_all (f->proxies[TEST_F], -1,
TP_IFACE_CHANNEL_DISPATCHER, method_cb, PTR (TEST_F),
destroy_user_data, NULL);
MYASSERT (!tp_intset_is_member (freed_user_data, TEST_F), "");
- g_message ("Forcibly disposing f's DBusGProxy to simulate name owner loss");
- tmp_obj = tp_proxy_get_interface_by_id (f->proxies[TEST_F],
- TP_IFACE_QUARK_DBUS_PROPERTIES, NULL);
- MYASSERT (tmp_obj != NULL, "");
- g_object_run_dispose (tmp_obj);
- /* the callback will be queued (to avoid reentrancy), so we don't get it
- * until the main loop runs */
- MYASSERT (!tp_intset_is_member (freed_user_data, TEST_F), "");
- MYASSERT (!tp_intset_is_member (method_ok, TEST_F), "");
- MYASSERT (!tp_intset_is_member (method_error, TEST_F), "");
/* g gets unreferenced, but survives long enough for the call to complete
* successfully later, because the pending call holds a reference;
@@ -423,9 +444,21 @@ main (int argc,
MYASSERT (!tp_intset_is_member (method_ok, TEST_Z), "");
MYASSERT (!tp_intset_is_member (method_error, TEST_Z), "");
+ g_message ("Dropping private D-Bus connection");
+ drop_private_connection ();
+ /* the callback will be queued (to avoid reentrancy), so we don't get it
+ * until the main loop runs */
+ MYASSERT (!tp_intset_is_member (freed_user_data, TEST_F), "");
+ MYASSERT (!tp_intset_is_member (method_ok, TEST_F), "");
+ MYASSERT (!tp_intset_is_member (method_error, TEST_F), "");
+
g_message ("Running main loop");
- g_main_loop_run (mainloop);
- g_main_loop_unref (mainloop);
+
+ /* There's no guarantee that proxy F will detect that its socket closed
+ * in any particular order relative to the signals, so wait for both. */
+ while (!f->had_last_reply ||
+ tp_proxy_get_invalidated (f->proxies[TEST_F]) == NULL)
+ g_main_context_iteration (NULL, TRUE);
/* now that the calls have been delivered, d will finally have gone away */
MYASSERT (tp_intset_is_member (freed_user_data, TEST_D), "");
diff --git a/tests/dbus/disconnection.c b/tests/dbus/disconnection.c
index 243db0702..5f3ff5247 100644
--- a/tests/dbus/disconnection.c
+++ b/tests/dbus/disconnection.c
@@ -1,5 +1,8 @@
#include "config.h"
+#include <dbus/dbus.h>
+#include <dbus/dbus-glib-lowlevel.h>
+
#include <telepathy-glib/cli-misc.h>
#include <telepathy-glib/dbus.h>
#include <telepathy-glib/debug.h>
@@ -19,7 +22,6 @@
#define PTR(ui) GUINT_TO_POINTER(ui)
/* state tracking */
-static GMainLoop *mainloop;
static TpIntset *caught_signal;
static TpIntset *freed_user_data;
@@ -40,6 +42,10 @@ typedef struct {
TpDBusDaemon *dbus_daemon;
TpProxy *proxies[N_PROXIES];
GObject *cd_service;
+
+ DBusConnection *private_libdbus;
+ DBusGConnection *private_dbusglib;
+ TpDBusDaemon *private_dbus_daemon;
} Fixture;
static Fixture *f;
@@ -112,13 +118,6 @@ signal_cb (TpProxy *proxy,
MYASSERT (proxy == want_proxy, ": %p != %p", proxy, want_proxy);
MYASSERT (weak_object == want_object, ": %p != %p", weak_object,
want_object);
-
- if (tp_intset_is_member (caught_signal, TEST_A) &&
- tp_intset_is_member (caught_signal, TEST_Z))
- {
- /* we've had all the signals we're going to */
- g_main_loop_quit (mainloop);
- }
}
static void
@@ -142,6 +141,26 @@ setup (void)
TP_TESTS_TYPE_SIMPLE_CHANNEL_DISPATCHER,
NULL);
tp_dbus_daemon_register_object (f->dbus_daemon, "/", f->cd_service);
+
+ f->private_libdbus = dbus_bus_get_private (DBUS_BUS_STARTER, NULL);
+ g_assert (f->private_libdbus != NULL);
+ dbus_connection_setup_with_g_main (f->private_libdbus, NULL);
+ dbus_connection_set_exit_on_disconnect (f->private_libdbus, FALSE);
+ f->private_dbusglib = dbus_connection_get_g_connection (
+ f->private_libdbus);
+ dbus_g_connection_ref (f->private_dbusglib);
+ f->private_dbus_daemon = tp_dbus_daemon_new (f->private_dbusglib);
+ g_assert (f->private_dbus_daemon != NULL);
+}
+
+static void
+drop_private_connection (void)
+{
+ dbus_g_connection_unref (f->private_dbusglib);
+ f->private_dbusglib = NULL;
+ dbus_connection_close (f->private_libdbus);
+ dbus_connection_unref (f->private_libdbus);
+ f->private_libdbus = NULL;
}
static void
@@ -149,13 +168,22 @@ teardown (void)
{
tp_tests_assert_last_unref (&f->cd_service);
tp_tests_assert_last_unref (&f->dbus_daemon);
+
+ tp_tests_assert_last_unref (&f->private_dbus_daemon);
}
static TpProxy *
-new_proxy (void)
+new_proxy (int which)
{
+ TpDBusDaemon *local_dbus_daemon;
+
+ if (which == TEST_F)
+ local_dbus_daemon = f->private_dbus_daemon;
+ else
+ local_dbus_daemon = f->dbus_daemon;
+
return tp_tests_object_new_static_class (TP_TYPE_PROXY,
- "dbus-daemon", f->dbus_daemon,
+ "dbus-daemon", local_dbus_daemon,
"bus-name", tp_dbus_daemon_get_unique_name (f->dbus_daemon),
"object-path", "/",
NULL);
@@ -170,7 +198,6 @@ main (int argc,
GError *error_out = NULL;
GError err = { TP_ERROR, TP_ERROR_INVALID_ARGUMENT, "Because I said so" };
TpProxySignalConnection *sc;
- gpointer tmp_obj;
gboolean freed = FALSE;
GHashTable *empty_asv;
int i;
@@ -188,17 +215,15 @@ main (int argc,
setup ();
- mainloop = g_main_loop_new (NULL, FALSE);
-
g_message ("Creating proxies");
for (i = TEST_A; i <= TEST_H; i++)
{
- f->proxies[i] = new_proxy ();
+ f->proxies[i] = new_proxy (i);
g_message ("%c=%p", 'a' + i, f->proxies[i]);
}
- f->proxies[TEST_Z] = new_proxy ();
+ f->proxies[TEST_Z] = new_proxy (TEST_Z);
g_message ("z=%p", f->proxies[TEST_Z]);
/* a survives */
@@ -266,30 +291,13 @@ main (int argc,
tp_proxy_signal_connection_disconnect (sc);
/* f gets its signal connection cancelled because it's implicitly
- * invalidated by its DBusGProxy being destroyed.
- *
- * Note that this test case exploits implementation details of dbus-glib.
- * If it stops working after a dbus-glib upgrade, that's probably why. */
+ * invalidated by its own connection disconnecting. */
g_message ("Connecting signal to f");
tp_cli_dbus_properties_connect_to_properties_changed (f->proxies[TEST_F],
signal_cb, PTR (TEST_F),
destroy_user_data, NULL, &error_out);
g_assert_no_error (error_out);
MYASSERT (!tp_intset_is_member (freed_user_data, TEST_F), "");
- g_message ("Forcibly disposing f's DBusGProxy to simulate name owner loss");
- tmp_obj = tp_proxy_get_interface_by_id (f->proxies[TEST_F],
- TP_IFACE_QUARK_DBUS_PROPERTIES, NULL);
- MYASSERT (tmp_obj != NULL, "");
- g_object_run_dispose (tmp_obj);
- /* assert that connecting to a signal on an invalid proxy fails */
- freed = FALSE;
- tp_cli_dbus_properties_connect_to_properties_changed (f->proxies[TEST_F],
- unwanted_signal_cb, &freed, set_freed, NULL, &error_out);
- MYASSERT (freed, "");
- MYASSERT (error_out != NULL, "");
- MYASSERT (error_out->code == DBUS_GERROR_NAME_HAS_NO_OWNER, "");
- g_error_free (error_out);
- error_out = NULL;
/* g gets its signal connection cancelled because it's
* implicitly invalidated by being destroyed; unlike d, the signal
@@ -333,9 +341,28 @@ main (int argc,
TP_IFACE_CHANNEL_DISPATCHER, empty_asv, NULL);
g_hash_table_unref (empty_asv);
+ g_message ("Dropping private D-Bus connection");
+ drop_private_connection ();
+
+ /* wait for everything to happen */
g_message ("Running main loop");
- g_main_loop_run (mainloop);
- g_main_loop_unref (mainloop);
+
+ /* There's no guarantee that proxy F will detect that its socket closed
+ * in any particular order relative to the signals, so wait for both. */
+ while (!tp_intset_is_member (caught_signal, TEST_A) ||
+ !tp_intset_is_member (caught_signal, TEST_Z) ||
+ tp_proxy_get_invalidated (f->proxies[TEST_F]) == NULL)
+ g_main_context_iteration (NULL, TRUE);
+
+ /* assert that connecting to a signal on an invalid proxy fails */
+ freed = FALSE;
+ tp_cli_dbus_properties_connect_to_properties_changed (f->proxies[TEST_F],
+ unwanted_signal_cb, &freed, set_freed, NULL, &error_out);
+ MYASSERT (freed, "");
+ MYASSERT (error_out != NULL, "");
+ MYASSERT (error_out->code == DBUS_GERROR_NAME_HAS_NO_OWNER, "");
+ g_error_free (error_out);
+ error_out = NULL;
/* Now that the main loop has run, cancelled signal connections have been
* freed */