mirror of
https://gitlab.gnome.org/GNOME/glib.git
synced 2025-01-11 23:16:14 +01:00
Merge branch '3061-dbus-name-crash' into 'main'
gdbusmessage: Validate required headers have the right type Closes #3061 See merge request GNOME/glib!3539
This commit is contained in:
commit
137956e700
@ -3966,10 +3966,22 @@ distribute_signals (GDBusConnection *connection,
|
|||||||
GDBusMessage *message)
|
GDBusMessage *message)
|
||||||
{
|
{
|
||||||
GPtrArray *signal_data_array;
|
GPtrArray *signal_data_array;
|
||||||
const gchar *sender;
|
const gchar *sender, *interface, *member, *path;
|
||||||
|
|
||||||
|
g_assert (g_dbus_message_get_message_type (message) == G_DBUS_MESSAGE_TYPE_SIGNAL);
|
||||||
|
|
||||||
sender = g_dbus_message_get_sender (message);
|
sender = g_dbus_message_get_sender (message);
|
||||||
|
|
||||||
|
/* all three of these are required, but should have been validated already
|
||||||
|
* by validate_headers() in gdbusmessage.c */
|
||||||
|
interface = g_dbus_message_get_interface (message);
|
||||||
|
member = g_dbus_message_get_member (message);
|
||||||
|
path = g_dbus_message_get_path (message);
|
||||||
|
|
||||||
|
g_assert (interface != NULL);
|
||||||
|
g_assert (member != NULL);
|
||||||
|
g_assert (path != NULL);
|
||||||
|
|
||||||
if (G_UNLIKELY (_g_dbus_debug_signal ()))
|
if (G_UNLIKELY (_g_dbus_debug_signal ()))
|
||||||
{
|
{
|
||||||
_g_dbus_debug_print_lock ();
|
_g_dbus_debug_print_lock ();
|
||||||
@ -3978,9 +3990,7 @@ distribute_signals (GDBusConnection *connection,
|
|||||||
" <<<< RECEIVED SIGNAL %s.%s\n"
|
" <<<< RECEIVED SIGNAL %s.%s\n"
|
||||||
" on object %s\n"
|
" on object %s\n"
|
||||||
" sent by name %s\n",
|
" sent by name %s\n",
|
||||||
g_dbus_message_get_interface (message),
|
interface, member, path,
|
||||||
g_dbus_message_get_member (message),
|
|
||||||
g_dbus_message_get_path (message),
|
|
||||||
sender != NULL ? sender : "(none)");
|
sender != NULL ? sender : "(none)");
|
||||||
_g_dbus_debug_print_unlock ();
|
_g_dbus_debug_print_unlock ();
|
||||||
}
|
}
|
||||||
@ -7186,19 +7196,26 @@ distribute_method_call (GDBusConnection *connection,
|
|||||||
GDBusMessage *reply;
|
GDBusMessage *reply;
|
||||||
ExportedObject *eo;
|
ExportedObject *eo;
|
||||||
ExportedSubtree *es;
|
ExportedSubtree *es;
|
||||||
const gchar *object_path;
|
const gchar *path;
|
||||||
const gchar *interface_name;
|
const gchar *interface_name;
|
||||||
const gchar *member;
|
const gchar *member;
|
||||||
const gchar *path;
|
|
||||||
gchar *subtree_path;
|
gchar *subtree_path;
|
||||||
gchar *needle;
|
gchar *needle;
|
||||||
gboolean object_found = FALSE;
|
gboolean object_found = FALSE;
|
||||||
|
|
||||||
g_assert (g_dbus_message_get_message_type (message) == G_DBUS_MESSAGE_TYPE_METHOD_CALL);
|
g_assert (g_dbus_message_get_message_type (message) == G_DBUS_MESSAGE_TYPE_METHOD_CALL);
|
||||||
|
|
||||||
interface_name = g_dbus_message_get_interface (message);
|
/* these are required, and should have been validated by validate_headers()
|
||||||
|
* in gdbusmessage.c already */
|
||||||
member = g_dbus_message_get_member (message);
|
member = g_dbus_message_get_member (message);
|
||||||
path = g_dbus_message_get_path (message);
|
path = g_dbus_message_get_path (message);
|
||||||
|
|
||||||
|
g_assert (member != NULL);
|
||||||
|
g_assert (path != NULL);
|
||||||
|
|
||||||
|
/* this is optional */
|
||||||
|
interface_name = g_dbus_message_get_interface (message);
|
||||||
|
|
||||||
subtree_path = g_strdup (path);
|
subtree_path = g_strdup (path);
|
||||||
needle = strrchr (subtree_path, '/');
|
needle = strrchr (subtree_path, '/');
|
||||||
if (needle != NULL && needle != subtree_path)
|
if (needle != NULL && needle != subtree_path)
|
||||||
@ -7211,7 +7228,6 @@ distribute_method_call (GDBusConnection *connection,
|
|||||||
subtree_path = NULL;
|
subtree_path = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (G_UNLIKELY (_g_dbus_debug_incoming ()))
|
if (G_UNLIKELY (_g_dbus_debug_incoming ()))
|
||||||
{
|
{
|
||||||
_g_dbus_debug_print_lock ();
|
_g_dbus_debug_print_lock ();
|
||||||
@ -7228,17 +7244,14 @@ distribute_method_call (GDBusConnection *connection,
|
|||||||
_g_dbus_debug_print_unlock ();
|
_g_dbus_debug_print_unlock ();
|
||||||
}
|
}
|
||||||
|
|
||||||
object_path = g_dbus_message_get_path (message);
|
eo = g_hash_table_lookup (connection->map_object_path_to_eo, path);
|
||||||
g_assert (object_path != NULL);
|
|
||||||
|
|
||||||
eo = g_hash_table_lookup (connection->map_object_path_to_eo, object_path);
|
|
||||||
if (eo != NULL)
|
if (eo != NULL)
|
||||||
{
|
{
|
||||||
if (obj_message_func (connection, eo, message, &object_found))
|
if (obj_message_func (connection, eo, message, &object_found))
|
||||||
goto out;
|
goto out;
|
||||||
}
|
}
|
||||||
|
|
||||||
es = g_hash_table_lookup (connection->map_object_path_to_es, object_path);
|
es = g_hash_table_lookup (connection->map_object_path_to_es, path);
|
||||||
if (es != NULL)
|
if (es != NULL)
|
||||||
{
|
{
|
||||||
if (subtree_message_func (connection, es, message))
|
if (subtree_message_func (connection, es, message))
|
||||||
@ -7265,14 +7278,14 @@ distribute_method_call (GDBusConnection *connection,
|
|||||||
"org.freedesktop.DBus.Error.UnknownMethod",
|
"org.freedesktop.DBus.Error.UnknownMethod",
|
||||||
_("No such interface “%s” on object at path %s"),
|
_("No such interface “%s” on object at path %s"),
|
||||||
interface_name,
|
interface_name,
|
||||||
object_path);
|
path);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
reply = g_dbus_message_new_method_error (message,
|
reply = g_dbus_message_new_method_error (message,
|
||||||
"org.freedesktop.DBus.Error.UnknownMethod",
|
"org.freedesktop.DBus.Error.UnknownMethod",
|
||||||
_("Object does not exist at path “%s”"),
|
_("Object does not exist at path “%s”"),
|
||||||
object_path);
|
path);
|
||||||
}
|
}
|
||||||
|
|
||||||
g_dbus_connection_send_message_unlocked (connection, reply, G_DBUS_SEND_MESSAGE_FLAGS_NONE, NULL, NULL);
|
g_dbus_connection_send_message_unlocked (connection, reply, G_DBUS_SEND_MESSAGE_FLAGS_NONE, NULL, NULL);
|
||||||
|
@ -1308,67 +1308,99 @@ validate_headers (GDBusMessage *message,
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case G_DBUS_MESSAGE_TYPE_METHOD_CALL:
|
case G_DBUS_MESSAGE_TYPE_METHOD_CALL:
|
||||||
if (g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_PATH) == NULL ||
|
{
|
||||||
g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_MEMBER) == NULL)
|
GVariant *path_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_PATH);
|
||||||
{
|
GVariant *member_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_MEMBER);
|
||||||
g_set_error_literal (error,
|
|
||||||
G_IO_ERROR,
|
if (path_variant == NULL ||
|
||||||
G_IO_ERROR_INVALID_ARGUMENT,
|
!g_variant_is_of_type (path_variant, G_VARIANT_TYPE_OBJECT_PATH) ||
|
||||||
_("METHOD_CALL message: PATH or MEMBER header field is missing"));
|
member_variant == NULL ||
|
||||||
goto out;
|
!g_variant_is_of_type (member_variant, G_VARIANT_TYPE_STRING) ||
|
||||||
}
|
!g_dbus_is_member_name (g_variant_get_string (member_variant, NULL)))
|
||||||
|
{
|
||||||
|
g_set_error_literal (error,
|
||||||
|
G_IO_ERROR,
|
||||||
|
G_IO_ERROR_INVALID_ARGUMENT,
|
||||||
|
_("METHOD_CALL message: PATH or MEMBER header field is missing or invalid"));
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case G_DBUS_MESSAGE_TYPE_METHOD_RETURN:
|
case G_DBUS_MESSAGE_TYPE_METHOD_RETURN:
|
||||||
if (g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL) == NULL)
|
{
|
||||||
{
|
GVariant *reply_serial_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL);
|
||||||
g_set_error_literal (error,
|
|
||||||
G_IO_ERROR,
|
if (reply_serial_variant == NULL ||
|
||||||
G_IO_ERROR_INVALID_ARGUMENT,
|
!g_variant_is_of_type (reply_serial_variant, G_VARIANT_TYPE_UINT32))
|
||||||
_("METHOD_RETURN message: REPLY_SERIAL header field is missing"));
|
{
|
||||||
goto out;
|
g_set_error_literal (error,
|
||||||
}
|
G_IO_ERROR,
|
||||||
|
G_IO_ERROR_INVALID_ARGUMENT,
|
||||||
|
_("METHOD_RETURN message: REPLY_SERIAL header field is missing or invalid"));
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case G_DBUS_MESSAGE_TYPE_ERROR:
|
case G_DBUS_MESSAGE_TYPE_ERROR:
|
||||||
if (g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_ERROR_NAME) == NULL ||
|
{
|
||||||
g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL) == NULL)
|
GVariant *error_name_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_ERROR_NAME);
|
||||||
{
|
GVariant *reply_serial_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL);
|
||||||
g_set_error_literal (error,
|
|
||||||
G_IO_ERROR,
|
if (error_name_variant == NULL ||
|
||||||
G_IO_ERROR_INVALID_ARGUMENT,
|
!g_variant_is_of_type (error_name_variant, G_VARIANT_TYPE_STRING) ||
|
||||||
_("ERROR message: REPLY_SERIAL or ERROR_NAME header field is missing"));
|
!g_dbus_is_error_name (g_variant_get_string (error_name_variant, NULL)) ||
|
||||||
goto out;
|
reply_serial_variant == NULL ||
|
||||||
}
|
!g_variant_is_of_type (reply_serial_variant, G_VARIANT_TYPE_UINT32))
|
||||||
|
{
|
||||||
|
g_set_error_literal (error,
|
||||||
|
G_IO_ERROR,
|
||||||
|
G_IO_ERROR_INVALID_ARGUMENT,
|
||||||
|
_("ERROR message: REPLY_SERIAL or ERROR_NAME header field is missing or invalid"));
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case G_DBUS_MESSAGE_TYPE_SIGNAL:
|
case G_DBUS_MESSAGE_TYPE_SIGNAL:
|
||||||
if (g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_PATH) == NULL ||
|
{
|
||||||
g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_INTERFACE) == NULL ||
|
GVariant *path_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_PATH);
|
||||||
g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_MEMBER) == NULL)
|
GVariant *interface_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_INTERFACE);
|
||||||
{
|
GVariant *member_variant = g_dbus_message_get_header (message, G_DBUS_MESSAGE_HEADER_FIELD_MEMBER);
|
||||||
g_set_error_literal (error,
|
|
||||||
G_IO_ERROR,
|
if (path_variant == NULL ||
|
||||||
G_IO_ERROR_INVALID_ARGUMENT,
|
!g_variant_is_of_type (path_variant, G_VARIANT_TYPE_OBJECT_PATH) ||
|
||||||
_("SIGNAL message: PATH, INTERFACE or MEMBER header field is missing"));
|
interface_variant == NULL ||
|
||||||
goto out;
|
!g_variant_is_of_type (interface_variant, G_VARIANT_TYPE_STRING) ||
|
||||||
}
|
!g_dbus_is_interface_name (g_variant_get_string (interface_variant, NULL)) ||
|
||||||
if (g_strcmp0 (g_dbus_message_get_path (message), "/org/freedesktop/DBus/Local") == 0)
|
member_variant == NULL ||
|
||||||
{
|
!g_variant_is_of_type (member_variant, G_VARIANT_TYPE_STRING) ||
|
||||||
g_set_error_literal (error,
|
!g_dbus_is_member_name (g_variant_get_string (member_variant, NULL)))
|
||||||
G_IO_ERROR,
|
{
|
||||||
G_IO_ERROR_INVALID_ARGUMENT,
|
g_set_error_literal (error,
|
||||||
_("SIGNAL message: The PATH header field is using the reserved value /org/freedesktop/DBus/Local"));
|
G_IO_ERROR,
|
||||||
goto out;
|
G_IO_ERROR_INVALID_ARGUMENT,
|
||||||
}
|
_("SIGNAL message: PATH, INTERFACE or MEMBER header field is missing or invalid"));
|
||||||
if (g_strcmp0 (g_dbus_message_get_interface (message), "org.freedesktop.DBus.Local") == 0)
|
goto out;
|
||||||
{
|
}
|
||||||
g_set_error_literal (error,
|
if (g_strcmp0 (g_dbus_message_get_path (message), "/org/freedesktop/DBus/Local") == 0)
|
||||||
G_IO_ERROR,
|
{
|
||||||
G_IO_ERROR_INVALID_ARGUMENT,
|
g_set_error_literal (error,
|
||||||
_("SIGNAL message: The INTERFACE header field is using the reserved value org.freedesktop.DBus.Local"));
|
G_IO_ERROR,
|
||||||
goto out;
|
G_IO_ERROR_INVALID_ARGUMENT,
|
||||||
}
|
_("SIGNAL message: The PATH header field is using the reserved value /org/freedesktop/DBus/Local"));
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
if (g_strcmp0 (g_dbus_message_get_interface (message), "org.freedesktop.DBus.Local") == 0)
|
||||||
|
{
|
||||||
|
g_set_error_literal (error,
|
||||||
|
G_IO_ERROR,
|
||||||
|
G_IO_ERROR_INVALID_ARGUMENT,
|
||||||
|
_("SIGNAL message: The INTERFACE header field is using the reserved value org.freedesktop.DBus.Local"));
|
||||||
|
goto out;
|
||||||
|
}
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
|
@ -936,7 +936,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_interface (message, NULL);
|
g_dbus_message_set_interface (message, NULL);
|
||||||
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: SIGNAL message: PATH, INTERFACE or MEMBER header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: SIGNAL message: PATH, INTERFACE or MEMBER header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
/* interface reserved value => error */
|
/* interface reserved value => error */
|
||||||
@ -953,7 +953,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_path (message, NULL);
|
g_dbus_message_set_path (message, NULL);
|
||||||
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: SIGNAL message: PATH, INTERFACE or MEMBER header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: SIGNAL message: PATH, INTERFACE or MEMBER header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
/* path reserved value => error */
|
/* path reserved value => error */
|
||||||
@ -970,7 +970,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_member (message, NULL);
|
g_dbus_message_set_member (message, NULL);
|
||||||
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: SIGNAL message: PATH, INTERFACE or MEMBER header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: SIGNAL message: PATH, INTERFACE or MEMBER header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
/* reset member */
|
/* reset member */
|
||||||
@ -988,7 +988,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_path (message, NULL);
|
g_dbus_message_set_path (message, NULL);
|
||||||
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: METHOD_CALL message: PATH or MEMBER header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: METHOD_CALL message: PATH or MEMBER header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
/* reset path */
|
/* reset path */
|
||||||
@ -998,7 +998,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_member (message, NULL);
|
g_dbus_message_set_member (message, NULL);
|
||||||
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (message, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: METHOD_CALL message: PATH or MEMBER header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: METHOD_CALL message: PATH or MEMBER header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
/* reset member */
|
/* reset member */
|
||||||
@ -1018,7 +1018,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_header (reply, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL, NULL);
|
g_dbus_message_set_header (reply, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL, NULL);
|
||||||
blob = g_dbus_message_to_blob (reply, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (reply, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: METHOD_RETURN message: REPLY_SERIAL header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: METHOD_RETURN message: REPLY_SERIAL header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
g_object_unref (reply);
|
g_object_unref (reply);
|
||||||
@ -1029,7 +1029,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_error_name (reply, NULL);
|
g_dbus_message_set_error_name (reply, NULL);
|
||||||
blob = g_dbus_message_to_blob (reply, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (reply, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: ERROR message: REPLY_SERIAL or ERROR_NAME header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: ERROR message: REPLY_SERIAL or ERROR_NAME header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
/* reset ERROR_NAME */
|
/* reset ERROR_NAME */
|
||||||
@ -1038,7 +1038,7 @@ test_message_serialize_header_checks (void)
|
|||||||
g_dbus_message_set_header (reply, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL, NULL);
|
g_dbus_message_set_header (reply, G_DBUS_MESSAGE_HEADER_FIELD_REPLY_SERIAL, NULL);
|
||||||
blob = g_dbus_message_to_blob (reply, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
blob = g_dbus_message_to_blob (reply, &blob_size, G_DBUS_CAPABILITY_FLAGS_NONE, &error);
|
||||||
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
g_assert_error (error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
g_assert_cmpstr (error->message, ==, "Cannot serialize message: ERROR message: REPLY_SERIAL or ERROR_NAME header field is missing");
|
g_assert_cmpstr (error->message, ==, "Cannot serialize message: ERROR message: REPLY_SERIAL or ERROR_NAME header field is missing or invalid");
|
||||||
g_clear_error (&error);
|
g_clear_error (&error);
|
||||||
g_assert_null (blob);
|
g_assert_null (blob);
|
||||||
g_object_unref (reply);
|
g_object_unref (reply);
|
||||||
@ -1615,6 +1615,127 @@ test_message_serialize_empty_structure (void)
|
|||||||
g_clear_object (&message);
|
g_clear_object (&message);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
test_message_parse_missing_header (void)
|
||||||
|
{
|
||||||
|
const guint8 data[] = {
|
||||||
|
'l', /* little-endian byte order */
|
||||||
|
0x01, /* message type (method call) */
|
||||||
|
0x00, /* message flags (none) */
|
||||||
|
0x01, /* major protocol version */
|
||||||
|
0x12, 0x00, 0x00, 0x00, /* body length (in bytes) */
|
||||||
|
0x20, 0x20, 0x20, 0x20, /* message serial */
|
||||||
|
/* a{yv} of header fields: */
|
||||||
|
0x24, 0x00, 0x00, 0x00, /* array length (in bytes), must be a multiple of 8 */
|
||||||
|
0x01, /* array key (PATH, required for method call messages) */
|
||||||
|
/* Variant array value: */
|
||||||
|
0x01, /* signature length */
|
||||||
|
'o', /* one complete type */
|
||||||
|
0x00, /* nul terminator */
|
||||||
|
/* (Variant array value payload) */
|
||||||
|
0x01, 0x00, 0x00, 0x00,
|
||||||
|
'/', 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x30, /* array key (MEMBER, required for method call messages; CORRUPTED from 0x03) */
|
||||||
|
/* Variant array value: */
|
||||||
|
0x01, /* signature length */
|
||||||
|
's', /* one complete type */
|
||||||
|
0x00, /* nul terminator */
|
||||||
|
/* (Variant array value payload) */
|
||||||
|
0x03, 0x00, 0x00, 0x00,
|
||||||
|
'H', 'e', 'y', 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x08, /* array key (SIGNATURE) */
|
||||||
|
/* Variant array value: */
|
||||||
|
0x01, /* signature length */
|
||||||
|
'g', /* one complete type */
|
||||||
|
0x00, /* nul terminator */
|
||||||
|
/* (Variant array value payload) */
|
||||||
|
0x02, 's', 's', 0x00,
|
||||||
|
/* Some arbitrary valid content inside the message body: */
|
||||||
|
0x03, 0x00, 0x00, 0x00,
|
||||||
|
'h', 'e', 'y', 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00,
|
||||||
|
't', 'h', 'e', 'r', 'e', 0x00
|
||||||
|
};
|
||||||
|
|
||||||
|
gsize size = sizeof (data);
|
||||||
|
GDBusMessage *message = NULL;
|
||||||
|
GError *local_error = NULL;
|
||||||
|
|
||||||
|
g_test_summary ("Test that missing (required) headers prompt an error.");
|
||||||
|
g_test_bug ("https://gitlab.gnome.org/GNOME/glib/-/issues/3061");
|
||||||
|
|
||||||
|
message = g_dbus_message_new_from_blob ((guchar *) data, size,
|
||||||
|
G_DBUS_CAPABILITY_FLAGS_NONE,
|
||||||
|
&local_error);
|
||||||
|
g_assert_error (local_error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
|
g_assert_null (message);
|
||||||
|
|
||||||
|
g_clear_error (&local_error);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
test_message_parse_invalid_header_type (void)
|
||||||
|
{
|
||||||
|
const guint8 data[] = {
|
||||||
|
'l', /* little-endian byte order */
|
||||||
|
0x01, /* message type (method call) */
|
||||||
|
0x00, /* message flags (none) */
|
||||||
|
0x01, /* major protocol version */
|
||||||
|
0x12, 0x00, 0x00, 0x00, /* body length (in bytes) */
|
||||||
|
0x20, 0x20, 0x20, 0x20, /* message serial */
|
||||||
|
/* a{yv} of header fields: */
|
||||||
|
0x24, 0x00, 0x00, 0x00, /* array length (in bytes), must be a multiple of 8 */
|
||||||
|
0x01, /* array key (PATH, required for method call messages) */
|
||||||
|
/* Variant array value: */
|
||||||
|
0x01, /* signature length */
|
||||||
|
'o', /* one complete type */
|
||||||
|
0x00, /* nul terminator */
|
||||||
|
/* (Variant array value payload) */
|
||||||
|
0x01, 0x00, 0x00, 0x00,
|
||||||
|
'/', 0x00, 0x00, 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x03, /* array key (MEMBER, required for method call messages) */
|
||||||
|
/* Variant array value: */
|
||||||
|
0x01, /* signature length */
|
||||||
|
't', /* one complete type; CORRUPTED, MEMBER should be 's' */
|
||||||
|
0x00, /* nul terminator */
|
||||||
|
/* (Padding to 64-bit alignment of 't)' */
|
||||||
|
0x00, 0x00, 0x00, 0x00,
|
||||||
|
/* (Variant array value payload) */
|
||||||
|
'H', 'e', 'y', 0x00,
|
||||||
|
0x00, 0x00, 0x00, 0x00,
|
||||||
|
0x08, /* array key (SIGNATURE) */
|
||||||
|
/* Variant array value: */
|
||||||
|
0x01, /* signature length */
|
||||||
|
'g', /* one complete type */
|
||||||
|
0x00, /* nul terminator */
|
||||||
|
/* (Variant array value payload) */
|
||||||
|
0x02, 's', 's', 0x00,
|
||||||
|
/* Some arbitrary valid content inside the message body: */
|
||||||
|
0x03, 0x00, 0x00, 0x00,
|
||||||
|
'h', 'e', 'y', 0x00,
|
||||||
|
0x05, 0x00, 0x00, 0x00,
|
||||||
|
't', 'h', 'e', 'r', 'e', 0x00
|
||||||
|
};
|
||||||
|
|
||||||
|
gsize size = sizeof (data);
|
||||||
|
GDBusMessage *message = NULL;
|
||||||
|
GError *local_error = NULL;
|
||||||
|
|
||||||
|
g_test_summary ("Test that the type of well-known headers is checked.");
|
||||||
|
g_test_bug ("https://gitlab.gnome.org/GNOME/glib/-/issues/3061");
|
||||||
|
|
||||||
|
message = g_dbus_message_new_from_blob ((guchar *) data, size,
|
||||||
|
G_DBUS_CAPABILITY_FLAGS_NONE,
|
||||||
|
&local_error);
|
||||||
|
g_assert_error (local_error, G_IO_ERROR, G_IO_ERROR_INVALID_ARGUMENT);
|
||||||
|
g_assert_null (message);
|
||||||
|
|
||||||
|
g_clear_error (&local_error);
|
||||||
|
}
|
||||||
|
|
||||||
/* ---------------------------------------------------------------------------------------------------- */
|
/* ---------------------------------------------------------------------------------------------------- */
|
||||||
|
|
||||||
int
|
int
|
||||||
@ -1657,6 +1778,10 @@ main (int argc,
|
|||||||
test_message_parse_truncated);
|
test_message_parse_truncated);
|
||||||
g_test_add_func ("/gdbus/message-parse/empty-structure",
|
g_test_add_func ("/gdbus/message-parse/empty-structure",
|
||||||
test_message_parse_empty_structure);
|
test_message_parse_empty_structure);
|
||||||
|
g_test_add_func ("/gdbus/message-parse/missing-header",
|
||||||
|
test_message_parse_missing_header);
|
||||||
|
g_test_add_func ("/gdbus/message-parse/invalid-header-type",
|
||||||
|
test_message_parse_invalid_header_type);
|
||||||
|
|
||||||
return g_test_run();
|
return g_test_run();
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user