diff options
author | Lennart Poettering <lennart@poettering.net> | 2009-04-22 04:07:01 +0200 |
---|---|---|
committer | Lennart Poettering <lennart@poettering.net> | 2009-05-20 02:09:30 +0200 |
commit | 004f01fa451b0341e7ea69ce7f08a1c4690f759a (patch) | |
tree | ce2438f8deecddbea5a3bed7f5689d6c3231e6ec | |
parent | 2eb14dbcac1870dda1b36ce1e6fedfe7500572cb (diff) |
unix-fd: add test for passing unix fds
This adds a full test for passing multiple fds across a D-Bus
connection.
-rw-r--r-- | bus/dispatch.c | 151 | ||||
-rw-r--r-- | bus/test-main.c | 10 | ||||
-rw-r--r-- | bus/test.h | 4 |
3 files changed, 164 insertions, 1 deletions
diff --git a/bus/dispatch.c b/bus/dispatch.c index 209bde3e..ca9a8433 100644 --- a/bus/dispatch.c +++ b/bus/dispatch.c @@ -35,6 +35,11 @@ #include <dbus/dbus-internals.h> #include <string.h> +#ifdef HAVE_UNIX_FD_PASSING +#include <dbus/dbus-sysdeps-unix.h> +#include <unistd.h> +#endif + static dbus_bool_t send_one_message (DBusConnection *connection, BusContext *context, @@ -4716,4 +4721,150 @@ bus_dispatch_sha1_test (const DBusString *test_data_dir) return TRUE; } +#ifdef HAVE_UNIX_FD_PASSING + +dbus_bool_t +bus_unix_fds_passing_test(const DBusString *test_data_dir) +{ + BusContext *context; + DBusConnection *foo, *bar; + DBusError error; + DBusMessage *m; + dbus_bool_t b; + int one[2], two[2], x, y, z; + char r; + + dbus_error_init (&error); + + context = bus_context_new_test (test_data_dir, "valid-config-files/debug-allow-all.conf"); + if (context == NULL) + _dbus_assert_not_reached ("could not alloc context"); + + foo = dbus_connection_open_private ("debug-pipe:name=test-server", &error); + if (foo == NULL) + _dbus_assert_not_reached ("could not alloc connection"); + + if (!bus_setup_debug_client (foo)) + _dbus_assert_not_reached ("could not set up connection"); + + spin_connection_until_authenticated (context, foo); + + if (!check_hello_message (context, foo)) + _dbus_assert_not_reached ("hello message failed"); + + if (!check_add_match_all (context, foo)) + _dbus_assert_not_reached ("AddMatch message failed"); + + bar = dbus_connection_open_private ("debug-pipe:name=test-server", &error); + if (bar == NULL) + _dbus_assert_not_reached ("could not alloc connection"); + + if (!bus_setup_debug_client (bar)) + _dbus_assert_not_reached ("could not set up connection"); + + spin_connection_until_authenticated (context, bar); + + if (!check_hello_message (context, bar)) + _dbus_assert_not_reached ("hello message failed"); + + if (!check_add_match_all (context, bar)) + _dbus_assert_not_reached ("AddMatch message failed"); + + if (!(m = dbus_message_new_signal("/", "a.b.c", "d"))) + _dbus_assert_not_reached ("could not alloc message"); + + if (!(_dbus_full_duplex_pipe(one, one+1, TRUE, &error))) + _dbus_assert_not_reached("Failed to allocate pipe #1"); + + if (!(_dbus_full_duplex_pipe(two, two+1, TRUE, &error))) + _dbus_assert_not_reached("Failed to allocate pipe #2"); + + if (!dbus_message_append_args(m, + DBUS_TYPE_UNIX_FD, one, + DBUS_TYPE_UNIX_FD, two, + DBUS_TYPE_UNIX_FD, two, + DBUS_TYPE_INVALID)) + _dbus_assert_not_reached("Failed to attach fds."); + + if (!_dbus_close(one[0], &error)) + _dbus_assert_not_reached("Failed to close pipe #1 "); + if (!_dbus_close(two[0], &error)) + _dbus_assert_not_reached("Failed to close pipe #2 "); + + + if (!dbus_connection_send (foo, m, NULL)) + _dbus_assert_not_reached("Failed to send fds"); + + dbus_message_unref(m); + + bus_test_run_clients_loop (SEND_PENDING (foo)); + + bus_test_run_everything (context); + + block_connection_until_message_from_bus (context, foo, "unix fd reception on foo"); + + if (!(m = pop_message_waiting_for_memory (foo))) + _dbus_assert_not_reached("Failed to receive msg"); + + if (!dbus_message_is_signal(m, "a.b.c", "d")) + _dbus_assert_not_reached("bogus message received"); + + dbus_message_unref(m); + + block_connection_until_message_from_bus (context, bar, "unix fd reception on bar"); + + if (!(m = pop_message_waiting_for_memory (bar))) + _dbus_assert_not_reached("Failed to receive msg"); + + if (!dbus_message_is_signal(m, "a.b.c", "d")) + _dbus_assert_not_reached("bogus message received"); + + if (!dbus_message_get_args(m, + &error, + DBUS_TYPE_UNIX_FD, &x, + DBUS_TYPE_UNIX_FD, &y, + DBUS_TYPE_UNIX_FD, &z, + DBUS_TYPE_INVALID)) + _dbus_assert_not_reached("Failed to parse fds."); + + dbus_message_unref(m); + + if (write(x, "X", 1) != 1) + _dbus_assert_not_reached("Failed to write to pipe #1"); + if (write(y, "Y", 1) != 1) + _dbus_assert_not_reached("Failed to write to pipe #2"); + if (write(z, "Z", 1) != 1) + _dbus_assert_not_reached("Failed to write to pipe #2/2nd fd"); + + if (!_dbus_close(x, &error)) + _dbus_assert_not_reached("Failed to close pipe #1/other side "); + if (!_dbus_close(y, &error)) + _dbus_assert_not_reached("Failed to close pipe #2/other side "); + if (!_dbus_close(z, &error)) + _dbus_assert_not_reached("Failed to close pipe #2/other size 2nd fd "); + + if (read(one[1], &r, 1) != 1 || r != 'X') + _dbus_assert_not_reached("Failed to read value from pipe."); + if (read(two[1], &r, 1) != 1 || r != 'Y') + _dbus_assert_not_reached("Failed to read value from pipe."); + if (read(two[1], &r, 1) != 1 || r != 'Z') + _dbus_assert_not_reached("Failed to read value from pipe."); + + if (!_dbus_close(one[1], &error)) + _dbus_assert_not_reached("Failed to close pipe #1 "); + if (!_dbus_close(two[1], &error)) + _dbus_assert_not_reached("Failed to close pipe #2 "); + + _dbus_verbose ("Disconnecting foo\n"); + kill_client_connection_unchecked (foo); + + _dbus_verbose ("Disconnecting bar\n"); + kill_client_connection_unchecked (bar); + + bus_context_unref (context); + + return TRUE; +} +#endif + #endif /* DBUS_BUILD_TESTS */ diff --git a/bus/test-main.c b/bus/test-main.c index 994550e2..2583f9a8 100644 --- a/bus/test-main.c +++ b/bus/test-main.c @@ -27,6 +27,7 @@ #include <dbus/dbus-string.h> #include <dbus/dbus-sysdeps.h> #include <dbus/dbus-internals.h> +#include <dbus/dbus-message-private.h> #include "selinux.h" #ifdef DBUS_BUILD_TESTS @@ -69,6 +70,7 @@ test_post_hook (void) if (_dbus_getenv ("DBUS_TEST_SELINUX")) bus_selinux_shutdown (); check_memleaks (progname); + _dbus_check_fdleaks(); } int @@ -138,6 +140,14 @@ main (int argc, char **argv) die ("service reload"); test_post_hook (); +#ifdef HAVE_UNIX_FD_PASSING + test_pre_hook (); + printf ("%s: Running unix fd passing test\n", argv[0]); + if (!bus_unix_fds_passing_test (&test_data_dir)) + die ("unix fd passing"); + test_post_hook (); +#endif + printf ("%s: Success\n", argv[0]); @@ -51,7 +51,9 @@ void bus_test_run_everything (BusContext *context); BusContext* bus_context_new_test (const DBusString *test_data_dir, const char *filename); - +#ifdef HAVE_UNIX_FD_PASSING +dbus_bool_t bus_unix_fds_passing_test (const DBusString *test_data_dir); +#endif #endif |