1 /* Integration tests for the dbus-daemon
3 * Author: Simon McVittie <simon.mcvittie@collabora.co.uk>
4 * Copyright © 2010-2011 Nokia Corporation
5 * Copyright © 2015 Collabora Ltd.
7 * Permission is hereby granted, free of charge, to any person
8 * obtaining a copy of this software and associated documentation files
9 * (the "Software"), to deal in the Software without restriction,
10 * including without limitation the rights to use, copy, modify, merge,
11 * publish, distribute, sublicense, and/or sell copies of the Software,
12 * and to permit persons to whom the Software is furnished to do so,
13 * subject to the following conditions:
15 * The above copyright notice and this permission notice shall be
16 * included in all copies or substantial portions of the Software.
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
22 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
23 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
24 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
33 #include <dbus/dbus.h>
36 #include <glib/gstdio.h>
39 #include "bus/stats.h"
40 #include "test-utils-glib.h"
47 # include <sys/types.h>
50 /* The CMake build system doesn't know how to check for this yet */
51 # include <gio/gunixfdmessage.h>
54 # ifdef HAVE_SYS_RESOURCE_H
55 # include <sys/resource.h>
58 # ifdef HAVE_SYS_TIME_H
59 # include <sys/time.h>
63 /* Platforms where we know that credentials-passing passes both the
64 * uid and the pid. Please keep these in alphabetical order.
66 * These platforms should #error in _dbus_read_credentials_socket()
67 * if we didn't detect their flavour of credentials-passing, since that
68 * would be a regression.
70 #if defined(__FreeBSD__) || defined(__FreeBSD_kernel__) || \
71 defined(__linux__) || \
72 defined(__NetBSD__) || \
74 # define UNIX_USER_SHOULD_WORK
75 # define PID_SHOULD_WORK
78 /* Platforms where we know that credentials-passing passes the
79 * uid, but not necessarily the pid. Again, alphabetical order please.
81 * These platforms should also #error in _dbus_read_credentials_socket()
82 * if we didn't detect their flavour of credentials-passing.
84 #if 0 /* defined(__your_platform_here__) */
85 # define UNIX_USER_SHOULD_WORK
99 DBusConnection *left_conn;
101 DBusConnection *right_conn;
102 GQueue held_messages;
103 gboolean right_conn_echo;
104 gboolean right_conn_hold;
105 gboolean wait_forever_called;
107 gchar *tmp_runtime_dir;
108 gchar *saved_runtime_dir;
111 static DBusHandlerResult
112 echo_filter (DBusConnection *connection,
113 DBusMessage *message,
116 Fixture *f = user_data;
119 if (dbus_message_get_type (message) != DBUS_MESSAGE_TYPE_METHOD_CALL)
120 return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
122 /* WaitForever() never replies, emulating a service that has got stuck */
123 if (dbus_message_is_method_call (message, "com.example", "WaitForever"))
125 f->wait_forever_called = TRUE;
126 return DBUS_HANDLER_RESULT_HANDLED;
129 reply = dbus_message_new_method_return (message);
134 if (!dbus_connection_send (connection, reply, NULL))
137 dbus_clear_message (&reply);
139 return DBUS_HANDLER_RESULT_HANDLED;
142 static DBusHandlerResult
143 hold_filter (DBusConnection *connection,
144 DBusMessage *message,
147 Fixture *f = user_data;
149 if (dbus_message_get_type (message) != DBUS_MESSAGE_TYPE_METHOD_CALL)
150 return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
152 g_queue_push_tail (&f->held_messages, dbus_message_ref (message));
154 return DBUS_HANDLER_RESULT_HANDLED;
160 const char *config_file;
162 enum { SPECIFY_ADDRESS = 0, RELY_ON_DEFAULT } connect_mode;
167 gconstpointer context)
169 const Config *config = context;
171 /* Some tests are fairly slow, so make the test timeout per-test */
172 test_timeout_reset (1);
174 f->ctx = test_main_context_get ();
176 dbus_error_init (&f->e);
178 if (config != NULL && config->connect_mode == RELY_ON_DEFAULT)
180 /* this is chosen to be something needing escaping */
181 f->tmp_runtime_dir = g_dir_make_tmp ("dbus=daemon=test.XXXXXX", &f->ge);
182 g_assert_no_error (f->ge);
184 /* we're relying on being single-threaded for this to be safe */
185 f->saved_runtime_dir = g_strdup (g_getenv ("XDG_RUNTIME_DIR"));
186 g_setenv ("XDG_RUNTIME_DIR", f->tmp_runtime_dir, TRUE);
187 g_unsetenv ("DBUS_SESSION_BUS_ADDRESS");
190 f->address = test_get_dbus_daemon (config ? config->config_file : NULL,
191 config ? config->user : TEST_USER_ME,
192 NULL, &f->daemon_pid);
194 if (f->address == NULL)
200 f->left_conn = test_connect_to_bus (f->ctx, f->address);
202 if (config != NULL && config->connect_mode == RELY_ON_DEFAULT)
204 /* use the default bus for the echo service ("right"), to check that
205 * it ends up on the same bus as the client ("left") */
206 f->right_conn = dbus_bus_get_private (DBUS_BUS_SESSION, &f->e);
207 test_assert_no_error (&f->e);
209 if (!test_connection_setup (f->ctx, f->right_conn))
214 f->right_conn = test_connect_to_bus (f->ctx, f->address);
219 add_echo_filter (Fixture *f)
221 if (!dbus_connection_add_filter (f->right_conn, echo_filter, f, NULL))
224 f->right_conn_echo = TRUE;
228 add_hold_filter (Fixture *f)
230 if (!dbus_connection_add_filter (f->right_conn, hold_filter, f, NULL))
233 f->right_conn_hold = TRUE;
237 pc_count (DBusPendingCall *pc,
240 guint *received_p = data;
246 pc_enqueue (DBusPendingCall *pc,
250 DBusMessage *m = dbus_pending_call_steal_reply (pc);
252 g_test_message ("message of type %d", dbus_message_get_type (m));
253 g_queue_push_tail (q, m);
257 test_echo (Fixture *f,
258 gconstpointer context)
260 const Config *config = context;
269 if (config != NULL && config->bug_ref != NULL)
270 g_test_bug (config->bug_ref);
276 count = MAX (config->min_messages, count);
280 g_test_timer_start ();
282 for (sent = 0; sent < count; sent++)
284 DBusMessage *m = dbus_message_new_method_call (
285 dbus_bus_get_unique_name (f->right_conn), "/",
286 "com.example", "Spam");
292 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
293 DBUS_TIMEOUT_INFINITE) ||
297 if (dbus_pending_call_get_completed (pc))
298 pc_count (pc, &received);
299 else if (!dbus_pending_call_set_notify (pc, pc_count, &received,
303 dbus_clear_pending_call (&pc);
304 dbus_clear_message (&m);
307 while (received < count)
308 test_main_context_iterate (f->ctx, TRUE);
310 elapsed = g_test_timer_elapsed ();
312 g_test_maximized_result (count / elapsed, "%u messages / %f seconds",
317 test_no_reply (Fixture *f,
318 gconstpointer context)
320 const Config *config = context;
323 DBusMessage *reply = NULL;
324 enum { TIMEOUT, DISCONNECT } mode;
330 g_test_bug ("76112");
332 if (config != NULL && config->config_file != NULL)
337 m = dbus_message_new_method_call (
338 dbus_bus_get_unique_name (f->right_conn), "/",
339 "com.example", "WaitForever");
346 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
347 DBUS_TIMEOUT_INFINITE) ||
351 if (dbus_pending_call_get_completed (pc))
352 test_pending_call_store_reply (pc, &reply);
353 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
357 dbus_clear_pending_call (&pc);
358 dbus_clear_message (&m);
360 if (mode == DISCONNECT)
362 while (!f->wait_forever_called)
363 test_main_context_iterate (f->ctx, TRUE);
365 dbus_connection_remove_filter (f->right_conn, echo_filter, f);
366 dbus_connection_close (f->right_conn);
367 dbus_clear_connection (&f->right_conn);
370 while (reply == NULL)
371 test_main_context_iterate (f->ctx, TRUE);
373 /* using inefficient string comparison for better assertion message */
375 dbus_message_type_to_string (dbus_message_get_type (reply)), ==,
376 dbus_message_type_to_string (DBUS_MESSAGE_TYPE_ERROR));
377 ok = dbus_set_error_from_message (&f->e, reply);
379 g_assert_cmpstr (f->e.name, ==, DBUS_ERROR_NO_REPLY);
381 if (mode == DISCONNECT)
382 g_assert_cmpstr (f->e.message, ==,
383 "Message recipient disconnected from message bus without replying");
385 g_assert_cmpstr (f->e.message, ==,
386 "Message did not receive a reply (timeout by message bus)");
388 dbus_clear_message (&reply);
392 test_creds (Fixture *f,
393 gconstpointer context)
395 const char *unique = dbus_bus_get_unique_name (f->left_conn);
396 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
397 DBUS_PATH_DBUS, DBUS_INTERFACE_DBUS, "GetConnectionCredentials");
399 DBusMessageIter args_iter;
400 DBusMessageIter arr_iter;
401 DBusMessageIter pair_iter;
402 DBusMessageIter var_iter;
406 SEEN_WINDOWS_SID = 4,
407 SEEN_LINUX_SECURITY_LABEL = 8
413 if (!dbus_message_append_args (m,
414 DBUS_TYPE_STRING, &unique,
418 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
419 DBUS_TIMEOUT_USE_DEFAULT) ||
423 dbus_clear_message (&m);
425 if (dbus_pending_call_get_completed (pc))
426 test_pending_call_store_reply (pc, &m);
427 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
432 test_main_context_iterate (f->ctx, TRUE);
434 g_assert_cmpstr (dbus_message_get_signature (m), ==, "a{sv}");
436 dbus_message_iter_init (m, &args_iter);
437 g_assert_cmpuint (dbus_message_iter_get_arg_type (&args_iter), ==,
439 g_assert_cmpuint (dbus_message_iter_get_element_type (&args_iter), ==,
440 DBUS_TYPE_DICT_ENTRY);
441 dbus_message_iter_recurse (&args_iter, &arr_iter);
443 while (dbus_message_iter_get_arg_type (&arr_iter) != DBUS_TYPE_INVALID)
447 dbus_message_iter_recurse (&arr_iter, &pair_iter);
448 g_assert_cmpuint (dbus_message_iter_get_arg_type (&pair_iter), ==,
450 dbus_message_iter_get_basic (&pair_iter, &name);
451 dbus_message_iter_next (&pair_iter);
452 g_assert_cmpuint (dbus_message_iter_get_arg_type (&pair_iter), ==,
454 dbus_message_iter_recurse (&pair_iter, &var_iter);
456 if (g_strcmp0 (name, "UnixUserID") == 0)
461 g_assert (!(seen & SEEN_UNIX_USER));
462 g_assert_cmpuint (dbus_message_iter_get_arg_type (&var_iter), ==,
464 dbus_message_iter_get_basic (&var_iter, &u32);
465 g_test_message ("%s of this process is %u", name, u32);
466 g_assert_cmpuint (u32, ==, geteuid ());
467 seen |= SEEN_UNIX_USER;
469 g_assert_not_reached ();
472 else if (g_strcmp0 (name, "WindowsSID") == 0)
478 g_assert (!(seen & SEEN_WINDOWS_SID));
479 g_assert_cmpuint (dbus_message_iter_get_arg_type (&var_iter), ==,
481 dbus_message_iter_get_basic (&var_iter, &sid);
482 g_test_message ("%s of this process is %s", name, sid);
483 if (_dbus_getsid (&self_sid, 0))
485 g_assert_cmpstr (self_sid, ==, sid);
488 seen |= SEEN_WINDOWS_SID;
490 g_assert_not_reached ();
493 else if (g_strcmp0 (name, "ProcessID") == 0)
497 g_assert (!(seen & SEEN_PID));
498 g_assert_cmpuint (dbus_message_iter_get_arg_type (&var_iter), ==,
500 dbus_message_iter_get_basic (&var_iter, &u32);
501 g_test_message ("%s of this process is %u", name, u32);
503 g_assert_cmpuint (u32, ==, getpid ());
504 #elif defined(G_OS_WIN32)
505 g_assert_cmpuint (u32, ==, GetCurrentProcessId ());
507 g_assert_not_reached ();
511 else if (g_strcmp0 (name, "LinuxSecurityLabel") == 0)
516 DBusMessageIter ay_iter;
518 g_assert (!(seen & SEEN_LINUX_SECURITY_LABEL));
519 g_assert_cmpuint (dbus_message_iter_get_arg_type (&var_iter), ==,
521 dbus_message_iter_recurse (&var_iter, &ay_iter);
522 g_assert_cmpuint (dbus_message_iter_get_arg_type (&ay_iter), ==,
524 dbus_message_iter_get_fixed_array (&ay_iter, &label, &len);
525 g_test_message ("%s of this process is %s", name, label);
526 g_assert_cmpuint (strlen (label) + 1, ==, len);
527 seen |= SEEN_LINUX_SECURITY_LABEL;
529 g_assert_not_reached ();
533 dbus_message_iter_next (&arr_iter);
536 #ifdef UNIX_USER_SHOULD_WORK
537 g_assert (seen & SEEN_UNIX_USER);
540 #ifdef PID_SHOULD_WORK
541 g_assert (seen & SEEN_PID);
545 g_assert (seen & SEEN_WINDOWS_SID);
548 dbus_clear_message (&m);
549 dbus_clear_pending_call (&pc);
553 test_processid (Fixture *f,
554 gconstpointer context)
556 const char *unique = dbus_bus_get_unique_name (f->left_conn);
557 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
558 DBUS_PATH_DBUS, DBUS_INTERFACE_DBUS, "GetConnectionUnixProcessID");
560 DBusError error = DBUS_ERROR_INIT;
566 if (!dbus_message_append_args (m,
567 DBUS_TYPE_STRING, &unique,
571 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
572 DBUS_TIMEOUT_USE_DEFAULT) ||
576 dbus_clear_message (&m);
578 if (dbus_pending_call_get_completed (pc))
579 test_pending_call_store_reply (pc, &m);
580 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
585 test_main_context_iterate (f->ctx, TRUE);
587 if (dbus_set_error_from_message (&error, m))
589 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNIX_PROCESS_ID_UNKNOWN);
591 #ifdef PID_SHOULD_WORK
592 g_error ("Expected pid to be passed, but got %s: %s",
593 error.name, error.message);
596 dbus_error_free (&error);
598 else if (dbus_message_get_args (m, &error,
599 DBUS_TYPE_UINT32, &pid,
602 g_assert_cmpstr (dbus_message_get_signature (m), ==, "u");
603 test_assert_no_error (&error);
605 g_test_message ("GetConnectionUnixProcessID returned %u", pid);
608 g_assert_cmpuint (pid, ==, getpid ());
609 #elif defined(G_OS_WIN32)
610 g_assert_cmpuint (pid, ==, GetCurrentProcessId ());
612 g_assert_not_reached ();
617 g_error ("Unexpected error: %s: %s", error.name, error.message);
620 dbus_clear_message (&m);
621 dbus_clear_pending_call (&pc);
625 test_canonical_path_uae (Fixture *f,
626 gconstpointer context)
628 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
629 DBUS_PATH_DBUS, DBUS_INTERFACE_DBUS, "UpdateActivationEnvironment");
631 DBusMessageIter args_iter;
632 DBusMessageIter arr_iter;
637 dbus_message_iter_init_append (m, &args_iter);
639 /* Append an empty a{ss} (string => string dictionary). */
640 if (!dbus_message_iter_open_container (&args_iter, DBUS_TYPE_ARRAY,
641 "{ss}", &arr_iter) ||
642 !dbus_message_iter_close_container (&args_iter, &arr_iter))
645 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
646 DBUS_TIMEOUT_USE_DEFAULT) ||
650 dbus_clear_message (&m);
652 if (dbus_pending_call_get_completed (pc))
653 test_pending_call_store_reply (pc, &m);
654 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
659 test_main_context_iterate (f->ctx, TRUE);
662 g_assert_cmpint (dbus_message_get_type (m), ==,
663 DBUS_MESSAGE_TYPE_METHOD_RETURN);
665 dbus_clear_message (&m);
666 dbus_clear_pending_call (&pc);
668 /* Now try with the wrong object path */
669 m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
670 "/com/example/Wrong", DBUS_INTERFACE_DBUS, "UpdateActivationEnvironment");
675 dbus_message_iter_init_append (m, &args_iter);
677 /* Append an empty a{ss} (string => string dictionary). */
678 if (!dbus_message_iter_open_container (&args_iter, DBUS_TYPE_ARRAY,
679 "{ss}", &arr_iter) ||
680 !dbus_message_iter_close_container (&args_iter, &arr_iter))
683 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
684 DBUS_TIMEOUT_USE_DEFAULT) ||
688 dbus_clear_message (&m);
690 if (dbus_pending_call_get_completed (pc))
691 test_pending_call_store_reply (pc, &m);
692 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
697 test_main_context_iterate (f->ctx, TRUE);
699 /* it fails, yielding an error message with one string argument */
700 g_assert_cmpint (dbus_message_get_type (m), ==, DBUS_MESSAGE_TYPE_ERROR);
701 g_assert_cmpstr (dbus_message_get_error_name (m), ==,
702 DBUS_ERROR_ACCESS_DENIED);
703 g_assert_cmpstr (dbus_message_get_signature (m), ==, "s");
705 dbus_clear_message (&m);
706 dbus_clear_pending_call (&pc);
710 test_max_connections (Fixture *f,
711 gconstpointer context)
713 DBusError error = DBUS_ERROR_INIT;
714 DBusConnection *third_conn;
715 DBusConnection *failing_conn;
720 /* We have two connections already */
721 g_assert (f->left_conn != NULL);
722 g_assert (f->right_conn != NULL);
724 /* Our configuration file sets the limit to 3 connections, either globally
725 * or per uid, so this one is the last that will work */
726 third_conn = test_connect_to_bus (f->ctx, f->address);
728 /* This one is going to fail. We don't guarantee whether it will fail
729 * now, or while registering (implementation detail: it's the latter). */
730 failing_conn = dbus_connection_open_private (f->address, &error);
732 if (failing_conn != NULL)
734 gboolean ok = dbus_bus_register (failing_conn, &error);
739 g_assert (dbus_error_is_set (&error));
740 g_assert_cmpstr (error.name, ==, DBUS_ERROR_LIMITS_EXCEEDED);
742 if (failing_conn != NULL)
743 dbus_connection_close (failing_conn);
745 dbus_clear_connection (&failing_conn);
746 dbus_connection_close (third_conn);
747 dbus_clear_connection (&third_conn);
751 test_max_replies_per_connection (Fixture *f,
752 gconstpointer context)
754 GQueue received = G_QUEUE_INIT;
755 GQueue errors = G_QUEUE_INIT;
759 DBusError error = DBUS_ERROR_INIT;
766 /* The configured limit is 3 replies per connection. */
767 for (i = 0; i < 3; i++)
769 m = dbus_message_new_method_call (
770 dbus_bus_get_unique_name (f->right_conn), "/",
771 "com.example", "Spam");
776 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
777 DBUS_TIMEOUT_INFINITE) ||
781 if (dbus_pending_call_get_completed (pc))
782 pc_enqueue (pc, &received);
783 else if (!dbus_pending_call_set_notify (pc, pc_enqueue, &received,
787 dbus_pending_call_unref (pc);
788 dbus_message_unref (m);
791 while (g_queue_get_length (&f->held_messages) < 3)
792 test_main_context_iterate (f->ctx, TRUE);
794 g_assert_cmpuint (g_queue_get_length (&received), ==, 0);
795 g_assert_cmpuint (g_queue_get_length (&errors), ==, 0);
797 /* Go a couple of messages over the limit. */
798 for (i = 0; i < 2; i++)
800 m = dbus_message_new_method_call (
801 dbus_bus_get_unique_name (f->right_conn), "/",
802 "com.example", "Spam");
807 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
808 DBUS_TIMEOUT_INFINITE) ||
812 if (dbus_pending_call_get_completed (pc))
813 pc_enqueue (pc, &errors);
814 else if (!dbus_pending_call_set_notify (pc, pc_enqueue, &errors,
818 dbus_pending_call_unref (pc);
819 dbus_message_unref (m);
822 /* Reply to the held messages. */
823 for (m = g_queue_pop_head (&f->held_messages);
825 m = g_queue_pop_head (&f->held_messages))
827 DBusMessage *reply = dbus_message_new_method_return (m);
832 if (!dbus_connection_send (f->right_conn, reply, NULL))
835 dbus_clear_message (&m);
836 dbus_clear_message (&reply);
839 /* Wait for all 5 replies to come in. */
840 while (g_queue_get_length (&received) + g_queue_get_length (&errors) < 5)
841 test_main_context_iterate (f->ctx, TRUE);
843 /* The first three succeeded. */
844 for (i = 0; i < 3; i++)
846 m = g_queue_pop_head (&received);
847 g_assert (m != NULL);
849 if (dbus_set_error_from_message (&error, m))
850 g_error ("Unexpected error: %s: %s", error.name, error.message);
852 dbus_clear_message (&m);
855 /* The last two failed. */
856 for (i = 0; i < 2; i++)
858 m = g_queue_pop_head (&errors);
859 g_assert (m != NULL);
861 if (!dbus_set_error_from_message (&error, m))
862 g_error ("Unexpected success");
864 g_assert_cmpstr (error.name, ==, DBUS_ERROR_LIMITS_EXCEEDED);
865 dbus_error_free (&error);
866 dbus_clear_message (&m);
869 g_assert_cmpuint (g_queue_get_length (&received), ==, 0);
870 g_assert_cmpuint (g_queue_get_length (&errors), ==, 0);
871 g_queue_clear (&received);
872 g_queue_clear (&errors);
876 test_max_match_rules_per_connection (Fixture *f,
877 gconstpointer context)
879 DBusError error = DBUS_ERROR_INIT;
884 dbus_bus_add_match (f->left_conn, "sender='com.example.C1'", &error);
885 test_assert_no_error (&error);
886 dbus_bus_add_match (f->left_conn, "sender='com.example.C2'", &error);
887 test_assert_no_error (&error);
888 dbus_bus_add_match (f->left_conn, "sender='com.example.C3'", &error);
889 test_assert_no_error (&error);
891 dbus_bus_add_match (f->left_conn, "sender='com.example.C4'", &error);
892 g_assert_cmpstr (error.name, ==, DBUS_ERROR_LIMITS_EXCEEDED);
893 dbus_error_free (&error);
895 dbus_bus_remove_match (f->left_conn, "sender='com.example.C3'", &error);
896 test_assert_no_error (&error);
898 dbus_bus_add_match (f->left_conn, "sender='com.example.C4'", &error);
899 test_assert_no_error (&error);
903 test_max_names_per_connection (Fixture *f,
904 gconstpointer context)
906 DBusError error = DBUS_ERROR_INIT;
912 /* The limit in the configuration file is set to 4, but we only own 3
913 * names here - remember that the unique name is a name too. */
915 ret = dbus_bus_request_name (f->left_conn, "com.example.C1", 0, &error);
916 test_assert_no_error (&error);
917 g_assert_cmpint (ret, ==, DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER);
919 ret = dbus_bus_request_name (f->left_conn, "com.example.C2", 0, &error);
920 test_assert_no_error (&error);
921 g_assert_cmpint (ret, ==, DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER);
923 ret = dbus_bus_request_name (f->left_conn, "com.example.C3", 0, &error);
924 test_assert_no_error (&error);
925 g_assert_cmpint (ret, ==, DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER);
927 ret = dbus_bus_request_name (f->left_conn, "com.example.C4", 0, &error);
928 g_assert_cmpstr (error.name, ==, DBUS_ERROR_LIMITS_EXCEEDED);
929 dbus_error_free (&error);
930 g_assert_cmpint (ret, ==, -1);
932 ret = dbus_bus_release_name (f->left_conn, "com.example.C3", &error);
933 test_assert_no_error (&error);
934 g_assert_cmpint (ret, ==, DBUS_RELEASE_NAME_REPLY_RELEASED);
936 ret = dbus_bus_request_name (f->left_conn, "com.example.C4", 0, &error);
937 test_assert_no_error (&error);
938 g_assert_cmpint (ret, ==, DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER);
941 #if defined(DBUS_UNIX) && defined(HAVE_UNIX_FD_PASSING) && defined(HAVE_GIO_UNIX)
943 static DBusHandlerResult
944 wait_for_disconnected_cb (DBusConnection *client_conn,
945 DBusMessage *message,
948 gboolean *disconnected = data;
950 if (dbus_message_is_signal (message, DBUS_INTERFACE_LOCAL, "Disconnected"))
952 *disconnected = TRUE;
953 return DBUS_HANDLER_RESULT_HANDLED;
956 return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
959 static const guchar partial_message[] =
962 DBUS_MESSAGE_TYPE_METHOD_CALL,
965 0xff, 0xff, 0, 0, /* length of body = 65535 bytes */
966 1, 2, 3, 4, /* cookie */
967 0xff, 0xff, 0, 0, /* length of header fields array = 65535 bytes */
968 42 /* pretending to be the beginning of the header fields array */
972 send_all_with_fd (GSocket *socket,
973 const guchar *local_partial_message,
977 GSocketControlMessage *fdm = g_unix_fd_message_new ();
978 GError *error = NULL;
980 GOutputVector vector = { local_partial_message, len };
982 g_unix_fd_message_append_fd (G_UNIX_FD_MESSAGE (fdm), fd, &error);
983 g_assert_no_error (error);
985 sent = g_socket_send_message (socket, NULL, &vector, 1, &fdm, 1,
986 G_SOCKET_MSG_NONE, NULL, &error);
987 g_assert_no_error (error);
988 g_assert_cmpint (sent, >=, 1);
989 g_assert_cmpint (sent, <=, vector.size);
991 while (((gsize) sent) < vector.size)
994 vector.buffer = ((const guchar *) vector.buffer) + sent;
995 sent = g_socket_send_message (socket, NULL, &vector, 1, NULL, 0,
996 G_SOCKET_MSG_NONE, NULL, &error);
997 g_assert_no_error (error);
998 g_assert_cmpint (sent, >=, 1);
999 g_assert_cmpint (sent, <=, vector.size);
1002 g_object_unref (fdm);
1006 test_pending_fd_timeout (Fixture *f,
1007 gconstpointer context)
1009 GError *error = NULL;
1014 gboolean disconnected = FALSE;
1021 g_test_skip ("Cannot test, uid 0 is immune to this limit");
1025 have_mem = dbus_connection_add_filter (f->left_conn, wait_for_disconnected_cb,
1026 &disconnected, NULL);
1027 g_assert (have_mem);
1029 /* This is not API. Never do this. */
1031 if (!dbus_connection_get_socket (f->left_conn, &fd))
1032 g_error ("failed to steal fd from left connection");
1034 socket = g_socket_new_from_fd (fd, &error);
1035 g_assert_no_error (error);
1036 g_assert (socket != NULL);
1038 /* We send part of a message that contains a fd, then stop. */
1039 start = g_get_monotonic_time ();
1040 send_all_with_fd (socket, partial_message, G_N_ELEMENTS (partial_message),
1043 while (!disconnected)
1045 test_progress ('.');
1046 test_main_context_iterate (f->ctx, TRUE);
1048 /* It should take 0.5s to get disconnected, as configured in
1049 * valid-config-files/pending-fd-timeout.conf; but this test
1050 * might get starved by other processes running in parallel
1051 * (particularly on shared CI systems), so we have to be a lot
1052 * more generous. Allow up to 10 seconds. */
1053 g_assert_cmpint (g_get_monotonic_time (), <=,
1054 start + (10 * G_USEC_PER_SEC));
1057 g_object_unref (socket);
1064 gboolean should_work;
1067 static const CountFdsVector count_fds_vectors[] =
1069 /* Deny sending if number of fds <= 2 */
1070 { "/test/DenySendMax2", 1, FALSE },
1071 { "/test/DenySendMax2", 2, FALSE },
1072 { "/test/DenySendMax2", 3, TRUE },
1073 { "/test/DenySendMax2", 4, TRUE },
1075 /* Deny receiving if number of fds <= 3 */
1076 { "/test/DenyReceiveMax3", 2, FALSE },
1077 { "/test/DenyReceiveMax3", 3, FALSE },
1078 { "/test/DenyReceiveMax3", 4, TRUE },
1079 { "/test/DenyReceiveMax3", 5, TRUE },
1081 /* Deny sending if number of fds >= 4 */
1082 { "/test/DenySendMin4", 2, TRUE },
1083 { "/test/DenySendMin4", 3, TRUE },
1084 { "/test/DenySendMin4", 4, FALSE },
1085 { "/test/DenySendMin4", 5, FALSE },
1087 /* Deny receiving if number of fds >= 5 */
1088 { "/test/DenyReceiveMin5", 3, TRUE },
1089 { "/test/DenyReceiveMin5", 4, TRUE },
1090 { "/test/DenyReceiveMin5", 5, FALSE },
1091 { "/test/DenyReceiveMin5", 6, FALSE },
1095 test_count_fds (Fixture *f,
1096 gconstpointer context)
1098 GQueue received = G_QUEUE_INIT;
1100 DBusPendingCall *pc;
1102 DBusError error = DBUS_ERROR_INIT;
1103 const int stdin_fd = 0;
1108 add_hold_filter (f);
1110 for (i = 0; i < G_N_ELEMENTS (count_fds_vectors); i++)
1112 const CountFdsVector *vector = &count_fds_vectors[i];
1115 m = dbus_message_new_method_call (
1116 dbus_bus_get_unique_name (f->right_conn), vector->path,
1117 "com.example", "Spam");
1122 for (j = 0; j < vector->n_fds; j++)
1124 if (!dbus_message_append_args (m,
1125 DBUS_TYPE_UNIX_FD, &stdin_fd,
1130 if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
1131 DBUS_TIMEOUT_INFINITE) ||
1135 if (dbus_pending_call_get_completed (pc))
1136 pc_enqueue (pc, &received);
1137 else if (!dbus_pending_call_set_notify (pc, pc_enqueue, &received,
1141 dbus_pending_call_unref (pc);
1142 dbus_message_unref (m);
1144 if (vector->should_work)
1148 while (g_queue_get_length (&f->held_messages) < 1)
1149 test_main_context_iterate (f->ctx, TRUE);
1151 g_assert_cmpint (g_queue_get_length (&f->held_messages), ==, 1);
1153 m = g_queue_pop_head (&f->held_messages);
1155 g_assert_cmpint (g_queue_get_length (&f->held_messages), ==, 0);
1157 reply = dbus_message_new_method_return (m);
1162 if (!dbus_connection_send (f->right_conn, reply, NULL))
1165 dbus_message_unref (reply);
1166 dbus_message_unref (m);
1169 while (g_queue_get_length (&received) < 1)
1170 test_main_context_iterate (f->ctx, TRUE);
1172 g_assert_cmpint (g_queue_get_length (&received), ==, 1);
1173 m = g_queue_pop_head (&received);
1174 g_assert (m != NULL);
1175 g_assert_cmpint (g_queue_get_length (&received), ==, 0);
1177 if (vector->should_work)
1179 if (dbus_set_error_from_message (&error, m))
1180 g_error ("Unexpected error: %s: %s", error.name, error.message);
1182 g_test_message ("Sending %u fds to %s was not denied, as expected",
1183 vector->n_fds, vector->path);
1185 else if (!dbus_set_error_from_message (&error, m))
1187 g_error ("Unexpected success");
1191 g_assert_cmpstr (error.name, ==, DBUS_ERROR_ACCESS_DENIED);
1192 dbus_error_free (&error);
1193 g_test_message ("Sending %u fds to %s was denied, as expected",
1194 vector->n_fds, vector->path);
1197 dbus_message_unref (m);
1204 test_peer_get_machine_id (Fixture *f,
1205 gconstpointer context)
1208 const char *what_daemon_thinks;
1209 DBusMessage *m = NULL;
1210 DBusPendingCall *pc = NULL;
1211 DBusError error = DBUS_ERROR_INIT;
1216 what_i_think = dbus_try_get_local_machine_id (&error);
1218 if (what_i_think == NULL)
1220 if (g_getenv ("DBUS_TEST_UNINSTALLED") != NULL)
1222 /* When running unit tests during make check or make installcheck,
1224 g_test_skip ("Machine UUID not available");
1229 /* When running integration tests, don't tolerate it */
1230 g_error ("%s", error.message);
1234 /* Check that the dbus-daemon agrees with us. */
1235 m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1237 DBUS_INTERFACE_PEER,
1241 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1242 DBUS_TIMEOUT_USE_DEFAULT) ||
1246 dbus_clear_message (&m);
1248 if (dbus_pending_call_get_completed (pc))
1249 test_pending_call_store_reply (pc, &m);
1250 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1255 test_main_context_iterate (f->ctx, TRUE);
1257 if (!dbus_message_get_args (m, &error,
1258 DBUS_TYPE_STRING, &what_daemon_thinks,
1260 g_error ("%s: %s", error.name, error.message);
1262 g_assert_cmpstr (what_i_think, ==, what_daemon_thinks);
1263 g_assert_nonnull (what_daemon_thinks);
1264 g_assert_cmpuint (strlen (what_daemon_thinks), ==, 32);
1266 dbus_clear_message (&m);
1267 dbus_clear_pending_call (&pc);
1268 dbus_free (what_i_think);
1272 test_peer_ping (Fixture *f,
1273 gconstpointer context)
1275 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1276 DBUS_PATH_DBUS, DBUS_INTERFACE_PEER, "Ping");
1277 DBusPendingCall *pc = NULL;
1278 DBusError error = DBUS_ERROR_INIT;
1283 m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1284 DBUS_PATH_DBUS, DBUS_INTERFACE_PEER, "Ping");
1287 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1288 DBUS_TIMEOUT_USE_DEFAULT) ||
1292 dbus_clear_message (&m);
1294 if (dbus_pending_call_get_completed (pc))
1295 test_pending_call_store_reply (pc, &m);
1296 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1301 test_main_context_iterate (f->ctx, TRUE);
1303 if (!dbus_message_get_args (m, &error, DBUS_TYPE_INVALID))
1304 g_error ("%s: %s", error.name, error.message);
1306 dbus_clear_message (&m);
1307 dbus_clear_pending_call (&pc);
1311 test_get_invalid_path (Fixture *f,
1312 gconstpointer context)
1314 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1315 "/", DBUS_INTERFACE_PROPERTIES, "Get");
1316 DBusPendingCall *pc = NULL;
1317 DBusError error = DBUS_ERROR_INIT;
1318 const char *iface = DBUS_INTERFACE_DBUS;
1319 const char *property = "Interfaces";
1325 !dbus_message_append_args (m,
1326 DBUS_TYPE_STRING, &iface,
1327 DBUS_TYPE_STRING, &property,
1328 DBUS_TYPE_INVALID) ||
1329 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1330 DBUS_TIMEOUT_USE_DEFAULT) ||
1334 dbus_clear_message (&m);
1336 if (dbus_pending_call_get_completed (pc))
1337 test_pending_call_store_reply (pc, &m);
1338 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1343 test_main_context_iterate (f->ctx, TRUE);
1345 if (!dbus_set_error_from_message (&error, m))
1346 g_error ("Unexpected success");
1348 /* That object path does not have that interface */
1349 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_INTERFACE);
1350 dbus_error_free (&error);
1352 dbus_clear_message (&m);
1353 dbus_clear_pending_call (&pc);
1357 test_get_invalid_iface (Fixture *f,
1358 gconstpointer context)
1360 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1361 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "Get");
1362 DBusPendingCall *pc = NULL;
1363 DBusError error = DBUS_ERROR_INIT;
1364 const char *iface = "com.example.Nope";
1365 const char *property = "Whatever";
1371 !dbus_message_append_args (m,
1372 DBUS_TYPE_STRING, &iface,
1373 DBUS_TYPE_STRING, &property,
1374 DBUS_TYPE_INVALID) ||
1375 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1376 DBUS_TIMEOUT_USE_DEFAULT) ||
1380 dbus_clear_message (&m);
1382 if (dbus_pending_call_get_completed (pc))
1383 test_pending_call_store_reply (pc, &m);
1384 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1389 test_main_context_iterate (f->ctx, TRUE);
1391 if (!dbus_set_error_from_message (&error, m))
1392 g_error ("Unexpected success");
1394 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_INTERFACE);
1395 dbus_error_free (&error);
1397 dbus_clear_message (&m);
1398 dbus_clear_pending_call (&pc);
1402 test_get_invalid (Fixture *f,
1403 gconstpointer context)
1405 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1406 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "Get");
1407 DBusPendingCall *pc = NULL;
1408 DBusError error = DBUS_ERROR_INIT;
1409 const char *iface = DBUS_INTERFACE_DBUS;
1410 const char *property = "Whatever";
1416 !dbus_message_append_args (m,
1417 DBUS_TYPE_STRING, &iface,
1418 DBUS_TYPE_STRING, &property,
1419 DBUS_TYPE_INVALID) ||
1420 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1421 DBUS_TIMEOUT_USE_DEFAULT) ||
1425 dbus_clear_message (&m);
1427 if (dbus_pending_call_get_completed (pc))
1428 test_pending_call_store_reply (pc, &m);
1429 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1434 test_main_context_iterate (f->ctx, TRUE);
1436 if (!dbus_set_error_from_message (&error, m))
1437 g_error ("Unexpected success");
1439 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_PROPERTY);
1440 dbus_error_free (&error);
1442 dbus_clear_message (&m);
1443 dbus_clear_pending_call (&pc);
1447 test_get_all_invalid_iface (Fixture *f,
1448 gconstpointer context)
1450 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1451 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "GetAll");
1452 DBusPendingCall *pc = NULL;
1453 DBusError error = DBUS_ERROR_INIT;
1454 const char *iface = "com.example.Nope";
1460 !dbus_message_append_args (m,
1461 DBUS_TYPE_STRING, &iface,
1462 DBUS_TYPE_INVALID) ||
1463 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1464 DBUS_TIMEOUT_USE_DEFAULT) ||
1468 dbus_clear_message (&m);
1470 if (dbus_pending_call_get_completed (pc))
1471 test_pending_call_store_reply (pc, &m);
1472 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1477 test_main_context_iterate (f->ctx, TRUE);
1479 if (!dbus_set_error_from_message (&error, m))
1480 g_error ("Unexpected success");
1482 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_INTERFACE);
1483 dbus_error_free (&error);
1485 dbus_clear_message (&m);
1486 dbus_clear_pending_call (&pc);
1490 test_get_all_invalid_path (Fixture *f,
1491 gconstpointer context)
1493 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1494 "/", DBUS_INTERFACE_PROPERTIES, "GetAll");
1495 DBusPendingCall *pc = NULL;
1496 DBusError error = DBUS_ERROR_INIT;
1497 const char *iface = DBUS_INTERFACE_DBUS;
1503 !dbus_message_append_args (m,
1504 DBUS_TYPE_STRING, &iface,
1505 DBUS_TYPE_INVALID) ||
1506 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1507 DBUS_TIMEOUT_USE_DEFAULT) ||
1511 dbus_clear_message (&m);
1513 if (dbus_pending_call_get_completed (pc))
1514 test_pending_call_store_reply (pc, &m);
1515 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1520 test_main_context_iterate (f->ctx, TRUE);
1522 if (!dbus_set_error_from_message (&error, m))
1523 g_error ("Unexpected success");
1525 /* That object path does not have that interface */
1526 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_INTERFACE);
1527 dbus_error_free (&error);
1529 dbus_clear_message (&m);
1530 dbus_clear_pending_call (&pc);
1534 test_set_invalid_iface (Fixture *f,
1535 gconstpointer context)
1537 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1538 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "Set");
1539 DBusPendingCall *pc = NULL;
1540 DBusError error = DBUS_ERROR_INIT;
1541 const char *iface = "com.example.Nope";
1542 const char *property = "Whatever";
1543 DBusMessageIter args_iter;
1544 DBusMessageIter var_iter;
1545 dbus_bool_t b = FALSE;
1551 !dbus_message_append_args (m,
1552 DBUS_TYPE_STRING, &iface,
1553 DBUS_TYPE_STRING, &property,
1557 dbus_message_iter_init_append (m, &args_iter);
1559 if (!dbus_message_iter_open_container (&args_iter,
1560 DBUS_TYPE_VARIANT, "b", &var_iter) ||
1561 !dbus_message_iter_append_basic (&var_iter, DBUS_TYPE_BOOLEAN, &b) ||
1562 !dbus_message_iter_close_container (&args_iter, &var_iter) ||
1563 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1564 DBUS_TIMEOUT_USE_DEFAULT) ||
1568 dbus_clear_message (&m);
1570 if (dbus_pending_call_get_completed (pc))
1571 test_pending_call_store_reply (pc, &m);
1572 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1577 test_main_context_iterate (f->ctx, TRUE);
1579 if (!dbus_set_error_from_message (&error, m))
1580 g_error ("Unexpected success");
1582 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_INTERFACE);
1583 dbus_error_free (&error);
1585 dbus_clear_message (&m);
1586 dbus_clear_pending_call (&pc);
1590 test_set_invalid_path (Fixture *f,
1591 gconstpointer context)
1593 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1594 "/", DBUS_INTERFACE_PROPERTIES, "Set");
1595 DBusPendingCall *pc = NULL;
1596 DBusError error = DBUS_ERROR_INIT;
1597 const char *iface = DBUS_INTERFACE_DBUS;
1598 const char *property = "Interfaces";
1599 DBusMessageIter args_iter;
1600 DBusMessageIter var_iter;
1601 dbus_bool_t b = FALSE;
1607 !dbus_message_append_args (m,
1608 DBUS_TYPE_STRING, &iface,
1609 DBUS_TYPE_STRING, &property,
1613 dbus_message_iter_init_append (m, &args_iter);
1615 if (!dbus_message_iter_open_container (&args_iter,
1616 DBUS_TYPE_VARIANT, "b", &var_iter) ||
1617 !dbus_message_iter_append_basic (&var_iter, DBUS_TYPE_BOOLEAN, &b) ||
1618 !dbus_message_iter_close_container (&args_iter, &var_iter) ||
1619 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1620 DBUS_TIMEOUT_USE_DEFAULT) ||
1624 dbus_clear_message (&m);
1626 if (dbus_pending_call_get_completed (pc))
1627 test_pending_call_store_reply (pc, &m);
1628 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1633 test_main_context_iterate (f->ctx, TRUE);
1635 if (!dbus_set_error_from_message (&error, m))
1636 g_error ("Unexpected success");
1638 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_INTERFACE);
1639 dbus_error_free (&error);
1641 dbus_clear_message (&m);
1642 dbus_clear_pending_call (&pc);
1646 test_set_invalid (Fixture *f,
1647 gconstpointer context)
1649 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1650 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "Set");
1651 DBusPendingCall *pc = NULL;
1652 DBusError error = DBUS_ERROR_INIT;
1653 const char *iface = DBUS_INTERFACE_DBUS;
1654 const char *property = "Whatever";
1655 DBusMessageIter args_iter;
1656 DBusMessageIter var_iter;
1657 dbus_bool_t b = FALSE;
1663 !dbus_message_append_args (m,
1664 DBUS_TYPE_STRING, &iface,
1665 DBUS_TYPE_STRING, &property,
1669 dbus_message_iter_init_append (m, &args_iter);
1671 if (!dbus_message_iter_open_container (&args_iter,
1672 DBUS_TYPE_VARIANT, "b", &var_iter) ||
1673 !dbus_message_iter_append_basic (&var_iter, DBUS_TYPE_BOOLEAN, &b) ||
1674 !dbus_message_iter_close_container (&args_iter, &var_iter) ||
1675 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1676 DBUS_TIMEOUT_USE_DEFAULT) ||
1680 dbus_clear_message (&m);
1682 if (dbus_pending_call_get_completed (pc))
1683 test_pending_call_store_reply (pc, &m);
1684 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1689 test_main_context_iterate (f->ctx, TRUE);
1691 if (!dbus_set_error_from_message (&error, m))
1692 g_error ("Unexpected success");
1694 g_assert_cmpstr (error.name, ==, DBUS_ERROR_UNKNOWN_PROPERTY);
1695 dbus_error_free (&error);
1697 dbus_clear_message (&m);
1698 dbus_clear_pending_call (&pc);
1702 test_set (Fixture *f,
1703 gconstpointer context)
1705 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1706 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "Set");
1707 DBusPendingCall *pc = NULL;
1708 DBusError error = DBUS_ERROR_INIT;
1709 const char *iface = DBUS_INTERFACE_DBUS;
1710 const char *property = "Features";
1711 DBusMessageIter args_iter;
1712 DBusMessageIter var_iter;
1713 dbus_bool_t b = FALSE;
1719 !dbus_message_append_args (m,
1720 DBUS_TYPE_STRING, &iface,
1721 DBUS_TYPE_STRING, &property,
1725 dbus_message_iter_init_append (m, &args_iter);
1727 if (!dbus_message_iter_open_container (&args_iter,
1728 DBUS_TYPE_VARIANT, "b", &var_iter) ||
1729 !dbus_message_iter_append_basic (&var_iter, DBUS_TYPE_BOOLEAN, &b) ||
1730 !dbus_message_iter_close_container (&args_iter, &var_iter) ||
1731 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1732 DBUS_TIMEOUT_USE_DEFAULT) ||
1736 dbus_clear_message (&m);
1738 if (dbus_pending_call_get_completed (pc))
1739 test_pending_call_store_reply (pc, &m);
1740 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1745 test_main_context_iterate (f->ctx, TRUE);
1747 if (!dbus_set_error_from_message (&error, m))
1748 g_error ("Unexpected success");
1750 g_assert_cmpstr (error.name, ==, DBUS_ERROR_PROPERTY_READ_ONLY);
1751 dbus_error_free (&error);
1753 dbus_clear_message (&m);
1754 dbus_clear_pending_call (&pc);
1758 check_features (DBusMessageIter *var_iter)
1760 DBusMessageIter arr_iter;
1761 gboolean have_systemd_activation = FALSE;
1763 g_assert_cmpint (dbus_message_iter_get_arg_type (var_iter), ==,
1765 g_assert_cmpint (dbus_message_iter_get_element_type (var_iter), ==,
1767 dbus_message_iter_recurse (var_iter, &arr_iter);
1769 while (dbus_message_iter_get_arg_type (&arr_iter) != DBUS_TYPE_INVALID)
1771 const char *feature;
1773 g_assert_cmpint (dbus_message_iter_get_arg_type (&arr_iter), ==,
1775 dbus_message_iter_get_basic (&arr_iter, &feature);
1777 g_test_message ("Feature: %s", feature);
1779 if (g_strcmp0 (feature, "SystemdActivation") == 0)
1780 have_systemd_activation = TRUE;
1782 dbus_message_iter_next (&arr_iter);
1785 /* We pass --systemd-activation to the daemon for this unit test on Unix
1786 * (it can only work in practice on Linux, but there's nothing
1787 * inherently Linux-specific about the protocol). */
1789 g_assert_true (have_systemd_activation);
1791 g_assert_false (have_systemd_activation);
1796 test_features (Fixture *f,
1797 gconstpointer context)
1799 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1800 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "Get");
1801 DBusPendingCall *pc = NULL;
1802 DBusMessageIter args_iter;
1803 DBusMessageIter var_iter;
1804 const char *iface = DBUS_INTERFACE_DBUS;
1805 const char *features = "Features";
1811 !dbus_message_append_args (m,
1812 DBUS_TYPE_STRING, &iface,
1813 DBUS_TYPE_STRING, &features,
1814 DBUS_TYPE_INVALID) ||
1815 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1816 DBUS_TIMEOUT_USE_DEFAULT) ||
1820 dbus_clear_message (&m);
1822 if (dbus_pending_call_get_completed (pc))
1823 test_pending_call_store_reply (pc, &m);
1824 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1829 test_main_context_iterate (f->ctx, TRUE);
1831 if (!dbus_message_iter_init (m, &args_iter))
1832 g_error ("Reply has no arguments");
1834 g_assert_cmpint (dbus_message_iter_get_arg_type (&args_iter), ==,
1837 dbus_message_iter_recurse (&args_iter, &var_iter);
1838 check_features (&var_iter);
1840 if (dbus_message_iter_next (&args_iter))
1841 g_error ("Reply has too many arguments");
1843 dbus_clear_message (&m);
1844 dbus_clear_pending_call (&pc);
1848 check_interfaces (DBusMessageIter *var_iter)
1850 DBusMessageIter arr_iter;
1851 gboolean have_monitoring = FALSE;
1852 gboolean have_stats = FALSE;
1853 gboolean have_verbose = FALSE;
1855 g_assert_cmpint (dbus_message_iter_get_arg_type (var_iter), ==,
1857 g_assert_cmpint (dbus_message_iter_get_element_type (var_iter), ==,
1859 dbus_message_iter_recurse (var_iter, &arr_iter);
1861 while (dbus_message_iter_get_arg_type (&arr_iter) != DBUS_TYPE_INVALID)
1865 g_assert_cmpint (dbus_message_iter_get_arg_type (&arr_iter), ==,
1867 dbus_message_iter_get_basic (&arr_iter, &iface);
1868 g_test_message ("Interface: %s", iface);
1870 g_assert_cmpstr (iface, !=, DBUS_INTERFACE_DBUS);
1871 g_assert_cmpstr (iface, !=, DBUS_INTERFACE_PROPERTIES);
1872 g_assert_cmpstr (iface, !=, DBUS_INTERFACE_INTROSPECTABLE);
1873 g_assert_cmpstr (iface, !=, DBUS_INTERFACE_PEER);
1875 if (g_strcmp0 (iface, DBUS_INTERFACE_MONITORING) == 0)
1876 have_monitoring = TRUE;
1877 else if (g_strcmp0 (iface, BUS_INTERFACE_STATS) == 0)
1879 else if (g_strcmp0 (iface, DBUS_INTERFACE_VERBOSE) == 0)
1880 have_verbose = TRUE;
1882 dbus_message_iter_next (&arr_iter);
1885 g_assert_true (have_monitoring);
1887 #ifdef DBUS_ENABLE_STATS
1888 g_assert_true (have_stats);
1890 g_assert_false (have_stats);
1893 #ifdef DBUS_ENABLE_VERBOSE_MODE
1894 g_assert_true (have_verbose);
1896 g_assert_false (have_verbose);
1901 test_interfaces (Fixture *f,
1902 gconstpointer context)
1904 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1905 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "Get");
1906 DBusPendingCall *pc = NULL;
1907 DBusMessageIter args_iter;
1908 DBusMessageIter var_iter;
1909 const char *iface = DBUS_INTERFACE_DBUS;
1910 const char *ifaces = "Interfaces";
1916 !dbus_message_append_args (m,
1917 DBUS_TYPE_STRING, &iface,
1918 DBUS_TYPE_STRING, &ifaces,
1919 DBUS_TYPE_INVALID) ||
1920 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1921 DBUS_TIMEOUT_USE_DEFAULT) ||
1925 dbus_clear_message (&m);
1927 if (dbus_pending_call_get_completed (pc))
1928 test_pending_call_store_reply (pc, &m);
1929 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1934 test_main_context_iterate (f->ctx, TRUE);
1936 if (!dbus_message_iter_init (m, &args_iter))
1937 g_error ("Reply has no arguments");
1939 if (dbus_message_iter_get_arg_type (&args_iter) != DBUS_TYPE_VARIANT)
1940 g_error ("Reply does not have a variant argument");
1942 dbus_message_iter_recurse (&args_iter, &var_iter);
1943 check_interfaces (&var_iter);
1945 if (dbus_message_iter_next (&args_iter))
1946 g_error ("Reply has too many arguments");
1948 dbus_clear_message (&m);
1949 dbus_clear_pending_call (&pc);
1953 test_get_all (Fixture *f,
1954 gconstpointer context)
1956 DBusMessage *m = dbus_message_new_method_call (DBUS_SERVICE_DBUS,
1957 DBUS_PATH_DBUS, DBUS_INTERFACE_PROPERTIES, "GetAll");
1958 DBusPendingCall *pc = NULL;
1959 DBusMessageIter args_iter;
1960 DBusMessageIter arr_iter;
1961 DBusMessageIter pair_iter;
1962 DBusMessageIter var_iter;
1963 const char *iface = DBUS_INTERFACE_DBUS;
1964 gboolean have_features = FALSE;
1965 gboolean have_interfaces = FALSE;
1971 !dbus_message_append_args (m,
1972 DBUS_TYPE_STRING, &iface,
1973 DBUS_TYPE_INVALID) ||
1974 !dbus_connection_send_with_reply (f->left_conn, m, &pc,
1975 DBUS_TIMEOUT_USE_DEFAULT) ||
1979 dbus_clear_message (&m);
1981 if (dbus_pending_call_get_completed (pc))
1982 test_pending_call_store_reply (pc, &m);
1983 else if (!dbus_pending_call_set_notify (pc, test_pending_call_store_reply,
1988 test_main_context_iterate (f->ctx, TRUE);
1990 dbus_message_iter_init (m, &args_iter);
1991 g_assert_cmpuint (dbus_message_iter_get_arg_type (&args_iter), ==,
1993 g_assert_cmpuint (dbus_message_iter_get_element_type (&args_iter), ==,
1994 DBUS_TYPE_DICT_ENTRY);
1995 dbus_message_iter_recurse (&args_iter, &arr_iter);
1997 while (dbus_message_iter_get_arg_type (&arr_iter) != DBUS_TYPE_INVALID)
2001 dbus_message_iter_recurse (&arr_iter, &pair_iter);
2002 g_assert_cmpuint (dbus_message_iter_get_arg_type (&pair_iter), ==,
2004 dbus_message_iter_get_basic (&pair_iter, &name);
2005 dbus_message_iter_next (&pair_iter);
2006 g_assert_cmpuint (dbus_message_iter_get_arg_type (&pair_iter), ==,
2008 dbus_message_iter_recurse (&pair_iter, &var_iter);
2010 if (g_strcmp0 (name, "Features") == 0)
2012 check_features (&var_iter);
2013 have_features = TRUE;
2015 else if (g_strcmp0 (name, "Interfaces") == 0)
2017 check_interfaces (&var_iter);
2018 have_interfaces = TRUE;
2021 dbus_message_iter_next (&arr_iter);
2024 g_assert_true (have_features);
2025 g_assert_true (have_interfaces);
2027 if (dbus_message_iter_next (&args_iter))
2028 g_error ("Reply has too many arguments");
2030 dbus_clear_message (&m);
2031 dbus_clear_pending_call (&pc);
2034 #define DESIRED_RLIMIT 65536
2038 test_fd_limit (Fixture *f,
2039 gconstpointer context)
2043 struct rlimit new_limit;
2044 const struct passwd *pwd = NULL;
2054 g_test_skip ("Cannot test, only uid 0 is expected to raise fd limit");
2058 pwd = getpwnam (DBUS_USER);
2062 gchar *message = g_strdup_printf ("user '%s' does not exist",
2065 g_test_skip (message);
2070 if (prlimit (getpid (), RLIMIT_NOFILE, NULL, &lim) < 0)
2071 g_error ("get prlimit (self): %s", g_strerror (errno));
2073 g_test_message ("our RLIMIT_NOFILE: rlim_cur: %ld, rlim_max: %ld",
2074 (long) lim.rlim_cur, (long) lim.rlim_max);
2076 if (lim.rlim_cur == RLIM_INFINITY || lim.rlim_cur >= DESIRED_RLIMIT)
2078 /* The dbus-daemon will have inherited our large rlimit */
2079 g_test_skip ("Cannot test, our own fd limit was already large");
2084 new_limit.rlim_cur = DESIRED_RLIMIT;
2085 new_limit.rlim_max = DESIRED_RLIMIT;
2087 /* Try to increase the rlimit ourselves. If we're root in an
2088 * unprivileged Linux container, then we won't have CAP_SYS_RESOURCE
2089 * and this will fail with EPERM. If so, the dbus-daemon wouldn't be
2090 * able to increase its rlimit either. */
2091 if (prlimit (getpid (), RLIMIT_NOFILE, &new_limit, NULL) < 0)
2095 message = g_strdup_printf ("Cannot test, we cannot change the rlimit so "
2096 "presumably neither can the dbus-daemon: %s",
2097 g_strerror (errno));
2098 g_test_skip (message);
2103 /* Immediately put our original limit back so it won't interfere with
2104 * subsequent tests. This should always succeed. */
2105 if (prlimit (getpid (), RLIMIT_NOFILE, &lim, NULL) < 0)
2106 g_error ("Cannot restore our original limits: %s", g_strerror (errno));
2108 if (prlimit (f->daemon_pid, RLIMIT_NOFILE, NULL, &lim) < 0)
2109 g_error ("get prlimit (dbus-daemon): %s", g_strerror (errno));
2111 g_test_message ("dbus-daemon's RLIMIT_NOFILE: rlim_cur: %ld, rlim_max: %ld",
2112 (long) lim.rlim_cur, (long) lim.rlim_max);
2114 if (lim.rlim_cur != RLIM_INFINITY)
2115 g_assert_cmpint (lim.rlim_cur, >=, DESIRED_RLIMIT);
2117 #else /* !HAVE_PRLIMIT */
2119 g_test_skip ("prlimit() not supported on this platform");
2121 #endif /* !HAVE_PRLIMIT */
2126 teardown (Fixture *f,
2127 gconstpointer context G_GNUC_UNUSED)
2129 dbus_error_free (&f->e);
2130 g_clear_error (&f->ge);
2132 if (f->left_conn != NULL)
2133 dbus_connection_close (f->left_conn);
2135 if (f->right_conn != NULL)
2137 if (f->right_conn_echo)
2139 dbus_connection_remove_filter (f->right_conn, echo_filter, f);
2140 f->right_conn_echo = FALSE;
2143 if (f->right_conn_hold)
2145 dbus_connection_remove_filter (f->right_conn, hold_filter, f);
2146 f->right_conn_hold = FALSE;
2149 g_queue_foreach (&f->held_messages, (GFunc) dbus_message_unref, NULL);
2150 g_queue_clear (&f->held_messages);
2152 dbus_connection_close (f->right_conn);
2155 dbus_clear_connection (&f->left_conn);
2156 dbus_clear_connection (&f->right_conn);
2158 if (f->daemon_pid != 0)
2160 test_kill_pid (f->daemon_pid);
2161 g_spawn_close_pid (f->daemon_pid);
2165 if (f->tmp_runtime_dir != NULL)
2169 /* the socket may exist */
2170 path = g_strdup_printf ("%s/bus", f->tmp_runtime_dir);
2172 test_remove_if_exists (path);
2174 /* there shouldn't be anything else in there */
2175 test_rmdir_must_exist (f->tmp_runtime_dir);
2177 /* we're relying on being single-threaded for this to be safe */
2178 if (f->saved_runtime_dir != NULL)
2179 g_setenv ("XDG_RUNTIME_DIR", f->saved_runtime_dir, TRUE);
2181 g_unsetenv ("XDG_RUNTIME_DIR");
2182 g_free (f->saved_runtime_dir);
2183 g_free (f->tmp_runtime_dir);
2186 test_main_context_unref (f->ctx);
2187 g_free (f->address);
2190 static Config limited_config = {
2191 "34393", 10000, "valid-config-files/incoming-limit.conf",
2192 TEST_USER_ME, SPECIFY_ADDRESS
2195 static Config finite_timeout_config = {
2196 NULL, 1, "valid-config-files/finite-timeout.conf",
2197 TEST_USER_ME, SPECIFY_ADDRESS
2201 static Config listen_unix_runtime_config = {
2202 "61303", 1, "valid-config-files/listen-unix-runtime.conf",
2203 TEST_USER_ME, RELY_ON_DEFAULT
2207 static Config max_completed_connections_config = {
2208 NULL, 1, "valid-config-files/max-completed-connections.conf",
2209 TEST_USER_ME, SPECIFY_ADDRESS
2212 static Config max_connections_per_user_config = {
2213 NULL, 1, "valid-config-files/max-connections-per-user.conf",
2214 TEST_USER_ME, SPECIFY_ADDRESS
2217 static Config max_replies_per_connection_config = {
2218 NULL, 1, "valid-config-files/max-replies-per-connection.conf",
2219 TEST_USER_ME, SPECIFY_ADDRESS
2222 static Config max_match_rules_per_connection_config = {
2223 NULL, 1, "valid-config-files/max-match-rules-per-connection.conf",
2224 TEST_USER_ME, SPECIFY_ADDRESS
2227 static Config max_names_per_connection_config = {
2228 NULL, 1, "valid-config-files/max-names-per-connection.conf",
2229 TEST_USER_ME, SPECIFY_ADDRESS
2232 #if defined(DBUS_UNIX) && defined(HAVE_UNIX_FD_PASSING) && defined(HAVE_GIO_UNIX)
2233 static Config pending_fd_timeout_config = {
2234 NULL, 1, "valid-config-files/pending-fd-timeout.conf",
2235 TEST_USER_ME, SPECIFY_ADDRESS
2238 static Config count_fds_config = {
2239 NULL, 1, "valid-config-files/count-fds.conf",
2240 TEST_USER_ME, SPECIFY_ADDRESS
2244 #if defined(DBUS_UNIX)
2245 static Config as_another_user_config = {
2246 NULL, 1, "valid-config-files/as-another-user.conf",
2247 /* We start the dbus-daemon as root and drop privileges, like the
2248 * real system bus does */
2249 TEST_USER_ROOT, SPECIFY_ADDRESS
2257 test_init (&argc, &argv);
2259 g_test_add ("/echo/session", Fixture, NULL, setup, test_echo, teardown);
2260 g_test_add ("/echo/limited", Fixture, &limited_config,
2261 setup, test_echo, teardown);
2262 g_test_add ("/no-reply/disconnect", Fixture, NULL,
2263 setup, test_no_reply, teardown);
2264 g_test_add ("/no-reply/timeout", Fixture, &finite_timeout_config,
2265 setup, test_no_reply, teardown);
2266 g_test_add ("/creds", Fixture, NULL, setup, test_creds, teardown);
2267 g_test_add ("/processid", Fixture, NULL, setup, test_processid, teardown);
2268 g_test_add ("/canonical-path/uae", Fixture, NULL,
2269 setup, test_canonical_path_uae, teardown);
2270 g_test_add ("/limits/max-completed-connections", Fixture,
2271 &max_completed_connections_config,
2272 setup, test_max_connections, teardown);
2273 g_test_add ("/limits/max-connections-per-user", Fixture,
2274 &max_connections_per_user_config,
2275 setup, test_max_connections, teardown);
2276 g_test_add ("/limits/max-replies-per-connection", Fixture,
2277 &max_replies_per_connection_config,
2278 setup, test_max_replies_per_connection, teardown);
2279 g_test_add ("/limits/max-match-rules-per-connection", Fixture,
2280 &max_match_rules_per_connection_config,
2281 setup, test_max_match_rules_per_connection, teardown);
2282 g_test_add ("/limits/max-names-per-connection", Fixture,
2283 &max_names_per_connection_config,
2284 setup, test_max_names_per_connection, teardown);
2285 g_test_add ("/peer/ping", Fixture, NULL, setup, test_peer_ping, teardown);
2286 g_test_add ("/peer/get-machine-id", Fixture, NULL,
2287 setup, test_peer_get_machine_id, teardown);
2288 g_test_add ("/properties/get-invalid-iface", Fixture, NULL,
2289 setup, test_get_invalid_iface, teardown);
2290 g_test_add ("/properties/get-invalid-path", Fixture, NULL,
2291 setup, test_get_invalid_path, teardown);
2292 g_test_add ("/properties/get-invalid", Fixture, NULL,
2293 setup, test_get_invalid, teardown);
2294 g_test_add ("/properties/get-all-invalid-iface", Fixture, NULL, setup,
2295 test_get_all_invalid_iface, teardown);
2296 g_test_add ("/properties/get-all-invalid-path", Fixture, NULL, setup,
2297 test_get_all_invalid_path, teardown);
2298 g_test_add ("/properties/set-invalid-iface", Fixture, NULL,
2299 setup, test_set_invalid_iface, teardown);
2300 g_test_add ("/properties/set-invalid-path", Fixture, NULL,
2301 setup, test_set_invalid_path, teardown);
2302 g_test_add ("/properties/set-invalid", Fixture, NULL,
2303 setup, test_set_invalid, teardown);
2304 g_test_add ("/properties/set", Fixture, NULL,
2305 setup, test_set, teardown);
2306 g_test_add ("/properties/features", Fixture, NULL,
2307 setup, test_features, teardown);
2308 g_test_add ("/properties/interfaces", Fixture, NULL, setup,
2309 test_interfaces, teardown);
2310 g_test_add ("/properties/get-all", Fixture, NULL, setup,
2311 test_get_all, teardown);
2313 #if defined(DBUS_UNIX) && defined(HAVE_UNIX_FD_PASSING) && defined(HAVE_GIO_UNIX)
2314 g_test_add ("/limits/pending-fd-timeout", Fixture,
2315 &pending_fd_timeout_config,
2316 setup, test_pending_fd_timeout, teardown);
2317 g_test_add ("/policy/count-fds", Fixture, &count_fds_config,
2318 setup, test_count_fds, teardown);
2322 /* We can't test this in loopback.c with the rest of unix:runtime=yes,
2323 * because dbus_bus_get[_private] is the only way to use the default,
2324 * and that blocks on a round-trip to the dbus-daemon */
2325 g_test_add ("/unix-runtime-is-default", Fixture, &listen_unix_runtime_config,
2326 setup, test_echo, teardown);
2328 g_test_add ("/fd-limit/session", Fixture, NULL,
2329 setup, test_fd_limit, teardown);
2330 g_test_add ("/fd-limit/system", Fixture, &as_another_user_config,
2331 setup, test_fd_limit, teardown);
2334 return g_test_run ();