diff options
author | Dan Winship <danw@gnome.org> | 2014-09-03 12:27:33 -0400 |
---|---|---|
committer | Dan Winship <danw@gnome.org> | 2014-09-18 11:26:59 -0400 |
commit | 1a5cfc1f458fe4c7955b535e44116b56266d57ce (patch) | |
tree | 917774282f1ae9fac450041facc91868031be7f5 /callouts | |
parent | 408e86dd35c8a49a9592d06e588ffbc7c98c87e3 (diff) |
dispatcher: port to GDBus
Port nm-dispatcher to GDBus, mostly, using dbus-glib's GVariant
utilities to translate the return value of nm_connection_to_dbus().
Diffstat (limited to 'callouts')
-rw-r--r-- | callouts/Makefile.am | 33 | ||||
-rw-r--r-- | callouts/nm-dispatcher-api.h | 4 | ||||
-rw-r--r-- | callouts/nm-dispatcher-utils.c | 292 | ||||
-rw-r--r-- | callouts/nm-dispatcher-utils.h | 18 | ||||
-rw-r--r-- | callouts/nm-dispatcher.c | 258 | ||||
-rw-r--r-- | callouts/nm-dispatcher.xml | 4 | ||||
-rw-r--r-- | callouts/tests/test-dispatcher-envp.c | 255 |
7 files changed, 389 insertions, 475 deletions
diff --git a/callouts/Makefile.am b/callouts/Makefile.am index 1d1eb3c764..d305554cc0 100644 --- a/callouts/Makefile.am +++ b/callouts/Makefile.am @@ -46,11 +46,33 @@ nm_dispatcher_SOURCES = \ nm_dispatcher_LDADD = \ $(top_builddir)/libnm/libnm.la \ - $(DBUS_LIBS) \ + libnmdbus-dispatcher.la \ $(GLIB_LIBS) -nm-dispatcher-glue.h: nm-dispatcher.xml - $(AM_V_GEN) dbus-binding-tool --prefix=nm_dispatcher --mode=glib-server --output=$@ $< +# We have to build the gdbus generated code separately, without +# -DGLIB_VERSION_MAX_ALLOWED, due to a bug in GLib 2.38 + +noinst_LTLIBRARIES += libnmdbus-dispatcher.la + +libnmdbus_dispatcher_la_SOURCES = \ + nmdbus-dispatcher.c \ + nmdbus-dispatcher.h + +libnmdbus_dispatcher_la_CPPFLAGS = $(filter-out -DGLIB_VERSION_MAX_ALLOWED%,$(AM_CPPFLAGS)) + +nmdbus-dispatcher.h: nm-dispatcher.xml + $(AM_V_GEN) gdbus-codegen \ + --generate-c-code $(basename $@) \ + --c-namespace NMDBus \ + --interface-prefix org.freedesktop \ + $< + +nmdbus-dispatcher.c: nmdbus-dispatcher.h + @true + +BUILT_SOURCES = \ + nmdbus-dispatcher.c \ + nmdbus-dispatcher.h ########################################### # dispatcher envp @@ -65,8 +87,7 @@ libtest_dispatcher_envp_la_CPPFLAGS = \ libtest_dispatcher_envp_la_LIBADD = \ $(top_builddir)/libnm/libnm.la \ - $(GLIB_LIBS) \ - $(DBUS_LIBS) + $(GLIB_LIBS) if WITH_UDEV_DIR @@ -93,8 +114,6 @@ install-data-hook: $(mkinstalldirs) -m 0755 $(DESTDIR)$(dispatcherdir)/pre-down.d $(mkinstalldirs) -m 0755 $(DESTDIR)$(dispatcherdir)/pre-up.d -BUILT_SOURCES = nm-dispatcher-glue.h - CLEANFILES = $(BUILT_SOURCES) $(dbusactivation_DATA) EXTRA_DIST = \ diff --git a/callouts/nm-dispatcher-api.h b/callouts/nm-dispatcher-api.h index bc156aa0f7..df1bced456 100644 --- a/callouts/nm-dispatcher-api.h +++ b/callouts/nm-dispatcher-api.h @@ -18,13 +18,11 @@ * Copyright (C) 2008 - 2012 Red Hat, Inc. */ -#include <dbus/dbus-glib.h> - #define NMD_SCRIPT_DIR_DEFAULT NMCONFDIR "/dispatcher.d" #define NMD_SCRIPT_DIR_PRE_UP NMD_SCRIPT_DIR_DEFAULT "/pre-up.d" #define NMD_SCRIPT_DIR_PRE_DOWN NMD_SCRIPT_DIR_DEFAULT "/pre-down.d" -/* dbus-glib types for dispatcher call return value */ +/* dbus-glib types for dispatcher call return value (used by src/nm-dispatcher.c) */ #define DISPATCHER_TYPE_RESULT (dbus_g_type_get_struct ("GValueArray", G_TYPE_STRING, G_TYPE_UINT, G_TYPE_STRING, G_TYPE_INVALID)) #define DISPATCHER_TYPE_RESULT_ARRAY (dbus_g_type_get_collection ("GPtrArray", DISPATCHER_TYPE_RESULT)) diff --git a/callouts/nm-dispatcher-utils.c b/callouts/nm-dispatcher-utils.c index 567c4773a6..9a16880a57 100644 --- a/callouts/nm-dispatcher-utils.c +++ b/callouts/nm-dispatcher-utils.c @@ -24,7 +24,6 @@ #include <glib-object.h> #include <nm-dbus-interface.h> -#include <nm-dbus-glib-types.h> #include <nm-connection.h> #include <nm-setting-ip4-config.h> #include <nm-setting-ip6-config.h> @@ -55,25 +54,26 @@ construct_basic_items (GSList *list, static GSList * add_domains (GSList *items, - GHashTable *hash, + GVariant *dict, const char *prefix, const char four_or_six) { - GValue *val; + GVariant *val; char **domains = NULL; GString *tmp; guint i; /* Search domains */ - val = g_hash_table_lookup (hash, "domains"); + val = g_variant_lookup_value (dict, "domains", G_VARIANT_TYPE_STRING_ARRAY); if (!val) return items; - g_return_val_if_fail (G_VALUE_HOLDS (val, G_TYPE_STRV), items); - - domains = (char **) g_value_get_boxed (val); - if (!domains || !domains[0]) + domains = g_variant_dup_strv (val, NULL); + g_variant_unref (val); + if (!domains[0]) { + g_strfreev (domains); return items; + } tmp = g_string_new (NULL); g_string_append_printf (tmp, "%sIP%c_DOMAINS=", prefix, four_or_six); @@ -82,22 +82,22 @@ add_domains (GSList *items, g_string_append_c (tmp, ' '); g_string_append (tmp, domains[i]); } - items = g_slist_prepend (items, tmp->str); - g_string_free (tmp, FALSE); + items = g_slist_prepend (items, g_string_free (tmp, FALSE)); + g_strfreev (domains); return items; } static GSList * -construct_ip4_items (GSList *items, GHashTable *ip4_config, const char *prefix) +construct_ip4_items (GSList *items, GVariant *ip4_config, const char *prefix) { - GSList *addresses, *routes, *iter; - GArray *dns, *wins; - guint32 num, i; + GPtrArray *addresses, *routes; + char **dns, **wins; GString *tmp; - GValue *val; + GVariant *val; char str_addr[INET_ADDRSTRLEN]; char str_gw[INET_ADDRSTRLEN]; + int i; if (ip4_config == NULL) return items; @@ -106,84 +106,78 @@ construct_ip4_items (GSList *items, GHashTable *ip4_config, const char *prefix) prefix = ""; /* IP addresses */ - val = g_hash_table_lookup (ip4_config, "addresses"); + val = g_variant_lookup_value (ip4_config, "addresses", G_VARIANT_TYPE ("aau")); if (val) { - addresses = nm_utils_ip4_addresses_from_gvalue (val); + addresses = nm_utils_ip4_addresses_from_variant (val); - for (iter = addresses, num = 0; iter; iter = g_slist_next (iter)) { - NMIP4Address *addr = (NMIP4Address *) iter->data; + for (i = 0; i < addresses->len; i++) { + NMIP4Address *addr = addresses->pdata[i]; guint32 ip_prefix = nm_ip4_address_get_prefix (addr); char *addrtmp; nm_utils_inet4_ntop (nm_ip4_address_get_address (addr), str_addr); nm_utils_inet4_ntop (nm_ip4_address_get_gateway (addr), str_gw); - addrtmp = g_strdup_printf ("%sIP4_ADDRESS_%d=%s/%d %s", prefix, num++, str_addr, ip_prefix, str_gw); + addrtmp = g_strdup_printf ("%sIP4_ADDRESS_%d=%s/%d %s", prefix, i, str_addr, ip_prefix, str_gw); items = g_slist_prepend (items, addrtmp); } - if (num) - items = g_slist_prepend (items, g_strdup_printf ("%sIP4_NUM_ADDRESSES=%d", prefix, num)); - g_slist_free_full (addresses, (GDestroyNotify) nm_ip4_address_unref); + if (addresses->len) + items = g_slist_prepend (items, g_strdup_printf ("%sIP4_NUM_ADDRESSES=%d", prefix, addresses->len)); + g_ptr_array_unref (addresses); + g_variant_unref (val); } /* DNS servers */ - val = g_hash_table_lookup (ip4_config, "nameservers"); - if (val && G_VALUE_HOLDS (val, DBUS_TYPE_G_UINT_ARRAY)) { - dns = (GArray *) g_value_get_boxed (val); - - if (dns && (dns->len > 0)) { - gboolean first = TRUE; + val = g_variant_lookup_value (ip4_config, "nameservers", G_VARIANT_TYPE ("au")); + if (val) { + dns = nm_utils_ip4_dns_from_variant (val); + if (dns[0]) { tmp = g_string_new (NULL); g_string_append_printf (tmp, "%sIP4_NAMESERVERS=", prefix); - for (i = 0; i < dns->len; i++) { - guint32 addr; - - addr = g_array_index (dns, guint32, i); - if (!first) + for (i = 0; dns[i]; i++) { + if (i != 0) g_string_append_c (tmp, ' '); - g_string_append (tmp, nm_utils_inet4_ntop (addr, NULL)); - first = FALSE; + g_string_append (tmp, dns[i]); } - items = g_slist_prepend (items, tmp->str); - g_string_free (tmp, FALSE); + + items = g_slist_prepend (items, g_string_free (tmp, FALSE)); } + g_strfreev (dns); + g_variant_unref (val); } /* Search domains */ items = add_domains (items, ip4_config, prefix, '4'); /* WINS servers */ - val = g_hash_table_lookup (ip4_config, "wins-servers"); - if (val && G_VALUE_HOLDS (val, DBUS_TYPE_G_UINT_ARRAY)) { - wins = (GArray *) g_value_get_boxed (val); - - if (wins && wins->len) { - gboolean first = TRUE; + val = g_variant_lookup_value (ip4_config, "wins-servers", G_VARIANT_TYPE ("au")); + if (val) { + wins = nm_utils_ip4_dns_from_variant (val); + if (wins[0]) { tmp = g_string_new (NULL); g_string_append_printf (tmp, "%sIP4_WINS_SERVERS=", prefix); - for (i = 0; i < wins->len; i++) { - guint32 addr; - addr = g_array_index (wins, guint32, i); - if (!first) + for (i = 0; wins[i]; i++) { + if (i != 0) g_string_append_c (tmp, ' '); - g_string_append (tmp, nm_utils_inet4_ntop (addr, NULL)); - first = FALSE; + g_string_append (tmp, wins[i]); } - items = g_slist_prepend (items, tmp->str); - g_string_free (tmp, FALSE); + + items = g_slist_prepend (items, g_string_free (tmp, FALSE)); } + g_strfreev (wins); + g_variant_unref (val); } /* Static routes */ - val = g_hash_table_lookup (ip4_config, "routes"); + val = g_variant_lookup_value (ip4_config, "routes", G_VARIANT_TYPE ("aau")); if (val) { - routes = nm_utils_ip4_routes_from_gvalue (val); + routes = nm_utils_ip4_routes_from_variant (val); - for (iter = routes, num = 0; iter; iter = g_slist_next (iter)) { - NMIP4Route *route = (NMIP4Route *) iter->data; + for (i = 0; i < routes->len; i++) { + NMIP4Route *route = routes->pdata[i]; guint32 ip_prefix = nm_ip4_route_get_prefix (route); guint32 metric = nm_ip4_route_get_metric (route); char *routetmp; @@ -191,11 +185,12 @@ construct_ip4_items (GSList *items, GHashTable *ip4_config, const char *prefix) nm_utils_inet4_ntop (nm_ip4_route_get_dest (route), str_addr); nm_utils_inet4_ntop (nm_ip4_route_get_next_hop (route), str_gw); - routetmp = g_strdup_printf ("%sIP4_ROUTE_%d=%s/%d %s %d", prefix, num++, str_addr, ip_prefix, str_gw, metric); + routetmp = g_strdup_printf ("%sIP4_ROUTE_%d=%s/%d %s %d", prefix, i, str_addr, ip_prefix, str_gw, metric); items = g_slist_prepend (items, routetmp); } - items = g_slist_prepend (items, g_strdup_printf ("%sIP4_NUM_ROUTES=%d", prefix, num)); - g_slist_free_full (routes, (GDestroyNotify) nm_ip4_route_unref); + items = g_slist_prepend (items, g_strdup_printf ("%sIP4_NUM_ROUTES=%d", prefix, routes->len)); + g_ptr_array_unref (routes); + g_variant_unref (val); } else items = g_slist_prepend (items, g_strdup_printf ("%sIP4_NUM_ROUTES=0", prefix)); @@ -203,20 +198,20 @@ construct_ip4_items (GSList *items, GHashTable *ip4_config, const char *prefix) } static GSList * -construct_device_dhcp4_items (GSList *items, GHashTable *dhcp4_config) +construct_device_dhcp4_items (GSList *items, GVariant *dhcp4_config) { - GHashTableIter iter; + GVariantIter iter; const char *key, *tmp; - GValue *val; + GVariant *val; char *ucased; if (dhcp4_config == NULL) return items; - g_hash_table_iter_init (&iter, dhcp4_config); - while (g_hash_table_iter_next (&iter, (gpointer) &key, (gpointer) &val)) { + g_variant_iter_init (&iter, dhcp4_config); + while (g_variant_iter_next (&iter, "{&sv}", &key, &val)) { ucased = g_ascii_strup (key, -1); - tmp = g_value_get_string (val); + tmp = g_variant_get_string (val, NULL); items = g_slist_prepend (items, g_strdup_printf ("DHCP4_%s=%s", ucased, tmp)); g_free (ucased); } @@ -224,14 +219,15 @@ construct_device_dhcp4_items (GSList *items, GHashTable *dhcp4_config) } static GSList * -construct_ip6_items (GSList *items, GHashTable *ip6_config, const char *prefix) +construct_ip6_items (GSList *items, GVariant *ip6_config, const char *prefix) { - GSList *addresses, *routes, *dns, *iter; - guint32 num; + GPtrArray *addresses, *routes; + char **dns; GString *tmp; - GValue *val; + GVariant *val; char str_addr[INET6_ADDRSTRLEN]; char str_gw[INET6_ADDRSTRLEN]; + int i; if (ip6_config == NULL) return items; @@ -240,61 +236,58 @@ construct_ip6_items (GSList *items, GHashTable *ip6_config, const char *prefix) prefix = ""; /* IP addresses */ - val = g_hash_table_lookup (ip6_config, "addresses"); + val = g_variant_lookup_value (ip6_config, "addresses", G_VARIANT_TYPE ("a(ayuay)")); if (val) { - addresses = nm_utils_ip6_addresses_from_gvalue (val); + addresses = nm_utils_ip6_addresses_from_variant (val); - for (iter = addresses, num = 0; iter; iter = g_slist_next (iter)) { - NMIP6Address *addr = (NMIP6Address *) iter->data; + for (i = 0; i < addresses->len; i++) { + NMIP6Address *addr = addresses->pdata[i]; guint32 ip_prefix = nm_ip6_address_get_prefix (addr); char *addrtmp; nm_utils_inet6_ntop (nm_ip6_address_get_address (addr), str_addr); nm_utils_inet6_ntop (nm_ip6_address_get_gateway (addr), str_gw); - addrtmp = g_strdup_printf ("%sIP6_ADDRESS_%d=%s/%d %s", prefix, num++, str_addr, ip_prefix, str_gw); + addrtmp = g_strdup_printf ("%sIP6_ADDRESS_%d=%s/%d %s", prefix, i, str_addr, ip_prefix, str_gw); items = g_slist_prepend (items, addrtmp); } - if (num) - items = g_slist_prepend (items, g_strdup_printf ("%sIP6_NUM_ADDRESSES=%d", prefix, num)); - g_slist_free_full (addresses, (GDestroyNotify) nm_ip6_address_unref); + if (addresses->len) + items = g_slist_prepend (items, g_strdup_printf ("%sIP6_NUM_ADDRESSES=%d", prefix, addresses->len)); + g_ptr_array_unref (addresses); + g_variant_unref (val); } /* DNS servers */ - val = g_hash_table_lookup (ip6_config, "nameservers"); + val = g_variant_lookup_value (ip6_config, "nameservers", G_VARIANT_TYPE ("aay")); if (val) { - dns = nm_utils_ip6_dns_from_gvalue (val); - - if (g_slist_length (dns)) { - gboolean first = TRUE; + dns = nm_utils_ip6_dns_from_variant (val); + if (dns[0]) { tmp = g_string_new (NULL); g_string_append_printf (tmp, "%sIP6_NAMESERVERS=", prefix); - for (iter = dns; iter; iter = g_slist_next (iter)) { - const struct in6_addr *addr = iter->data; - - if (!first) + for (i = 0; dns[i]; i++) { + if (i != 0) g_string_append_c (tmp, ' '); - g_string_append (tmp, nm_utils_inet6_ntop (addr, NULL)); - first = FALSE; + g_string_append (tmp, dns[i]); } - items = g_slist_prepend (items, tmp->str); - g_string_free (tmp, FALSE); + items = g_slist_prepend (items, g_string_free (tmp, FALSE)); } + g_strfreev (dns); + g_variant_unref (val); } /* Search domains */ items = add_domains (items, ip6_config, prefix, '6'); /* Static routes */ - val = g_hash_table_lookup (ip6_config, "routes"); + val = g_variant_lookup_value (ip6_config, "routes", G_VARIANT_TYPE ("a(ayuayu)")); if (val) { - routes = nm_utils_ip6_routes_from_gvalue (val); + routes = nm_utils_ip6_routes_from_variant (val); - for (iter = routes, num = 0; iter; iter = g_slist_next (iter)) { - NMIP6Route *route = (NMIP6Route *) iter->data; + for (i = 0; i < routes->len; i++) { + NMIP6Route *route = routes->pdata[i]; guint32 ip_prefix = nm_ip6_route_get_prefix (route); guint32 metric = nm_ip6_route_get_metric (route); char *routetmp; @@ -302,32 +295,33 @@ construct_ip6_items (GSList *items, GHashTable *ip6_config, const char *prefix) nm_utils_inet6_ntop (nm_ip6_route_get_dest (route), str_addr); nm_utils_inet6_ntop (nm_ip6_route_get_next_hop (route), str_gw); - routetmp = g_strdup_printf ("%sIP6_ROUTE_%d=%s/%d %s %d", prefix, num++, str_addr, ip_prefix, str_gw, metric); + routetmp = g_strdup_printf ("%sIP6_ROUTE_%d=%s/%d %s %d", prefix, i, str_addr, ip_prefix, str_gw, metric); items = g_slist_prepend (items, routetmp); } - if (num) - items = g_slist_prepend (items, g_strdup_printf ("%sIP6_NUM_ROUTES=%d", prefix, num)); - g_slist_free_full (routes, (GDestroyNotify) nm_ip6_route_unref); + if (routes->len) + items = g_slist_prepend (items, g_strdup_printf ("%sIP6_NUM_ROUTES=%d", prefix, routes->len)); + g_ptr_array_unref (routes); + g_variant_unref (val); } return items; } static GSList * -construct_device_dhcp6_items (GSList *items, GHashTable *dhcp6_config) +construct_device_dhcp6_items (GSList *items, GVariant *dhcp6_config) { - GHashTableIter iter; + GVariantIter iter; const char *key, *tmp; - GValue *val; + GVariant *val; char *ucased; if (dhcp6_config == NULL) return items; - g_hash_table_iter_init (&iter, dhcp6_config); - while (g_hash_table_iter_next (&iter, (gpointer) &key, (gpointer) &val)) { + g_variant_iter_init (&iter, dhcp6_config); + while (g_variant_iter_next (&iter, "{&sv}", &key, &val)) { ucased = g_ascii_strup (key, -1); - tmp = g_value_get_string (val); + tmp = g_variant_get_string (val, NULL); items = g_slist_prepend (items, g_strdup_printf ("DHCP6_%s=%s", ucased, tmp)); g_free (ucased); } @@ -336,26 +330,26 @@ construct_device_dhcp6_items (GSList *items, GHashTable *dhcp6_config) char ** nm_dispatcher_utils_construct_envp (const char *action, - GHashTable *connection_hash, - GHashTable *connection_props, - GHashTable *device_props, - GHashTable *device_ip4_props, - GHashTable *device_ip6_props, - GHashTable *device_dhcp4_props, - GHashTable *device_dhcp6_props, + GVariant *connection_dict, + GVariant *connection_props, + GVariant *device_props, + GVariant *device_ip4_props, + GVariant *device_ip6_props, + GVariant *device_dhcp4_props, + GVariant *device_dhcp6_props, const char *vpn_ip_iface, - GHashTable *vpn_ip4_props, - GHashTable *vpn_ip6_props, + GVariant *vpn_ip4_props, + GVariant *vpn_ip6_props, char **out_iface) { const char *iface = NULL, *ip_iface = NULL; const char *uuid = NULL, *id = NULL, *path; NMDeviceState dev_state = NM_DEVICE_STATE_UNKNOWN; - GValue *value; + GVariant *value; char **envp = NULL, *path_item; GSList *items = NULL, *iter; guint i; - GHashTable *con_setting_hash; + GVariant *con_setting; g_return_val_if_fail (action != NULL, NULL); g_return_val_if_fail (out_iface != NULL, NULL); @@ -371,69 +365,67 @@ nm_dispatcher_utils_construct_envp (const char *action, if (vpn_ip_iface && !strlen (vpn_ip_iface)) vpn_ip_iface = NULL; - con_setting_hash = g_hash_table_lookup (connection_hash, NM_SETTING_CONNECTION_SETTING_NAME); - if (!con_setting_hash) { - g_warning ("Failed to read connection setting"); - return NULL; - } - - value = g_hash_table_lookup (con_setting_hash, NM_SETTING_CONNECTION_UUID); - if (!value || !G_VALUE_HOLDS (value, G_TYPE_STRING)) { - g_warning ("Connection hash did not contain the UUID"); - return NULL; - } - uuid = g_value_get_string (value); - - value = g_hash_table_lookup (con_setting_hash, NM_SETTING_CONNECTION_ID); - if (!value || !G_VALUE_HOLDS (value, G_TYPE_STRING)) { - g_warning ("Connection hash did not contain the ID"); - return NULL; - } - id = g_value_get_string (value); - /* interface name */ - value = g_hash_table_lookup (device_props, NMD_DEVICE_PROPS_INTERFACE); - if (!value || !G_VALUE_HOLDS_STRING (value)) { + if (!g_variant_lookup (device_props, NMD_DEVICE_PROPS_INTERFACE, "&s", &iface)) { g_warning ("Missing or invalid required value " NMD_DEVICE_PROPS_INTERFACE "!"); return NULL; } - iface = g_value_get_string (value); - if (iface && !strlen (iface)) + if (!*iface) iface = NULL; /* IP interface name */ - value = g_hash_table_lookup (device_props, NMD_DEVICE_PROPS_IP_INTERFACE); + value = g_variant_lookup_value (device_props, NMD_DEVICE_PROPS_IP_INTERFACE, NULL); if (value) { - if (!G_VALUE_HOLDS_STRING (value)) { - g_warning ("Invalid required value " NMD_DEVICE_PROPS_IP_INTERFACE "!"); + if (!g_variant_is_of_type (value, G_VARIANT_TYPE_STRING)) { + g_warning ("Invalid value " NMD_DEVICE_PROPS_IP_INTERFACE "!"); return NULL; } - ip_iface = g_value_get_string (value); + g_variant_unref (value); + g_variant_lookup (device_props, NMD_DEVICE_PROPS_IP_INTERFACE, "&s", &ip_iface); } /* Device type */ - value = g_hash_table_lookup (device_props, NMD_DEVICE_PROPS_TYPE); - if (!value || !G_VALUE_HOLDS_UINT (value)) { + if (!g_variant_lookup (device_props, NMD_DEVICE_PROPS_TYPE, "u", NULL)) { g_warning ("Missing or invalid required value " NMD_DEVICE_PROPS_TYPE "!"); return NULL; } /* Device state */ - value = g_hash_table_lookup (device_props, NMD_DEVICE_PROPS_STATE); - if (!value || !G_VALUE_HOLDS_UINT (value)) { + value = g_variant_lookup_value (device_props, NMD_DEVICE_PROPS_STATE, G_VARIANT_TYPE_UINT32); + if (!value) { g_warning ("Missing or invalid required value " NMD_DEVICE_PROPS_STATE "!"); return NULL; } - dev_state = g_value_get_uint (value); + dev_state = g_variant_get_uint32 (value); + g_variant_unref (value); /* device itself */ - value = g_hash_table_lookup (device_props, NMD_DEVICE_PROPS_PATH); - if (!value || (G_VALUE_TYPE (value) != DBUS_TYPE_G_OBJECT_PATH)) { + if (!g_variant_lookup (device_props, NMD_DEVICE_PROPS_PATH, "o", NULL)) { g_warning ("Missing or invalid required value " NMD_DEVICE_PROPS_PATH "!"); return NULL; } + /* UUID and ID */ + con_setting = g_variant_lookup_value (connection_dict, NM_SETTING_CONNECTION_SETTING_NAME, G_VARIANT_TYPE ("a{sv}")); + if (!con_setting) { + g_warning ("Failed to read connection setting"); + return NULL; + } + + if (!g_variant_lookup (con_setting, NM_SETTING_CONNECTION_UUID, "&s", &uuid)) { + g_warning ("Connection hash did not contain the UUID"); + g_variant_unref (con_setting); + return NULL; + } + + if (!g_variant_lookup (con_setting, NM_SETTING_CONNECTION_ID, "&s", &id)) { + g_warning ("Connection hash did not contain the ID"); + g_variant_unref (con_setting); + return NULL; + } + items = construct_basic_items (items, uuid, id, iface, ip_iface); + g_variant_unref (con_setting); /* Device it's aren't valid if the device isn't activated */ if (iface && (dev_state == NM_DEVICE_STATE_ACTIVATED)) { diff --git a/callouts/nm-dispatcher-utils.h b/callouts/nm-dispatcher-utils.h index d64dfce190..665a0d4eaf 100644 --- a/callouts/nm-dispatcher-utils.h +++ b/callouts/nm-dispatcher-utils.h @@ -25,16 +25,16 @@ char ** nm_dispatcher_utils_construct_envp (const char *action, - GHashTable *connection_hash, - GHashTable *connection_props, - GHashTable *device_props, - GHashTable *device_ip4_props, - GHashTable *device_ip6_props, - GHashTable *device_dhcp4_props, - GHashTable *device_dhcp6_props, + GVariant *connection_dict, + GVariant *connection_props, + GVariant *device_props, + GVariant *device_ip4_props, + GVariant *device_ip6_props, + GVariant *device_dhcp4_props, + GVariant *device_dhcp6_props, const char *vpn_ip_iface, - GHashTable *vpn_ip4_props, - GHashTable *vpn_ip6_props, + GVariant *vpn_ip4_props, + GVariant *vpn_ip6_props, char **out_iface); #endif /* __NETWORKMANAGER_DISPATCHER_UTILS_H__ */ diff --git a/callouts/nm-dispatcher.c b/callouts/nm-dispatcher.c index 733af511fb..a7a83d5aa5 100644 --- a/callouts/nm-dispatcher.c +++ b/callouts/nm-dispatcher.c @@ -32,17 +32,18 @@ #include <glib.h> #include <glib-unix.h> -#include <dbus/dbus.h> -#include <dbus/dbus-glib-lowlevel.h> -#include <dbus/dbus-glib.h> #include "nm-dispatcher-api.h" #include "nm-dispatcher-utils.h" #include "nm-glib-compat.h" +#include "nmdbus-dispatcher.h" + static GMainLoop *loop = NULL; static gboolean debug = FALSE; +static gboolean persist = FALSE; +static guint quit_id; typedef struct Request Request; @@ -50,10 +51,10 @@ typedef struct { GObject parent; /* Private data */ + NMDBusDispatcher *dbus_dispatcher; + Request *current_request; GQueue *pending_requests; - guint quit_id; - gboolean persist; } Handler; typedef struct { @@ -68,28 +69,30 @@ GType handler_get_type (void); G_DEFINE_TYPE(Handler, handler, G_TYPE_OBJECT) -static void -impl_dispatch (Handler *h, - const char *action, - GHashTable *connection_hash, - GHashTable *connection_props, - GHashTable *device_props, - GHashTable *device_ip4_props, - GHashTable *device_ip6_props, - GHashTable *device_dhcp4_props, - GHashTable *device_dhcp6_props, +static gboolean +handle_action (NMDBusDispatcher *dbus_dispatcher, + GDBusMethodInvocation *context, + const char *str_action, + GVariant *connection_dict, + GVariant *connection_props, + GVariant *device_props, + GVariant *device_ip4_props, + GVariant *device_ip6_props, + GVariant *device_dhcp4_props, + GVariant *device_dhcp6_props, const char *vpn_ip_iface, - GHashTable *vpn_ip4_props, - GHashTable *vpn_ip6_props, + GVariant *vpn_ip4_props, + GVariant *vpn_ip6_props, gboolean request_debug, - DBusGMethodInvocation *context); - -#include "nm-dispatcher-glue.h" - + gpointer user_data); static void handler_init (Handler *h) { + h->pending_requests = g_queue_new (); + h->dbus_dispatcher = nmdbus_dispatcher_skeleton_new (); + g_signal_connect (h->dbus_dispatcher, "handle-action", + G_CALLBACK (handle_action), h); } static void @@ -111,7 +114,7 @@ typedef struct { struct Request { Handler *handler; - DBusGMethodInvocation *context; + GDBusMethodInvocation *context; char *action; char *iface; char **envp; @@ -152,20 +155,20 @@ quit_timeout_cb (gpointer user_data) } static void -quit_timeout_cancel (Handler *h) +quit_timeout_cancel (void) { - if (h->quit_id) { - g_source_remove (h->quit_id); - h->quit_id = 0; + if (quit_id) { + g_source_remove (quit_id); + quit_id = 0; } } static void -quit_timeout_reschedule (Handler *h) +quit_timeout_reschedule (void) { - quit_timeout_cancel (h); - if (!h->persist) - h->quit_id = g_timeout_add_seconds (10, quit_timeout_cb, NULL); + quit_timeout_cancel (); + if (!persist) + quit_id = g_timeout_add_seconds (10, quit_timeout_cb, NULL); } static void @@ -191,7 +194,7 @@ next_request (Handler *h) } h->current_request = NULL; - quit_timeout_reschedule (h); + quit_timeout_reschedule (); } static gboolean @@ -199,8 +202,8 @@ next_script (gpointer user_data) { Request *request = user_data; Handler *h = request->handler; - GPtrArray *results; - GValueArray *item; + GVariantBuilder results; + GVariant *ret; guint i; request->idx++; @@ -210,36 +213,18 @@ next_script (gpointer user_data) } /* All done */ - results = g_ptr_array_new_full (request->scripts->len, (GDestroyNotify) g_value_array_free); + g_variant_builder_init (&results, G_VARIANT_TYPE ("a(sus)")); for (i = 0; i < request->scripts->len; i++) { ScriptInfo *script = g_ptr_array_index (request->scripts, i); - GValue elt = G_VALUE_INIT; - - item = g_value_array_new (3); - - /* Script path */ - g_value_init (&elt, G_TYPE_STRING); - g_value_set_string (&elt, script->script); - g_value_array_append (item, &elt); - g_value_unset (&elt); - - /* Result */ - g_value_init (&elt, G_TYPE_UINT); - g_value_set_uint (&elt, script->result); - g_value_array_append (item, &elt); - g_value_unset (&elt); - - /* Error */ - g_value_init (&elt, G_TYPE_STRING); - g_value_set_string (&elt, script->error ? script->error : ""); - g_value_array_append (item, &elt); - g_value_unset (&elt); - g_ptr_array_add (results, item); + g_variant_builder_add (&results, "(sus)", + script->script, + script->result, + script->error ? script->error : ""); } - dbus_g_method_return (request->context, results); - g_ptr_array_unref (results); + ret = g_variant_new ("(a(sus))", &results); + g_dbus_method_invocation_return_value (request->context, ret); if (request->debug) { if (request->iface) @@ -470,22 +455,24 @@ find_scripts (const char *str_action) return sorted; } -static void -impl_dispatch (Handler *h, +static gboolean +handle_action (NMDBusDispatcher *dbus_dispatcher, + GDBusMethodInvocation *context, const char *str_action, - GHashTable *connection_hash, - GHashTable *connection_props, - GHashTable *device_props, - GHashTable *device_ip4_props, - GHashTable *device_ip6_props, - GHashTable *device_dhcp4_props, - GHashTable *device_dhcp6_props, + GVariant *connection_dict, + GVariant *connection_props, + GVariant *device_props, + GVariant *device_ip4_props, + GVariant *device_ip6_props, + GVariant *device_dhcp4_props, + GVariant *device_dhcp6_props, const char *vpn_ip_iface, - GHashTable *vpn_ip4_props, - GHashTable *vpn_ip6_props, + GVariant *vpn_ip4_props, + GVariant *vpn_ip6_props, gboolean request_debug, - DBusGMethodInvocation *context) + gpointer user_data) { + Handler *h = user_data; GSList *sorted_scripts = NULL; GSList *iter; Request *request; @@ -495,11 +482,14 @@ impl_dispatch (Handler *h, sorted_scripts = find_scripts (str_action); if (!sorted_scripts) { - dbus_g_method_return (context, g_ptr_array_new ()); - return; + GVariant *results; + + results = g_variant_new_array (G_VARIANT_TYPE ("sus"), NULL, 0); + g_dbus_method_invocation_return_value (context, g_variant_new ("(@a(sus))", results)); + return TRUE; } - quit_timeout_cancel (h); + quit_timeout_cancel (); request = g_malloc0 (sizeof (*request)); request->handler = h; @@ -508,7 +498,7 @@ impl_dispatch (Handler *h, request->action = g_strdup (str_action); request->envp = nm_dispatcher_utils_construct_envp (str_action, - connection_hash, + connection_dict, connection_props, device_props, device_ip4_props, @@ -543,76 +533,35 @@ impl_dispatch (Handler *h, g_queue_push_tail (h->pending_requests, request); else start_request (request); + + return TRUE; } +static gboolean ever_acquired_name = FALSE; + static void -destroy_cb (DBusGProxy *proxy, gpointer user_data) +on_name_acquired (GDBusConnection *connection, + const char *name, + gpointer user_data) { - g_warning ("Disconnected from the system bus, exiting."); - g_main_loop_quit (loop); + ever_acquired_name = TRUE; } -static DBusGConnection * -dbus_init (void) +static void +on_name_lost (GDBusConnection *connection, + const char *name, + gpointer user_data) { - GError *error = NULL; - DBusGConnection *bus; - DBusConnection *connection; - DBusGProxy *proxy; - int result; - - dbus_connection_set_change_sigpipe (TRUE); - - bus = dbus_g_bus_get (DBUS_BUS_SYSTEM, &error); - if (!bus) { - g_warning ("Could not get the system bus. Make sure " - "the message bus daemon is running! Message: %s", - error->message); - g_error_free (error); - return NULL; - } - - /* Clean up nicely if we get kicked off the bus */ - connection = dbus_g_connection_get_connection (bus); - dbus_connection_set_exit_on_disconnect (connection, FALSE); - - proxy = dbus_g_proxy_new_for_name (bus, - "org.freedesktop.DBus", - "/org/freedesktop/DBus", - "org.freedesktop.DBus"); - if (!proxy) { - g_warning ("Could not create the DBus proxy!"); - goto error; - } - - g_signal_connect (proxy, "destroy", G_CALLBACK (destroy_cb), NULL); - - if (!dbus_g_proxy_call (proxy, "RequestName", &error, - G_TYPE_STRING, NM_DISPATCHER_DBUS_SERVICE, - G_TYPE_UINT, DBUS_NAME_FLAG_DO_NOT_QUEUE, - G_TYPE_INVALID, - G_TYPE_UINT, &result, - G_TYPE_INVALID)) { - g_warning ("Could not acquire the " NM_DISPATCHER_DBUS_SERVICE " service.\n" - " Message: '%s'", error->message); - g_error_free (error); - goto error; - } - - if (result != DBUS_REQUEST_NAME_REPLY_PRIMARY_OWNER) { - g_warning ("Could not acquire the " NM_DISPATCHER_DBUS_SERVICE " service " - "as it is already taken. Result: %d", - result); - goto error; + if (!connection) { + g_warning ("Could not get the system bus. Make sure the message bus daemon is running!"); + exit (1); + } else if (!ever_acquired_name) { + g_warning ("Could not acquire the " NM_DISPATCHER_DBUS_SERVICE " service."); + exit (1); + } else { + g_message ("Lost the " NM_DISPATCHER_DBUS_SERVICE " name. Exiting"); + exit (0); } - - return bus; - -error: - if (proxy) - g_object_unref (proxy); - dbus_g_connection_unref (bus); - return NULL; } static void @@ -681,8 +630,7 @@ main (int argc, char **argv) { GOptionContext *opt_ctx; GError *error = NULL; - gboolean persist = FALSE; - DBusGConnection *bus; + GDBusConnection *bus; Handler *handler; GOptionEntry entries[] = { @@ -715,31 +663,41 @@ main (int argc, char **argv) loop = g_main_loop_new (NULL, FALSE); - bus = dbus_init (); - if (!bus) + bus = g_bus_get_sync (G_BUS_TYPE_SYSTEM, NULL, &error); + if (!bus) { + g_warning ("Could not get the system bus (%s). Make sure the message bus daemon is running!", + error->message); + g_error_free (error); return 1; + } handler = g_object_new (HANDLER_TYPE, NULL); - if (!handler) + g_dbus_interface_skeleton_export (G_DBUS_INTERFACE_SKELETON (handler->dbus_dispatcher), + bus, + NM_DISPATCHER_DBUS_PATH, + &error); + if (error) { + g_warning ("Could not export Dispatcher D-Bus interface: %s", error->message); + g_error_free (error); return 1; - handler->persist = persist; - handler->pending_requests = g_queue_new (); + } - dbus_g_object_type_install_info (HANDLER_TYPE, &dbus_glib_nm_dispatcher_object_info); - dbus_g_connection_register_g_object (bus, - NM_DISPATCHER_DBUS_PATH, - G_OBJECT (handler)); + g_bus_own_name_on_connection (bus, + NM_DISPATCHER_DBUS_SERVICE, + G_BUS_NAME_OWNER_FLAGS_NONE, + on_name_acquired, + on_name_lost, + NULL, NULL); + g_object_unref (bus); if (!persist) - handler->quit_id = g_timeout_add_seconds (10, quit_timeout_cb, NULL); + quit_id = g_timeout_add_seconds (10, quit_timeout_cb, NULL); g_main_loop_run (loop); g_queue_free (handler->pending_requests); g_object_unref (handler); - dbus_g_connection_unref (bus); - if (!debug) logging_shutdown (); diff --git a/callouts/nm-dispatcher.xml b/callouts/nm-dispatcher.xml index 1ae138b35b..b2c4a21aec 100644 --- a/callouts/nm-dispatcher.xml +++ b/callouts/nm-dispatcher.xml @@ -2,15 +2,13 @@ <node name="/" xmlns:tp="http://telepathy.freedesktop.org/wiki/DbusSpec#extensions-v0"> <interface name="org.freedesktop.nm_dispatcher"> + <annotation name="org.gtk.GDBus.C.Name" value="Dispatcher"/> <method name="Action"> <tp:docstring> INTERNAL; not public API. Perform an action. </tp:docstring> - <annotation name="org.freedesktop.DBus.GLib.CSymbol" value="impl_dispatch"/> - <annotation name="org.freedesktop.DBus.GLib.Async" value=""/> - <arg name="action" type="s" direction="in"> <tp:docstring> The action being performed. diff --git a/callouts/tests/test-dispatcher-envp.c b/callouts/tests/test-dispatcher-envp.c index 05c2e8ed9c..f3a80c6f76 100644 --- a/callouts/tests/test-dispatcher-envp.c +++ b/callouts/tests/test-dispatcher-envp.c @@ -28,107 +28,31 @@ #include "nm-connection.h" #include "nm-setting-connection.h" #include "nm-dispatcher-utils.h" -#include "nm-dbus-glib-types.h" #include "nm-dispatcher-api.h" #include "nm-utils.h" +#include "nm-dbus-glib-types.h" /*******************************************/ -static void -value_destroy (gpointer data) -{ - GValue *value = (GValue *) data; - - g_value_unset (value); - g_slice_free (GValue, value); -} - -static GHashTable * -value_hash_create (void) -{ - return g_hash_table_new_full (g_str_hash, g_str_equal, g_free, value_destroy); -} - -static void -value_hash_add (GHashTable *hash, - const char *key, - GValue *value) -{ - g_hash_table_insert (hash, g_strdup (key), value); -} - -static void -value_hash_add_string (GHashTable *hash, - const char *key, - const char *str) -{ - GValue *value; - - value = g_slice_new0 (GValue); - g_value_init (value, G_TYPE_STRING); - g_value_set_string (value, str); - - value_hash_add (hash, key, value); -} - -static void -value_hash_add_object_path (GHashTable *hash, - const char *key, - const char *op) -{ - GValue *value; - - value = g_slice_new0 (GValue); - g_value_init (value, DBUS_TYPE_G_OBJECT_PATH); - g_value_set_boxed (value, op); - - value_hash_add (hash, key, value); -} - -static void -value_hash_add_uint (GHashTable *hash, - const char *key, - guint32 val) +static GVariant * +connection_hash_to_dict (GHashTable *hash) { - GValue *value; + GValue val = { 0, }; + GVariant *dict; - value = g_slice_new0 (GValue); - g_value_init (value, G_TYPE_UINT); - g_value_set_uint (value, val); + g_value_init (&val, DBUS_TYPE_G_MAP_OF_MAP_OF_VARIANT); + g_value_set_boxed (&val, hash); + dict = dbus_g_value_build_g_variant (&val); + g_value_unset (&val); - value_hash_add (hash, key, value); -} - -static void -value_hash_add_strv (GHashTable *hash, - const char *key, - char **strv) -{ - GValue *value; - - value = g_slice_new0 (GValue); - g_value_init (value, G_TYPE_STRV); - g_value_take_boxed (value, strv); - value_hash_add (hash, key, value); -} - -static void -value_hash_add_uint_array (GHashTable *hash, - const char *key, - GArray *array) -{ - GValue *value; - - value = g_slice_new0 (GValue); - g_value_init (value, DBUS_TYPE_G_UINT_ARRAY); - g_value_take_boxed (value, array); - value_hash_add (hash, key, value); + g_variant_ref_sink (dict); + return dict; } static gboolean parse_main (GKeyFile *kf, - GHashTable **out_con_hash, - GHashTable **out_con_props, + GVariant **out_con_dict, + GVariant **out_con_props, char **out_expected_iface, char **out_action, char **out_vpn_ip_iface, @@ -137,6 +61,8 @@ parse_main (GKeyFile *kf, char *uuid, *id; NMConnection *connection; NMSettingConnection *s_con; + GVariantBuilder props; + GHashTable *con_hash; *out_expected_iface = g_key_file_get_string (kf, "main", "expected-iface", error); if (*out_expected_iface == NULL) @@ -167,57 +93,74 @@ parse_main (GKeyFile *kf, g_free (id); nm_connection_add_setting (connection, NM_SETTING (s_con)); - *out_con_hash = nm_connection_to_dbus (connection, NM_CONNECTION_SERIALIZE_ALL); + con_hash = nm_connection_to_dbus (connection, NM_CONNECTION_SERIALIZE_ALL); g_object_unref (connection); + *out_con_dict = connection_hash_to_dict (con_hash); + g_hash_table_unref (con_hash); - *out_con_props = value_hash_create (); - value_hash_add_object_path (*out_con_props, "connection-path", "/org/freedesktop/NetworkManager/Connections/5"); + g_variant_builder_init (&props, G_VARIANT_TYPE ("a{sv}")); + g_variant_builder_add (&props, "{sv}", + "connection-path", + g_variant_new_object_path ("/org/freedesktop/NetworkManager/Connections/5")); + *out_con_props = g_variant_builder_end (&props); return TRUE; } static gboolean -parse_device (GKeyFile *kf, GHashTable **out_device_props, GError **error) +parse_device (GKeyFile *kf, GVariant **out_device_props, GError **error) { + GVariantBuilder props; char *tmp; gint i; - *out_device_props = value_hash_create (); + g_variant_builder_init (&props, G_VARIANT_TYPE ("a{sv}")); i = g_key_file_get_integer (kf, "device", "state", error); if (i == 0) return FALSE; - value_hash_add_uint (*out_device_props, NMD_DEVICE_PROPS_STATE, (guint) i); + g_variant_builder_add (&props, "{sv}", + NMD_DEVICE_PROPS_STATE, + g_variant_new_uint32 (i)); i = g_key_file_get_integer (kf, "device", "type", error); if (i == 0) return FALSE; - value_hash_add_uint (*out_device_props, NMD_DEVICE_PROPS_TYPE, (guint) i); + g_variant_builder_add (&props, "{sv}", + NMD_DEVICE_PROPS_TYPE, + g_variant_new_uint32 (i)); tmp = g_key_file_get_string (kf, "device", "interface", error); if (tmp == NULL) return FALSE; - value_hash_add_string (*out_device_props, NMD_DEVICE_PROPS_INTERFACE, tmp); + g_variant_builder_add (&props, "{sv}", + NMD_DEVICE_PROPS_INTERFACE, + g_variant_new_string (tmp)); g_free (tmp); tmp = g_key_file_get_string (kf, "device", "ip-interface", error); if (tmp == NULL) return FALSE; - value_hash_add_string (*out_device_props, NMD_DEVICE_PROPS_IP_INTERFACE, tmp); + g_variant_builder_add (&props, "{sv}", + NMD_DEVICE_PROPS_IP_INTERFACE, + g_variant_new_string (tmp)); g_free (tmp); tmp = g_key_file_get_string (kf, "device", "path", error); if (tmp == NULL) return FALSE; - value_hash_add_object_path (*out_device_props, NMD_DEVICE_PROPS_PATH, tmp); + g_variant_builder_add (&props, "{sv}", + NMD_DEVICE_PROPS_PATH, + g_variant_new_object_path (tmp)); g_free (tmp); + *out_device_props = g_variant_builder_end (&props); return TRUE; } static gboolean add_uint_array (GKeyFile *kf, - GHashTable *props, + GVariantBuilder *props, const char *section, const char *key, GError **error) @@ -244,21 +187,25 @@ add_uint_array (GKeyFile *kf, g_array_append_val (items, addr); } } - value_hash_add_uint_array (props, key, items); + g_variant_builder_add (props, "{sv}", key, + g_variant_new_fixed_array (G_VARIANT_TYPE_UINT32, + items->data, items->len, + sizeof (guint32))); + g_array_unref (items); } g_strfreev (split); return TRUE; } static gboolean -parse_ip4 (GKeyFile *kf, GHashTable **out_props, const char *section, GError **error) +parse_ip4 (GKeyFile *kf, GVariant **out_props, const char *section, GError **error) { + GVariantBuilder props; char *tmp; char **split, **iter; - GSList *list; - GValue *val; + GPtrArray *addresses, *routes; - *out_props = value_hash_create (); + g_variant_builder_init (&props, G_VARIANT_TYPE ("a{sv}")); /* search domains */ /* Use char** for domains. (DBUS_TYPE_G_ARRAY_OF_STRING of NMIP4Config @@ -273,14 +220,15 @@ parse_ip4 (GKeyFile *kf, GHashTable **out_props, const char *section, GError **e if (g_strv_length (split) > 0) { for (iter = split; iter && *iter; iter++) g_strstrip (*iter); - value_hash_add_strv (*out_props, "domains", split); + g_variant_builder_add (&props, "{sv}", "domains", g_variant_new_strv ((gpointer) split, -1)); + g_strfreev (split); } /* nameservers */ - if (!add_uint_array (kf, *out_props, "ip4", "nameservers", error)) + if (!add_uint_array (kf, &props, "ip4", "nameservers", error)) return FALSE; /* wins-servers */ - if (!add_uint_array (kf, *out_props, "ip4", "wins-servers", error)) + if (!add_uint_array (kf, &props, "ip4", "wins-servers", error)) return FALSE; /* Addresses */ @@ -291,7 +239,7 @@ parse_ip4 (GKeyFile *kf, GHashTable **out_props, const char *section, GError **e g_free (tmp); if (g_strv_length (split) > 0) { - list = NULL; + addresses = g_ptr_array_new_with_free_func ((GDestroyNotify) nm_ip4_address_unref); for (iter = split; iter && *iter; iter++) { NMIP4Address *addr; guint32 a; @@ -317,13 +265,12 @@ parse_ip4 (GKeyFile *kf, GHashTable **out_props, const char *section, GError **e g_assert_cmpint (inet_pton (AF_INET, p, &a), ==, 1); nm_ip4_address_set_gateway (addr, a); - list = g_slist_append (list, addr); + g_ptr_array_add (addresses, addr); } - val = g_slice_new0 (GValue); - g_value_init (val, DBUS_TYPE_G_ARRAY_OF_ARRAY_OF_UINT); - nm_utils_ip4_addresses_to_gvalue (list, val); - value_hash_add (*out_props, "addresses", val); + g_variant_builder_add (&props, "{sv}", "addresses", + nm_utils_ip4_addresses_to_variant (addresses)); + g_ptr_array_unref (addresses); } g_strfreev (split); @@ -335,7 +282,7 @@ parse_ip4 (GKeyFile *kf, GHashTable **out_props, const char *section, GError **e g_free (tmp); if (g_strv_length (split) > 0) { - list = NULL; + routes = g_ptr_array_new_with_free_func ((GDestroyNotify) nm_ip4_route_unref); for (iter = split; iter && *iter; iter++) { NMIP4Route *route; guint32 a; @@ -366,56 +313,58 @@ parse_ip4 (GKeyFile *kf, GHashTable **out_props, const char *section, GError **e p++; nm_ip4_route_set_metric (route, (guint) atoi (p)); - list = g_slist_append (list, route); + g_ptr_array_add (routes, route); } - val = g_slice_new0 (GValue); - g_value_init (val, DBUS_TYPE_G_ARRAY_OF_ARRAY_OF_UINT); - nm_utils_ip4_routes_to_gvalue (list, val); - value_hash_add (*out_props, "routes", val); + g_variant_builder_add (&props, "{sv}", "routes", + nm_utils_ip4_routes_to_variant (routes)); + g_ptr_array_unref (routes); } g_strfreev (split); } + *out_props = g_variant_builder_end (&props); return TRUE; } static gboolean parse_dhcp (GKeyFile *kf, const char *group_name, - GHashTable **out_props, + GVariant **out_props, GError **error) { char **keys, **iter, *val; + GVariantBuilder props; keys = g_key_file_get_keys (kf, group_name, NULL, error); if (!keys) return FALSE; - *out_props = value_hash_create (); + g_variant_builder_init (&props, G_VARIANT_TYPE ("a{sv}")); for (iter = keys; iter && *iter; iter++) { val = g_key_file_get_string (kf, group_name, *iter, error); if (!val) return FALSE; - value_hash_add_string (*out_props, *iter, val); + g_variant_builder_add (&props, "{sv}", *iter, g_variant_new_string (val)); g_free (val); } + *out_props = g_variant_builder_end (&props); return TRUE; } static gboolean get_dispatcher_file (const char *file, - GHashTable **out_con_hash, - GHashTable **out_con_props, - GHashTable **out_device_props, - GHashTable **out_device_ip4_props, - GHashTable **out_device_ip6_props, - GHashTable **out_device_dhcp4_props, - GHashTable **out_device_dhcp6_props, + GVariant **out_con_dict, + GVariant **out_con_props, + GVariant **out_device_props, + GVariant **out_device_ip4_props, + GVariant **out_device_ip6_props, + GVariant **out_device_dhcp4_props, + GVariant **out_device_dhcp6_props, char **out_vpn_ip_iface, - GHashTable **out_vpn_ip4_props, - GHashTable **out_vpn_ip6_props, + GVariant **out_vpn_ip4_props, + GVariant **out_vpn_ip6_props, char **out_expected_iface, char **out_action, GHashTable **out_env, @@ -430,7 +379,7 @@ get_dispatcher_file (const char *file, return FALSE; if (!parse_main (kf, - out_con_hash, + out_con_dict, out_con_props, out_expected_iface, out_action, @@ -482,16 +431,16 @@ out: static void test_generic (const char *path, const char *file, const char *override_vpn_ip_iface) { - GHashTable *con_hash = NULL; - GHashTable *con_props = NULL; - GHashTable *device_props = NULL; - GHashTable *device_ip4_props = NULL; - GHashTable *device_ip6_props = NULL; - GHashTable *device_dhcp4_props = NULL; - GHashTable *device_dhcp6_props = NULL; + GVariant *con_dict = NULL; + GVariant *con_props = NULL; + GVariant *device_props = NULL; + GVariant *device_ip4_props = NULL; + GVariant *device_ip6_props = NULL; + GVariant *device_dhcp4_props = NULL; + GVariant *device_dhcp6_props = NULL; char *vpn_ip_iface = NULL; - GHashTable *vpn_ip4_props = NULL; - GHashTable *vpn_ip6_props = NULL; + GVariant *vpn_ip4_props = NULL; + GVariant *vpn_ip6_props = NULL; char *expected_iface = NULL; char *action = NULL; char *out_iface = NULL; @@ -504,7 +453,7 @@ test_generic (const char *path, const char *file, const char *override_vpn_ip_if /* Read in the test file */ p = g_strdup_printf ("%s/%s", path, file); success = get_dispatcher_file (p, - &con_hash, + &con_dict, &con_props, &device_props, &device_ip4_props, @@ -524,7 +473,7 @@ test_generic (const char *path, const char *file, const char *override_vpn_ip_if /* Get the environment from the dispatcher code */ denv = nm_dispatcher_utils_construct_envp (action, - con_hash, + con_dict, con_props, device_props, device_ip4_props, @@ -581,21 +530,21 @@ test_generic (const char *path, const char *file, const char *override_vpn_ip_if g_free (vpn_ip_iface); g_free (expected_iface); g_free (action); - g_hash_table_destroy (con_hash); - g_hash_table_destroy (con_props); - g_hash_table_destroy (device_props); + g_variant_unref (con_dict); + g_variant_unref (con_props); + g_variant_unref (device_props); if (device_ip4_props) - g_hash_table_destroy (device_ip4_props); + g_variant_unref (device_ip4_props); if (device_ip6_props) - g_hash_table_destroy (device_ip6_props); + g_variant_unref (device_ip6_props); if (device_dhcp4_props) - g_hash_table_destroy (device_dhcp4_props); + g_variant_unref (device_dhcp4_props); if (device_dhcp6_props) - g_hash_table_destroy (device_dhcp6_props); + g_variant_unref (device_dhcp6_props); if (vpn_ip4_props) - g_hash_table_destroy (vpn_ip4_props); + g_variant_unref (vpn_ip4_props); if (vpn_ip6_props) - g_hash_table_destroy (vpn_ip6_props); + g_variant_unref (vpn_ip6_props); g_hash_table_destroy (expected_env); } |