mirror of
https://gitlab.freedesktop.org/dbus/dbus.git
synced 2026-02-03 10:10:31 +01:00
dbus-daemon test: exercise maximum replies per connection
This time we're doing so deliberately. Bug: https://bugs.freedesktop.org/show_bug.cgi?id=86442 Signed-off-by: Simon McVittie <simon.mcvittie@collabora.co.uk>
This commit is contained in:
parent
78b40bbde8
commit
5cfd755f5d
3 changed files with 197 additions and 0 deletions
|
|
@ -349,6 +349,7 @@ in_data = \
|
|||
data/valid-config-files/incoming-limit.conf.in \
|
||||
data/valid-config-files/max-completed-connections.conf.in \
|
||||
data/valid-config-files/max-connections-per-user.conf.in \
|
||||
data/valid-config-files/max-replies-per-connection.conf.in \
|
||||
data/valid-config-files/multi-user.conf.in \
|
||||
data/valid-config-files/systemd-activation.conf.in \
|
||||
data/invalid-service-files-system/org.freedesktop.DBus.TestSuiteNoExec.service.in \
|
||||
|
|
|
|||
|
|
@ -0,0 +1,18 @@
|
|||
<!DOCTYPE busconfig PUBLIC "-//freedesktop//DTD D-Bus Bus Configuration 1.0//EN"
|
||||
"http://www.freedesktop.org/standards/dbus/1.0/busconfig.dtd">
|
||||
<busconfig>
|
||||
<!-- Our well-known bus type, don't change this -->
|
||||
<type>session</type>
|
||||
<listen>@TEST_LISTEN@</listen>
|
||||
|
||||
<policy context="default">
|
||||
<!-- Allow everything to be sent -->
|
||||
<allow send_destination="*" eavesdrop="true"/>
|
||||
<!-- Allow everything to be received -->
|
||||
<allow eavesdrop="true"/>
|
||||
<!-- Allow anyone to own anything -->
|
||||
<allow own="*"/>
|
||||
</policy>
|
||||
|
||||
<limit name="max_replies_per_connection">3</limit>
|
||||
</busconfig>
|
||||
|
|
@ -83,7 +83,9 @@ typedef struct {
|
|||
DBusConnection *left_conn;
|
||||
|
||||
DBusConnection *right_conn;
|
||||
GQueue held_messages;
|
||||
gboolean right_conn_echo;
|
||||
gboolean right_conn_hold;
|
||||
gboolean wait_forever_called;
|
||||
|
||||
gchar *tmp_runtime_dir;
|
||||
|
|
@ -121,6 +123,21 @@ echo_filter (DBusConnection *connection,
|
|||
return DBUS_HANDLER_RESULT_HANDLED;
|
||||
}
|
||||
|
||||
static DBusHandlerResult
|
||||
hold_filter (DBusConnection *connection,
|
||||
DBusMessage *message,
|
||||
void *user_data)
|
||||
{
|
||||
Fixture *f = user_data;
|
||||
|
||||
if (dbus_message_get_type (message) != DBUS_MESSAGE_TYPE_METHOD_CALL)
|
||||
return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
|
||||
|
||||
g_queue_push_tail (&f->held_messages, dbus_message_ref (message));
|
||||
|
||||
return DBUS_HANDLER_RESULT_HANDLED;
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
const char *bug_ref;
|
||||
guint min_messages;
|
||||
|
|
@ -186,6 +203,15 @@ add_echo_filter (Fixture *f)
|
|||
f->right_conn_echo = TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
add_hold_filter (Fixture *f)
|
||||
{
|
||||
if (!dbus_connection_add_filter (f->right_conn, hold_filter, f, NULL))
|
||||
g_error ("OOM");
|
||||
|
||||
f->right_conn_hold = TRUE;
|
||||
}
|
||||
|
||||
static void
|
||||
pc_count (DBusPendingCall *pc,
|
||||
void *data)
|
||||
|
|
@ -195,6 +221,17 @@ pc_count (DBusPendingCall *pc,
|
|||
(*received_p)++;
|
||||
}
|
||||
|
||||
static void
|
||||
pc_enqueue (DBusPendingCall *pc,
|
||||
void *data)
|
||||
{
|
||||
GQueue *q = data;
|
||||
DBusMessage *m = dbus_pending_call_steal_reply (pc);
|
||||
|
||||
g_test_message ("message of type %d", dbus_message_get_type (m));
|
||||
g_queue_push_tail (q, m);
|
||||
}
|
||||
|
||||
static void
|
||||
test_echo (Fixture *f,
|
||||
gconstpointer context)
|
||||
|
|
@ -686,6 +723,130 @@ test_max_connections (Fixture *f,
|
|||
dbus_connection_unref (third_conn);
|
||||
}
|
||||
|
||||
static void
|
||||
test_max_replies_per_connection (Fixture *f,
|
||||
gconstpointer context)
|
||||
{
|
||||
GQueue received = G_QUEUE_INIT;
|
||||
GQueue errors = G_QUEUE_INIT;
|
||||
DBusMessage *m;
|
||||
DBusPendingCall *pc;
|
||||
guint i;
|
||||
DBusError error = DBUS_ERROR_INIT;
|
||||
|
||||
if (f->skip)
|
||||
return;
|
||||
|
||||
add_hold_filter (f);
|
||||
|
||||
/* The configured limit is 3 replies per connection. */
|
||||
for (i = 0; i < 3; i++)
|
||||
{
|
||||
m = dbus_message_new_method_call (
|
||||
dbus_bus_get_unique_name (f->right_conn), "/",
|
||||
"com.example", "Spam");
|
||||
|
||||
if (m == NULL)
|
||||
g_error ("OOM");
|
||||
|
||||
if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
|
||||
DBUS_TIMEOUT_INFINITE) ||
|
||||
pc == NULL)
|
||||
g_error ("OOM");
|
||||
|
||||
if (dbus_pending_call_get_completed (pc))
|
||||
pc_enqueue (pc, &received);
|
||||
else if (!dbus_pending_call_set_notify (pc, pc_enqueue, &received,
|
||||
NULL))
|
||||
g_error ("OOM");
|
||||
|
||||
dbus_pending_call_unref (pc);
|
||||
dbus_message_unref (m);
|
||||
}
|
||||
|
||||
while (g_queue_get_length (&f->held_messages) < 3)
|
||||
test_main_context_iterate (f->ctx, TRUE);
|
||||
|
||||
g_assert_cmpuint (g_queue_get_length (&received), ==, 0);
|
||||
g_assert_cmpuint (g_queue_get_length (&errors), ==, 0);
|
||||
|
||||
/* Go a couple of messages over the limit. */
|
||||
for (i = 0; i < 2; i++)
|
||||
{
|
||||
m = dbus_message_new_method_call (
|
||||
dbus_bus_get_unique_name (f->right_conn), "/",
|
||||
"com.example", "Spam");
|
||||
|
||||
if (m == NULL)
|
||||
g_error ("OOM");
|
||||
|
||||
if (!dbus_connection_send_with_reply (f->left_conn, m, &pc,
|
||||
DBUS_TIMEOUT_INFINITE) ||
|
||||
pc == NULL)
|
||||
g_error ("OOM");
|
||||
|
||||
if (dbus_pending_call_get_completed (pc))
|
||||
pc_enqueue (pc, &errors);
|
||||
else if (!dbus_pending_call_set_notify (pc, pc_enqueue, &errors,
|
||||
NULL))
|
||||
g_error ("OOM");
|
||||
|
||||
dbus_pending_call_unref (pc);
|
||||
dbus_message_unref (m);
|
||||
}
|
||||
|
||||
/* Reply to the held messages. */
|
||||
for (m = g_queue_pop_head (&f->held_messages);
|
||||
m != NULL;
|
||||
m = g_queue_pop_head (&f->held_messages))
|
||||
{
|
||||
DBusMessage *reply = dbus_message_new_method_return (m);
|
||||
|
||||
if (reply == NULL)
|
||||
g_error ("OOM");
|
||||
|
||||
if (!dbus_connection_send (f->right_conn, reply, NULL))
|
||||
g_error ("OOM");
|
||||
|
||||
dbus_message_unref (reply);
|
||||
}
|
||||
|
||||
/* Wait for all 5 replies to come in. */
|
||||
while (g_queue_get_length (&received) + g_queue_get_length (&errors) < 5)
|
||||
test_main_context_iterate (f->ctx, TRUE);
|
||||
|
||||
/* The first three succeeded. */
|
||||
for (i = 0; i < 3; i++)
|
||||
{
|
||||
m = g_queue_pop_head (&received);
|
||||
g_assert (m != NULL);
|
||||
|
||||
if (dbus_set_error_from_message (&error, m))
|
||||
g_error ("Unexpected error: %s: %s", error.name, error.message);
|
||||
|
||||
dbus_message_unref (m);
|
||||
}
|
||||
|
||||
/* The last two failed. */
|
||||
for (i = 0; i < 2; i++)
|
||||
{
|
||||
m = g_queue_pop_head (&errors);
|
||||
g_assert (m != NULL);
|
||||
|
||||
if (!dbus_set_error_from_message (&error, m))
|
||||
g_error ("Unexpected success");
|
||||
|
||||
g_assert_cmpstr (error.name, ==, DBUS_ERROR_LIMITS_EXCEEDED);
|
||||
dbus_error_free (&error);
|
||||
dbus_message_unref (m);
|
||||
}
|
||||
|
||||
g_assert_cmpuint (g_queue_get_length (&received), ==, 0);
|
||||
g_assert_cmpuint (g_queue_get_length (&errors), ==, 0);
|
||||
g_queue_clear (&received);
|
||||
g_queue_clear (&errors);
|
||||
}
|
||||
|
||||
static void
|
||||
teardown (Fixture *f,
|
||||
gconstpointer context G_GNUC_UNUSED)
|
||||
|
|
@ -708,6 +869,15 @@ teardown (Fixture *f,
|
|||
f->right_conn_echo = FALSE;
|
||||
}
|
||||
|
||||
if (f->right_conn_hold)
|
||||
{
|
||||
dbus_connection_remove_filter (f->right_conn, hold_filter, f);
|
||||
f->right_conn_hold = FALSE;
|
||||
}
|
||||
|
||||
g_queue_foreach (&f->held_messages, (GFunc) dbus_message_unref, NULL);
|
||||
g_queue_clear (&f->held_messages);
|
||||
|
||||
dbus_connection_close (f->right_conn);
|
||||
dbus_connection_unref (f->right_conn);
|
||||
f->right_conn = NULL;
|
||||
|
|
@ -771,6 +941,11 @@ static Config max_connections_per_user_config = {
|
|||
SPECIFY_ADDRESS
|
||||
};
|
||||
|
||||
static Config max_replies_per_connection_config = {
|
||||
NULL, 1, "valid-config-files/max-replies-per-connection.conf",
|
||||
SPECIFY_ADDRESS
|
||||
};
|
||||
|
||||
int
|
||||
main (int argc,
|
||||
char **argv)
|
||||
|
|
@ -794,6 +969,9 @@ main (int argc,
|
|||
g_test_add ("/limits/max-connections-per-user", Fixture,
|
||||
&max_connections_per_user_config,
|
||||
setup, test_max_connections, teardown);
|
||||
g_test_add ("/limits/max-replies-per-connection", Fixture,
|
||||
&max_replies_per_connection_config,
|
||||
setup, test_max_replies_per_connection, teardown);
|
||||
#ifdef DBUS_UNIX
|
||||
/* We can't test this in loopback.c with the rest of unix:runtime=yes,
|
||||
* because dbus_bus_get[_private] is the only way to use the default,
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue