diff options
author | Dan Winship <danw@gnome.org> | 2014-09-16 16:38:04 -0400 |
---|---|---|
committer | Dan Winship <danw@gnome.org> | 2014-11-07 07:49:40 -0500 |
commit | 39709fdc2ecaf42e431410f9ad425a9fb5c57812 (patch) | |
tree | c4e971a276cb5f15f9583d762dca80fcc7f82ae4 /libnm-core | |
parent | 21c8a6b20effbe1e689505a0cbb23594be06068c (diff) | |
download | NetworkManager-39709fdc2ecaf42e431410f9ad425a9fb5c57812.tar.gz |
libnm-core: add NMIPAddress/NMIPRoute attributes, use for labels
Add key-value attributes to NMIPAddress and NMIPRoute, and use them to
store IPv4 address labels. Demote NMSettingIP4Config:address-labels to
a D-Bus-only property, and arrange for :addresses setter to read the
labels out of that property when creating the addresses.
Diffstat (limited to 'libnm-core')
-rw-r--r-- | libnm-core/nm-core-internal.h | 6 | ||||
-rw-r--r-- | libnm-core/nm-setting-ip-config.c | 186 | ||||
-rw-r--r-- | libnm-core/nm-setting-ip-config.h | 15 | ||||
-rw-r--r-- | libnm-core/nm-setting-ip4-config.c | 177 | ||||
-rw-r--r-- | libnm-core/tests/test-general.c | 137 |
5 files changed, 352 insertions, 169 deletions
diff --git a/libnm-core/nm-core-internal.h b/libnm-core/nm-core-internal.h index ff44eb043f..407d189e3c 100644 --- a/libnm-core/nm-core-internal.h +++ b/libnm-core/nm-core-internal.h @@ -74,12 +74,6 @@ g_clear_object (&c); \ } -const char *_nm_setting_ip4_config_get_address_label (NMSettingIP4Config *setting, - guint32 i); -gboolean _nm_setting_ip4_config_add_address_with_label (NMSettingIP4Config *setting, - NMIPAddress *address, - const char *label); - /* NM_SETTING_COMPARE_FLAG_INFERRABLE: check whether a device-generated * connection can be replaced by a already-defined connection. This flag only * takes into account properties marked with the %NM_SETTING_PARAM_INFERRABLE diff --git a/libnm-core/nm-setting-ip-config.c b/libnm-core/nm-setting-ip-config.c index 12080bd05f..42857dca00 100644 --- a/libnm-core/nm-setting-ip-config.c +++ b/libnm-core/nm-setting-ip-config.c @@ -89,6 +89,8 @@ struct NMIPAddress { char *address, *gateway; int prefix, family; + + GHashTable *attributes; }; /** @@ -202,6 +204,8 @@ nm_ip_address_unref (NMIPAddress *address) if (address->refcount == 0) { g_free (address->address); g_free (address->gateway); + if (address->attributes) + g_hash_table_unref (address->attributes); g_slice_free (NMIPAddress, address); } } @@ -211,7 +215,8 @@ nm_ip_address_unref (NMIPAddress *address) * @address: the #NMIPAddress * @other: the #NMIPAddress to compare @address to. * - * Determines if two #NMIPAddress objects contain the same values. + * Determines if two #NMIPAddress objects contain the same address, prefix, and + * gateway (attributes are not compared). * * Returns: %TRUE if the objects contain the same values, %FALSE if they do not. **/ @@ -251,6 +256,16 @@ nm_ip_address_dup (NMIPAddress *address) copy = nm_ip_address_new (address->family, address->address, address->prefix, address->gateway, NULL); + if (address->attributes) { + GHashTableIter iter; + const char *key; + GVariant *value; + + g_hash_table_iter_init (&iter, address->attributes); + while (g_hash_table_iter_next (&iter, (gpointer *) &key, (gpointer *) &value)) + nm_ip_address_set_attribute (copy, key, value); + } + return copy; } @@ -427,6 +442,82 @@ nm_ip_address_set_gateway (NMIPAddress *address, address->gateway = canonicalize_ip (address->family, gateway, TRUE); } +/** + * nm_ip_address_get_attribute_names: + * @address: the #NMIPAddress + * + * Gets an array of attribute names defined on @address. + * + * Returns: (transfer full): a %NULL-terminated array of attribute names, + **/ +char ** +nm_ip_address_get_attribute_names (NMIPAddress *address) +{ + GHashTableIter iter; + const char *key; + GPtrArray *names; + + g_return_val_if_fail (address != NULL, NULL); + + names = g_ptr_array_new (); + + if (address->attributes) { + g_hash_table_iter_init (&iter, address->attributes); + while (g_hash_table_iter_next (&iter, (gpointer *) &key, NULL)) + g_ptr_array_add (names, g_strdup (key)); + } + g_ptr_array_add (names, NULL); + + return (char **) g_ptr_array_free (names, FALSE); +} + +/** + * nm_ip_address_get_attribute: + * @address: the #NMIPAddress + * @name: the name of an address attribute + * + * Gets the value of the attribute with name @name on @address + * + * Returns: (transfer none): the value of the attribute with name @name on + * @address, or %NULL if @address has no such attribute. + **/ +GVariant * +nm_ip_address_get_attribute (NMIPAddress *address, const char *name) +{ + g_return_val_if_fail (address != NULL, NULL); + g_return_val_if_fail (name != NULL && *name != '\0', NULL); + + if (address->attributes) + return g_hash_table_lookup (address->attributes, name); + else + return NULL; +} + +/** + * nm_ip_address_set_attribute: + * @address: the #NMIPAddress + * @name: the name of an address attribute + * @value: (transfer none) (allow-none): the value + * + * Sets or clears the named attribute on @address to the given value. + **/ +void +nm_ip_address_set_attribute (NMIPAddress *address, const char *name, GVariant *value) +{ + g_return_if_fail (address != NULL); + g_return_if_fail (name != NULL && *name != '\0'); + + if (!address->attributes) { + address->attributes = g_hash_table_new_full (g_str_hash, g_str_equal, + g_free, (GDestroyNotify) g_variant_unref); + } + + if (value) + g_hash_table_insert (address->attributes, g_strdup (name), g_variant_ref_sink (value)); + else + g_hash_table_remove (address->attributes, name); +} + G_DEFINE_BOXED_TYPE (NMIPRoute, nm_ip_route, nm_ip_route_dup, nm_ip_route_unref) @@ -438,6 +529,8 @@ struct NMIPRoute { guint prefix; char *next_hop; guint32 metric; + + GHashTable *attributes; }; /** @@ -559,6 +652,8 @@ nm_ip_route_unref (NMIPRoute *route) if (route->refcount == 0) { g_free (route->dest); g_free (route->next_hop); + if (route->attributes) + g_hash_table_unref (route->attributes); g_slice_free (NMIPRoute, route); } } @@ -568,7 +663,8 @@ nm_ip_route_unref (NMIPRoute *route) * @route: the #NMIPRoute * @other: the #NMIPRoute to compare @route to. * - * Determines if two #NMIPRoute objects contain the same values. + * Determines if two #NMIPRoute objects contain the same destination, prefix, + * next hop, and metric. (Attributes are not compared.) * * Returns: %TRUE if the objects contain the same values, %FALSE if they do not. **/ @@ -609,6 +705,16 @@ nm_ip_route_dup (NMIPRoute *route) route->dest, route->prefix, route->next_hop, route->metric, NULL); + if (route->attributes) { + GHashTableIter iter; + const char *key; + GVariant *value; + + g_hash_table_iter_init (&iter, route->attributes); + while (g_hash_table_iter_next (&iter, (gpointer *) &key, (gpointer *) &value)) + nm_ip_route_set_attribute (copy, key, value); + } + return copy; } @@ -872,3 +978,79 @@ nm_ip_route_set_metric (NMIPRoute *route, route->metric = metric; } + +/** + * nm_ip_route_get_attribute_names: + * @route: the #NMIPRoute + * + * Gets an array of attribute names defined on @route. + * + * Returns: (transfer full): a %NULL-terminated array of attribute names + **/ +char ** +nm_ip_route_get_attribute_names (NMIPRoute *route) +{ + GHashTableIter iter; + const char *key; + GPtrArray *names; + + g_return_val_if_fail (route != NULL, NULL); + + names = g_ptr_array_new (); + + if (route->attributes) { + g_hash_table_iter_init (&iter, route->attributes); + while (g_hash_table_iter_next (&iter, (gpointer *) &key, NULL)) + g_ptr_array_add (names, g_strdup (key)); + } + g_ptr_array_add (names, NULL); + + return (char **) g_ptr_array_free (names, FALSE); +} + +/** + * nm_ip_route_get_attribute: + * @route: the #NMIPRoute + * @name: the name of an route attribute + * + * Gets the value of the attribute with name @name on @route + * + * Returns: (transfer none): the value of the attribute with name @name on + * @route, or %NULL if @route has no such attribute. + **/ +GVariant * +nm_ip_route_get_attribute (NMIPRoute *route, const char *name) +{ + g_return_val_if_fail (route != NULL, NULL); + g_return_val_if_fail (name != NULL && *name != '\0', NULL); + + if (route->attributes) + return g_hash_table_lookup (route->attributes, name); + else + return NULL; +} + +/** + * nm_ip_route_set_attribute: + * @route: the #NMIPRoute + * @name: the name of a route attribute + * @value: (transfer none) (allow-none): the value + * + * Sets the named attribute on @route to the given value. + **/ +void +nm_ip_route_set_attribute (NMIPRoute *route, const char *name, GVariant *value) +{ + g_return_if_fail (route != NULL); + g_return_if_fail (name != NULL && *name != '\0'); + + if (!route->attributes) { + route->attributes = g_hash_table_new_full (g_str_hash, g_str_equal, + g_free, (GDestroyNotify) g_variant_unref); + } + + if (value) + g_hash_table_insert (route->attributes, g_strdup (name), g_variant_ref_sink (value)); + else + g_hash_table_remove (route->attributes, name); +} diff --git a/libnm-core/nm-setting-ip-config.h b/libnm-core/nm-setting-ip-config.h index d282935083..24c1cbda42 100644 --- a/libnm-core/nm-setting-ip-config.h +++ b/libnm-core/nm-setting-ip-config.h @@ -67,6 +67,14 @@ const char *nm_ip_address_get_gateway (NMIPAddress *address); void nm_ip_address_set_gateway (NMIPAddress *address, const char *gateway); +char **nm_ip_address_get_attribute_names (NMIPAddress *address); +GVariant *nm_ip_address_get_attribute (NMIPAddress *address, + const char *name); +void nm_ip_address_set_attribute (NMIPAddress *address, + const char *name, + GVariant *value); + + typedef struct NMIPRoute NMIPRoute; GType nm_ip_route_get_type (void); @@ -112,6 +120,13 @@ guint32 nm_ip_route_get_metric (NMIPRoute *route); void nm_ip_route_set_metric (NMIPRoute *route, guint32 metric); +char **nm_ip_route_get_attribute_names (NMIPRoute *route); +GVariant *nm_ip_route_get_attribute (NMIPRoute *route, + const char *name); +void nm_ip_route_set_attribute (NMIPRoute *route, + const char *name, + GVariant *value); + G_END_DECLS #endif /* NM_SETTING_IP_CONFIG_H */ diff --git a/libnm-core/nm-setting-ip4-config.c b/libnm-core/nm-setting-ip4-config.c index 2cc00093f9..e15dae0491 100644 --- a/libnm-core/nm-setting-ip4-config.c +++ b/libnm-core/nm-setting-ip4-config.c @@ -50,7 +50,6 @@ typedef struct { GSList *dns; /* list of IP address strings */ GSList *dns_search; /* list of strings */ GSList *addresses; /* array of NMIPAddress */ - GSList *address_labels; /* list of strings */ GSList *routes; /* array of NMIPRoute */ gboolean ignore_auto_routes; gboolean ignore_auto_dns; @@ -67,7 +66,6 @@ enum { PROP_DNS, PROP_DNS_SEARCH, PROP_ADDRESSES, - PROP_ADDRESS_LABELS, PROP_ROUTES, PROP_IGNORE_AUTO_ROUTES, PROP_IGNORE_AUTO_DNS, @@ -434,19 +432,6 @@ nm_setting_ip4_config_get_address (NMSettingIP4Config *setting, guint32 i) return (NMIPAddress *) g_slist_nth_data (priv->addresses, i); } -const char * -_nm_setting_ip4_config_get_address_label (NMSettingIP4Config *setting, guint32 i) -{ - NMSettingIP4ConfigPrivate *priv; - - g_return_val_if_fail (NM_IS_SETTING_IP4_CONFIG (setting), NULL); - - priv = NM_SETTING_IP4_CONFIG_GET_PRIVATE (setting); - g_return_val_if_fail (i < g_slist_length (priv->address_labels), NULL); - - return (const char *) g_slist_nth_data (priv->address_labels, i); -} - /** * nm_setting_ip4_config_add_address: * @setting: the #NMSettingIP4Config @@ -462,21 +447,12 @@ gboolean nm_setting_ip4_config_add_address (NMSettingIP4Config *setting, NMIPAddress *address) { - return _nm_setting_ip4_config_add_address_with_label (setting, address, ""); -} - -gboolean -_nm_setting_ip4_config_add_address_with_label (NMSettingIP4Config *setting, - NMIPAddress *address, - const char *label) -{ NMSettingIP4ConfigPrivate *priv; NMIPAddress *copy; GSList *iter; g_return_val_if_fail (NM_IS_SETTING_IP4_CONFIG (setting), FALSE); g_return_val_if_fail (address != NULL, FALSE); - g_return_val_if_fail (label != NULL, FALSE); priv = NM_SETTING_IP4_CONFIG_GET_PRIVATE (setting); for (iter = priv->addresses; iter; iter = g_slist_next (iter)) { @@ -486,7 +462,6 @@ _nm_setting_ip4_config_add_address_with_label (NMSettingIP4Config *setting, copy = nm_ip_address_dup (address); priv->addresses = g_slist_append (priv->addresses, copy); - priv->address_labels = g_slist_append (priv->address_labels, g_strdup (label)); g_object_notify (G_OBJECT (setting), NM_SETTING_IP4_CONFIG_ADDRESSES); return TRUE; @@ -503,19 +478,16 @@ void nm_setting_ip4_config_remove_address (NMSettingIP4Config *setting, guint32 i) { NMSettingIP4ConfigPrivate *priv; - GSList *addr, *label; + GSList *addr; g_return_if_fail (NM_IS_SETTING_IP4_CONFIG (setting)); priv = NM_SETTING_IP4_CONFIG_GET_PRIVATE (setting); addr = g_slist_nth (priv->addresses, i); - label = g_slist_nth (priv->address_labels, i); - g_return_if_fail (addr != NULL && label != NULL); + g_return_if_fail (addr != NULL); nm_ip_address_unref ((NMIPAddress *) addr->data); priv->addresses = g_slist_delete_link (priv->addresses, addr); - g_free (label->data); - priv->address_labels = g_slist_delete_link (priv->address_labels, label); g_object_notify (G_OBJECT (setting), NM_SETTING_IP4_CONFIG_ADDRESSES); } @@ -566,8 +538,6 @@ nm_setting_ip4_config_clear_addresses (NMSettingIP4Config *setting) g_slist_free_full (priv->addresses, (GDestroyNotify) nm_ip_address_unref); priv->addresses = NULL; - g_slist_free_full (priv->address_labels, g_free); - priv->address_labels = NULL; g_object_notify (G_OBJECT (setting), NM_SETTING_IP4_CONFIG_ADDRESSES); } @@ -843,9 +813,6 @@ verify_label (const char *label) const char *p; char *iface; - if (!*label) - return TRUE; - p = strchr (label, ':'); if (!p) return FALSE; @@ -955,31 +922,33 @@ verify (NMSetting *setting, NMConnection *connection, GError **error) } /* Validate address labels */ - for (iter = priv->address_labels, i = 0; iter; iter = g_slist_next (iter), i++) { - const char *label = (const char *) iter->data; - - if (!verify_label (label)) { + for (iter = priv->addresses, i = 0; iter; iter = g_slist_next (iter), i++) { + NMIPAddress *addr = (NMIPAddress *) iter->data; + GVariant *label; + + label = nm_ip_address_get_attribute (addr, "label"); + if (!label) + continue; + if (!g_variant_is_of_type (label, G_VARIANT_TYPE_STRING)) { + g_set_error (error, + NM_CONNECTION_ERROR, + NM_CONNECTION_ERROR_INVALID_PROPERTY, + _("%d. IPv4 address has 'label' property with invalid type"), + i+1); + g_prefix_error (error, "%s.%s: ", NM_SETTING_IP4_CONFIG_SETTING_NAME, NM_SETTING_IP4_CONFIG_ADDRESSES); + return FALSE; + } + if (!verify_label (g_variant_get_string (label, NULL))) { g_set_error (error, NM_CONNECTION_ERROR, NM_CONNECTION_ERROR_INVALID_PROPERTY, _("%d. IPv4 address has invalid label '%s'"), - i+1, label); - g_prefix_error (error, "%s.%s: ", NM_SETTING_IP4_CONFIG_SETTING_NAME, "address-labels"); + i+1, g_variant_get_string (label, NULL)); + g_prefix_error (error, "%s.%s: ", NM_SETTING_IP4_CONFIG_SETTING_NAME, NM_SETTING_IP4_CONFIG_ADDRESSES); return FALSE; } } - if (g_slist_length (priv->addresses) != g_slist_length (priv->address_labels)) { - g_set_error (error, - NM_CONNECTION_ERROR, - NM_CONNECTION_ERROR_INVALID_PROPERTY, - _("IPv4 address / label count mismatch (%d vs %d)"), - g_slist_length (priv->addresses), - g_slist_length (priv->address_labels)); - g_prefix_error (error, "%s.%s: ", NM_SETTING_IP4_CONFIG_SETTING_NAME, "address-labels"); - return FALSE; - } - /* Validate DNS */ for (iter = priv->dns, i = 0; iter; iter = g_slist_next (iter), i++) { const char *dns = (const char *) iter->data; @@ -1018,7 +987,6 @@ finalize (GObject *object) g_slist_free_full (priv->dns, g_free); g_slist_free_full (priv->dns_search, g_free); g_slist_free_full (priv->addresses, (GDestroyNotify) nm_ip_address_unref); - g_slist_free_full (priv->address_labels, g_free); g_slist_free_full (priv->routes, (GDestroyNotify) nm_ip_route_unref); G_OBJECT_CLASS (nm_setting_ip4_config_parent_class)->finalize (object); @@ -1038,16 +1006,67 @@ ip4_dns_from_dbus (GVariant *dbus_value, } static GVariant * -ip4_addresses_to_dbus (const GValue *prop_value) +ip4_addresses_get (NMSetting *setting, + const char *property) { - return nm_utils_ip4_addresses_to_variant (g_value_get_boxed (prop_value)); + GPtrArray *addrs; + GVariant *ret; + + g_object_get (setting, property, &addrs, NULL); + ret = nm_utils_ip4_addresses_to_variant (addrs); + g_ptr_array_unref (addrs); + + return ret; } static void -ip4_addresses_from_dbus (GVariant *dbus_value, - GValue *prop_value) +ip4_addresses_set (NMSetting *setting, + GVariant *connection_dict, + const char *property, + GVariant *value) { - g_value_take_boxed (prop_value, nm_utils_ip4_addresses_from_variant (dbus_value)); + GPtrArray *addrs; + GVariant *s_ip4; + char **labels; + int i; + + addrs = nm_utils_ip4_addresses_from_variant (value); + + s_ip4 = g_variant_lookup_value (connection_dict, NM_SETTING_IP4_CONFIG_SETTING_NAME, NM_VARIANT_TYPE_SETTING); + if (g_variant_lookup (s_ip4, "address-labels", "^as", &labels)) { + for (i = 0; i < addrs->len && labels[i]; i++) + if (*labels[i]) + nm_ip_address_set_attribute (addrs->pdata[i], "label", g_variant_new_string (labels[i])); + g_strfreev (labels); + } + g_variant_unref (s_ip4); + + g_object_set (setting, property, addrs, NULL); + g_ptr_array_unref (addrs); +} + +static GVariant * +ip4_address_labels_get (NMSetting *setting, + NMConnection *connection, + const char *property) +{ + NMSettingIP4ConfigPrivate *priv = NM_SETTING_IP4_CONFIG_GET_PRIVATE (setting); + GPtrArray *labels; + GSList *iter; + GVariant *ret; + + labels = g_ptr_array_new (); + for (iter = priv->addresses; iter; iter = iter->next) { + NMIPAddress *addr = iter->data; + GVariant *label = nm_ip_address_get_attribute (addr, "label"); + + g_ptr_array_add (labels, (char *) (label ? g_variant_get_string (label, NULL) : "")); + } + + ret = g_variant_new_strv ((const char * const *) labels->pdata, labels->len); + g_ptr_array_unref (labels); + + return ret; } static GVariant * @@ -1069,7 +1088,6 @@ set_property (GObject *object, guint prop_id, { NMSettingIP4Config *setting = NM_SETTING_IP4_CONFIG (object); NMSettingIP4ConfigPrivate *priv = NM_SETTING_IP4_CONFIG_GET_PRIVATE (setting); - GSList *iter; switch (prop_id) { case PROP_METHOD: @@ -1089,16 +1107,6 @@ set_property (GObject *object, guint prop_id, priv->addresses = _nm_utils_copy_array_to_slist (g_value_get_boxed (value), (NMUtilsCopyFunc) nm_ip_address_dup); - if (g_slist_length (priv->addresses) != g_slist_length (priv->address_labels)) { - g_slist_free_full (priv->address_labels, g_free); - priv->address_labels = NULL; - for (iter = priv->addresses; iter; iter = iter->next) - priv->address_labels = g_slist_prepend (priv->address_labels, g_strdup ("")); - } - break; - case PROP_ADDRESS_LABELS: - g_slist_free_full (priv->address_labels, g_free); - priv->address_labels = _nm_utils_strv_to_slist (g_value_get_boxed (value)); break; case PROP_ROUTES: g_slist_free_full (priv->routes, (GDestroyNotify) nm_ip_route_unref); @@ -1154,9 +1162,6 @@ get_property (GObject *object, guint prop_id, case PROP_ADDRESSES: g_value_take_boxed (value, _nm_utils_copy_slist_to_array (priv->addresses, (NMUtilsCopyFunc) nm_ip_address_dup, (GDestroyNotify) nm_ip_address_unref)); break; - case PROP_ADDRESS_LABELS: - g_value_take_boxed (value, _nm_utils_slist_to_strv (priv->address_labels)); - break; case PROP_ROUTES: g_value_take_boxed (value, _nm_utils_copy_slist_to_array (priv->routes, (NMUtilsCopyFunc) nm_ip_route_dup, (GDestroyNotify) nm_ip_route_unref)); break; @@ -1281,23 +1286,17 @@ nm_setting_ip4_config_class_init (NMSettingIP4ConfigClass *setting_class) G_PARAM_READWRITE | NM_SETTING_PARAM_INFERRABLE | G_PARAM_STATIC_STRINGS)); - _nm_setting_class_transform_property (parent_class, NM_SETTING_IP4_CONFIG_ADDRESSES, - G_VARIANT_TYPE ("aau"), - ip4_addresses_to_dbus, - ip4_addresses_from_dbus); - - /** - * NMSettingIP4Config:address-labels: - * - * Internal use only. - **/ - g_object_class_install_property - (object_class, PROP_ADDRESS_LABELS, - g_param_spec_boxed ("address-labels", "", "", - G_TYPE_STRV, - G_PARAM_READWRITE | - NM_SETTING_PARAM_INFERRABLE | - G_PARAM_STATIC_STRINGS)); + _nm_setting_class_override_property (parent_class, NM_SETTING_IP4_CONFIG_ADDRESSES, + G_VARIANT_TYPE ("aau"), + ip4_addresses_get, + ip4_addresses_set, + NULL); + + _nm_setting_class_add_dbus_only_property (parent_class, + "address-labels", + G_VARIANT_TYPE_STRING_ARRAY, + ip4_address_labels_get, + NULL); /** * NMSettingIP4Config:routes: diff --git a/libnm-core/tests/test-general.c b/libnm-core/tests/test-general.c index 41189481f2..b103ce8922 100644 --- a/libnm-core/tests/test-general.c +++ b/libnm-core/tests/test-general.c @@ -325,9 +325,11 @@ test_setting_ip4_config_labels (void) { NMSettingIP4Config *s_ip4; NMIPAddress *addr; - const char *label; + GVariant *label; GPtrArray *addrs; char **labels; + NMConnection *conn; + GVariant *dict, *setting_dict, *value; GError *error = NULL; s_ip4 = (NMSettingIP4Config *) nm_setting_ip4_config_new (); @@ -344,32 +346,38 @@ test_setting_ip4_config_labels (void) nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); g_assert_no_error (error); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 0); - g_assert_cmpstr (label, ==, ""); + addr = nm_setting_ip4_config_get_address (s_ip4, 0); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label == NULL); /* addr 2 */ addr = nm_ip_address_new (AF_INET, "2.2.2.2", 24, NULL, &error); g_assert_no_error (error); + nm_ip_address_set_attribute (addr, "label", g_variant_new_string ("eth0:1")); - _nm_setting_ip4_config_add_address_with_label (s_ip4, addr, "eth0:1"); + nm_setting_ip4_config_add_address (s_ip4, addr); nm_ip_address_unref (addr); nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); g_assert_no_error (error); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 1); - g_assert_cmpstr (label, ==, "eth0:1"); + addr = nm_setting_ip4_config_get_address (s_ip4, 1); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label != NULL); + g_assert_cmpstr (g_variant_get_string (label, NULL), ==, "eth0:1"); /* addr 3 */ addr = nm_ip_address_new (AF_INET, "3.3.3.3", 24, NULL, &error); g_assert_no_error (error); + nm_ip_address_set_attribute (addr, "label", NULL); - _nm_setting_ip4_config_add_address_with_label (s_ip4, addr, ""); + nm_setting_ip4_config_add_address (s_ip4, addr); nm_ip_address_unref (addr); nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); g_assert_no_error (error); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 2); - g_assert_cmpstr (label, ==, ""); + addr = nm_setting_ip4_config_get_address (s_ip4, 2); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label == NULL); /* Remove addr 1 and re-verify remaining addresses */ nm_setting_ip4_config_remove_address (s_ip4, 0); @@ -378,95 +386,81 @@ test_setting_ip4_config_labels (void) addr = nm_setting_ip4_config_get_address (s_ip4, 0); g_assert_cmpstr (nm_ip_address_get_address (addr), ==, "2.2.2.2"); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 0); - g_assert_cmpstr (label, ==, "eth0:1"); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label != NULL); + g_assert_cmpstr (g_variant_get_string (label, NULL), ==, "eth0:1"); addr = nm_setting_ip4_config_get_address (s_ip4, 1); g_assert_cmpstr (nm_ip_address_get_address (addr), ==, "3.3.3.3"); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 1); - g_assert_cmpstr (label, ==, ""); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label == NULL); + /* The labels should appear in the D-Bus serialization */ + conn = nmtst_create_minimal_connection ("label test", NULL, NM_SETTING_WIRED_SETTING_NAME, NULL); + nm_connection_add_setting (conn, NM_SETTING (s_ip4)); + dict = nm_connection_to_dbus (conn, NM_CONNECTION_SERIALIZE_ALL); + g_object_unref (conn); - /* Test explicit property assignment */ - g_object_get (G_OBJECT (s_ip4), - NM_SETTING_IP4_CONFIG_ADDRESSES, &addrs, - "address-labels", &labels, - NULL); + setting_dict = g_variant_lookup_value (dict, NM_SETTING_IP4_CONFIG_SETTING_NAME, NM_VARIANT_TYPE_SETTING); + g_assert (setting_dict != NULL); + value = g_variant_lookup_value (setting_dict, "address-labels", G_VARIANT_TYPE_STRING_ARRAY); + g_assert (value != NULL); - nm_setting_ip4_config_clear_addresses (s_ip4); - g_assert_cmpint (nm_setting_ip4_config_get_num_addresses (s_ip4), ==, 0); + g_variant_get (value, "^as", &labels); + g_assert_cmpint (g_strv_length (labels), ==, 2); + g_assert_cmpstr (labels[0], ==, "eth0:1"); + g_assert_cmpstr (labels[1], ==, ""); - /* Setting addrs but not labels will result in empty labels */ - g_object_set (G_OBJECT (s_ip4), - NM_SETTING_IP4_CONFIG_ADDRESSES, addrs, - NULL); - g_ptr_array_unref (addrs); - nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); + g_variant_unref (setting_dict); + g_variant_unref (value); + g_strfreev (labels); + + /* And should be deserialized */ + conn = nm_simple_connection_new_from_dbus (dict, &error); g_assert_no_error (error); - g_assert_cmpint (nm_setting_ip4_config_get_num_addresses (s_ip4), ==, 2); + g_variant_unref (dict); + + s_ip4 = nm_connection_get_setting_ip4_config (conn); addr = nm_setting_ip4_config_get_address (s_ip4, 0); g_assert_cmpstr (nm_ip_address_get_address (addr), ==, "2.2.2.2"); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 0); - g_assert_cmpstr (label, ==, ""); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label != NULL); + g_assert_cmpstr (g_variant_get_string (label, NULL), ==, "eth0:1"); addr = nm_setting_ip4_config_get_address (s_ip4, 1); g_assert_cmpstr (nm_ip_address_get_address (addr), ==, "3.3.3.3"); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 1); - g_assert_cmpstr (label, ==, ""); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label == NULL); + + /* Test explicit property assignment */ + g_object_get (G_OBJECT (s_ip4), + NM_SETTING_IP4_CONFIG_ADDRESSES, &addrs, + NULL); + + nm_setting_ip4_config_clear_addresses (s_ip4); + g_assert_cmpint (nm_setting_ip4_config_get_num_addresses (s_ip4), ==, 0); - /* Setting labels now will leave addresses untouched */ g_object_set (G_OBJECT (s_ip4), - "address-labels", labels, + NM_SETTING_IP4_CONFIG_ADDRESSES, addrs, NULL); - g_strfreev (labels); + g_ptr_array_unref (addrs); nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); g_assert_no_error (error); g_assert_cmpint (nm_setting_ip4_config_get_num_addresses (s_ip4), ==, 2); addr = nm_setting_ip4_config_get_address (s_ip4, 0); g_assert_cmpstr (nm_ip_address_get_address (addr), ==, "2.2.2.2"); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 0); - g_assert_cmpstr (label, ==, "eth0:1"); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label != NULL); + g_assert_cmpstr (g_variant_get_string (label, NULL), ==, "eth0:1"); addr = nm_setting_ip4_config_get_address (s_ip4, 1); g_assert_cmpstr (nm_ip_address_get_address (addr), ==, "3.3.3.3"); - label = _nm_setting_ip4_config_get_address_label (s_ip4, 1); - g_assert_cmpstr (label, ==, ""); - - /* Setting labels to a value that's too short or too long will result in - * the setting not verifying. - */ - labels = g_strsplit ("eth0:2", ",", -1); - g_object_set (G_OBJECT (s_ip4), - "address-labels", labels, - NULL); - g_strfreev (labels); - - nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); - g_assert_error (error, NM_CONNECTION_ERROR, NM_CONNECTION_ERROR_INVALID_PROPERTY); - g_assert (g_str_has_prefix (error->message, "ipv4.address-labels:")); - g_clear_error (&error); - - labels = g_strsplit ("eth0:2,eth0:3", ",", -1); - g_object_set (G_OBJECT (s_ip4), - "address-labels", labels, - NULL); - g_strfreev (labels); - nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); - g_assert_no_error (error); - - labels = g_strsplit ("eth0:2,eth0:3,eth0:4", ",", -1); - g_object_set (G_OBJECT (s_ip4), - "address-labels", labels, - NULL); - g_strfreev (labels); - nm_setting_verify (NM_SETTING (s_ip4), NULL, &error); - g_assert_error (error, NM_CONNECTION_ERROR, NM_CONNECTION_ERROR_INVALID_PROPERTY); - g_assert (g_str_has_prefix (error->message, "ipv4.address-labels:")); - g_clear_error (&error); + label = nm_ip_address_get_attribute (addr, "label"); + g_assert (label == NULL); - g_object_unref (s_ip4); + g_object_unref (conn); } static void @@ -1640,7 +1634,6 @@ test_connection_diff_a_only (void) { NM_SETTING_IP4_CONFIG_DNS, NM_SETTING_DIFF_RESULT_IN_A }, { NM_SETTING_IP4_CONFIG_DNS_SEARCH, NM_SETTING_DIFF_RESULT_IN_A }, { NM_SETTING_IP4_CONFIG_ADDRESSES, NM_SETTING_DIFF_RESULT_IN_A }, - { "address-labels", NM_SETTING_DIFF_RESULT_IN_A }, { NM_SETTING_IP4_CONFIG_ROUTES, NM_SETTING_DIFF_RESULT_IN_A }, { NM_SETTING_IP4_CONFIG_IGNORE_AUTO_ROUTES, NM_SETTING_DIFF_RESULT_IN_A }, { NM_SETTING_IP4_CONFIG_IGNORE_AUTO_DNS, NM_SETTING_DIFF_RESULT_IN_A }, |