diff --git a/tools/dbus-send.c b/tools/dbus-send.c index 65f9854e..86858c50 100644 --- a/tools/dbus-send.c +++ b/tools/dbus-send.c @@ -69,6 +69,8 @@ handle_oom (dbus_bool_t success) } } +static int type_from_name (const char *arg, dbus_bool_t allow_container_types); + static void append_arg (DBusMessageIter *iter, int type, const char *value) { @@ -151,6 +153,33 @@ append_arg (DBusMessageIter *iter, int type, const char *value) } break; + case DBUS_TYPE_VARIANT: + { + DBusMessageIter subiter; + + char sig[2] = "\0\0"; + char *subtype = strdup (value); + char *c = NULL; + + handle_oom (subtype != NULL); + c = strchr (subtype, ':'); + if (!c) + { + fprintf (stderr, "%s: missing variant subtype specifier\n", + appname); + exit (1); + } + *c = '\0'; + + sig[0] = (char) type_from_name (subtype, TRUE); + + handle_oom (dbus_message_iter_open_container (iter, DBUS_TYPE_VARIANT, + sig, &subiter)); + append_arg (&subiter, sig[0], c + 1); + free (subtype); + ret = dbus_message_iter_close_container (iter, &subiter); + break; + } default: fprintf (stderr, "%s: Unsupported data type %c\n", appname, (char) type); exit (1); @@ -210,7 +239,7 @@ append_dict (DBusMessageIter *iter, int keytype, int valtype, const char *value) } static int -type_from_name (const char *arg) +type_from_name (const char *arg, dbus_bool_t allow_container_types) { int type; if (!strcmp (arg, "string")) @@ -235,6 +264,16 @@ type_from_name (const char *arg) type = DBUS_TYPE_BOOLEAN; else if (!strcmp (arg, "objpath")) type = DBUS_TYPE_OBJECT_PATH; + else if (!strcmp(arg, "variant")) + { + if (!allow_container_types) + { + fprintf (stderr, "%s: A variant cannot be the key in a dictionary\n", appname); + exit (1); + } + + type = DBUS_TYPE_VARIANT; + } else { fprintf (stderr, "%s: Unknown type \"%s\"\n", appname, arg); @@ -609,7 +648,7 @@ main (int argc, char *argv[]) if (arg[0] == 0) type2 = DBUS_TYPE_STRING; else - type2 = type_from_name (arg); + type2 = type_from_name (arg, FALSE); if (container_type == DBUS_TYPE_DICT_ENTRY) { @@ -622,7 +661,7 @@ main (int argc, char *argv[]) exit (1); } *(c++) = 0; - secondary_type = type_from_name (arg); + secondary_type = type_from_name (arg, TRUE); sig[0] = DBUS_DICT_ENTRY_BEGIN_CHAR; sig[1] = type2; sig[2] = secondary_type;