summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--libnm-core/nm-connection.c22
-rw-r--r--libnm-core/nm-setting-bond.c35
-rw-r--r--libnm-core/nm-utils.c61
-rw-r--r--libnm-core/nm-utils.h5
-rw-r--r--libnm/libnm.ver2
-rw-r--r--src/settings/plugins/ifcfg-rh/reader.c3
-rw-r--r--src/settings/plugins/ifcfg-rh/tests/network-scripts/Makefile.am1
-rw-r--r--src/settings/plugins/ifcfg-rh/tests/network-scripts/ifcfg-test-bond-mode-numeric5
-rw-r--r--src/settings/plugins/ifcfg-rh/tests/test-ifcfg-rh.c32
9 files changed, 152 insertions, 14 deletions
diff --git a/libnm-core/nm-connection.c b/libnm-core/nm-connection.c
index 907713bd08..239079e3b1 100644
--- a/libnm-core/nm-connection.c
+++ b/libnm-core/nm-connection.c
@@ -723,6 +723,27 @@ _normalize_infiniband_mtu (NMConnection *self, GHashTable *parameters)
return FALSE;
}
+static gboolean
+_normalize_bond_mode (NMConnection *self, GHashTable *parameters)
+{
+ NMSettingBond *s_bond = nm_connection_get_setting_bond (self);
+
+ /* Convert mode from numeric to string notation */
+ if (s_bond) {
+ const char *mode = nm_setting_bond_get_option_by_name (s_bond, NM_SETTING_BOND_OPTION_MODE);
+ int mode_int = nm_utils_bond_mode_string_to_int (mode);
+
+ if (mode_int != -1) {
+ const char *mode_new = nm_utils_bond_mode_int_to_string (mode_int);
+ if (g_strcmp0 (mode_new, mode) != 0) {
+ nm_setting_bond_add_option (s_bond, NM_SETTING_BOND_OPTION_MODE, mode_new);
+ return TRUE;
+ }
+ }
+ }
+ return FALSE;
+}
+
/**
* nm_connection_verify:
* @connection: the #NMConnection to verify
@@ -936,6 +957,7 @@ nm_connection_normalize (NMConnection *connection,
was_modified |= _normalize_connection_slave_type (connection);
was_modified |= _normalize_ip_config (connection, parameters);
was_modified |= _normalize_infiniband_mtu (connection, parameters);
+ was_modified |= _normalize_bond_mode (connection, parameters);
/* Verify anew. */
success = _nm_connection_verify (connection, error);
diff --git a/libnm-core/nm-setting-bond.c b/libnm-core/nm-setting-bond.c
index bb05312539..5441a090da 100644
--- a/libnm-core/nm-setting-bond.c
+++ b/libnm-core/nm-setting-bond.c
@@ -440,15 +440,8 @@ verify (NMSetting *setting, NMConnection *connection, GError **error)
NMSettingBondPrivate *priv = NM_SETTING_BOND_GET_PRIVATE (setting);
GHashTableIter iter;
const char *key, *value;
- const char *valid_modes[] = { "balance-rr",
- "active-backup",
- "balance-xor",
- "broadcast",
- "802.3ad",
- "balance-tlb",
- "balance-alb",
- NULL };
- int miimon = 0, arp_interval = 0;
+ int mode, miimon = 0, arp_interval = 0;
+ const char *mode_orig, *mode_new;
const char *arp_ip_target = NULL;
const char *lacp_rate;
const char *primary;
@@ -484,7 +477,8 @@ verify (NMSetting *setting, NMConnection *connection, GError **error)
g_prefix_error (error, "%s.%s: ", NM_SETTING_BOND_SETTING_NAME, NM_SETTING_BOND_OPTIONS);
}
- value = g_hash_table_lookup (priv->options, NM_SETTING_BOND_OPTION_MODE);
+ /* Verify bond mode */
+ mode_orig = value = g_hash_table_lookup (priv->options, NM_SETTING_BOND_OPTION_MODE);
if (!value) {
g_set_error (error,
NM_CONNECTION_ERROR,
@@ -494,7 +488,8 @@ verify (NMSetting *setting, NMConnection *connection, GError **error)
g_prefix_error (error, "%s.%s: ", NM_SETTING_BOND_SETTING_NAME, NM_SETTING_BOND_OPTIONS);
return FALSE;
}
- if (!_nm_utils_string_in_list (value, valid_modes)) {
+ mode = nm_utils_bond_mode_string_to_int (value);
+ if (mode == -1) {
g_set_error (error,
NM_CONNECTION_ERROR,
NM_CONNECTION_ERROR_INVALID_PROPERTY,
@@ -503,6 +498,7 @@ verify (NMSetting *setting, NMConnection *connection, GError **error)
g_prefix_error (error, "%s.%s: ", NM_SETTING_BOND_SETTING_NAME, NM_SETTING_BOND_OPTIONS);
return FALSE;
}
+ mode_new = value = nm_utils_bond_mode_int_to_string (mode);
/* Make sure mode is compatible with other settings */
if ( strcmp (value, "balance-alb") == 0
@@ -645,7 +641,22 @@ verify (NMSetting *setting, NMConnection *connection, GError **error)
return FALSE;
}
- return _nm_connection_verify_required_interface_name (connection, error);
+ if (!_nm_connection_verify_required_interface_name (connection, error))
+ return FALSE;
+
+ /* *** errors above here should be always fatal, below NORMALIZABLE_ERROR *** */
+
+ if (g_strcmp0 (mode_orig, mode_new) != 0) {
+ g_set_error (error,
+ NM_CONNECTION_ERROR,
+ NM_CONNECTION_ERROR_INVALID_PROPERTY,
+ _("'%s' option should be string"),
+ NM_SETTING_BOND_OPTION_MODE);
+ g_prefix_error (error, "%s.%s: ", NM_SETTING_BOND_SETTING_NAME, NM_SETTING_BOND_OPTIONS);
+ return NM_SETTING_VERIFY_NORMALIZABLE;
+ }
+
+ return TRUE;
}
static void
diff --git a/libnm-core/nm-utils.c b/libnm-core/nm-utils.c
index b3198f4c0b..f55a7dac03 100644
--- a/libnm-core/nm-utils.c
+++ b/libnm-core/nm-utils.c
@@ -3213,3 +3213,64 @@ nm_utils_check_virtual_device_compatibility (GType virtual_type, GType other_typ
return FALSE;
}
}
+
+typedef struct {
+ const char *str;
+ const char *num;
+} BondMode;
+
+static BondMode bond_mode_table[] = {
+ [0] = { "balance-rr", "0" },
+ [1] = { "active-backup", "1" },
+ [2] = { "balance-xor", "2" },
+ [3] = { "broadcast", "3" },
+ [4] = { "802.3ad", "4" },
+ [5] = { "balance-tlb", "5" },
+ [6] = { "balance-alb", "6" },
+};
+
+/**
+ * nm_utils_bond_mode_int_to_string:
+ * @mode: bonding mode as a numeric value
+ *
+ * Convert bonding mode from integer value to descriptive name.
+ * See https://www.kernel.org/doc/Documentation/networking/bonding.txt for
+ * available modes.
+ *
+ * Returns: bonding mode string, or NULL on error
+*/
+
+const char *
+nm_utils_bond_mode_int_to_string (int mode)
+{
+ if (mode >= 0 && mode < G_N_ELEMENTS (bond_mode_table))
+ return bond_mode_table[mode].str;
+ return NULL;
+}
+
+/**
+ * nm_utils_bond_mode_string_to_int:
+ * @mode: bonding mode as string
+ *
+ * Convert bonding mode from string representation to numeric value.
+ * See https://www.kernel.org/doc/Documentation/networking/bonding.txt for
+ * available modes.
+ * The @mode string can be either a descriptive name or a number (as string).
+ *
+ * Returns: numeric bond mode, or -1 on error
+*/
+int
+nm_utils_bond_mode_string_to_int (const char *mode)
+{
+ int i;
+
+ if (!mode || !*mode)
+ return -1;
+
+ for (i = 0; i < G_N_ELEMENTS (bond_mode_table); i++) {
+ if ( strcmp (mode, bond_mode_table[i].str) == 0
+ || strcmp (mode, bond_mode_table[i].num) == 0)
+ return i;
+ }
+ return -1;
+}
diff --git a/libnm-core/nm-utils.h b/libnm-core/nm-utils.h
index 8c22cfd168..7393040696 100644
--- a/libnm-core/nm-utils.h
+++ b/libnm-core/nm-utils.h
@@ -15,7 +15,7 @@
* Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
* Boston, MA 02110-1301 USA.
*
- * Copyright 2005 - 2013 Red Hat, Inc.
+ * Copyright 2005 - 2014 Red Hat, Inc.
*/
#ifndef __NM_UTILS_H__
@@ -185,6 +185,9 @@ gboolean nm_utils_ipaddr_valid (int family, const char *ip);
gboolean nm_utils_check_virtual_device_compatibility (GType virtual_type, GType other_type);
+int nm_utils_bond_mode_string_to_int (const char *mode);
+const char *nm_utils_bond_mode_int_to_string (int mode);
+
G_END_DECLS
#endif /* __NM_UTILS_H__ */
diff --git a/libnm/libnm.ver b/libnm/libnm.ver
index 82bcdb9f07..322d553560 100644
--- a/libnm/libnm.ver
+++ b/libnm/libnm.ver
@@ -754,6 +754,8 @@ global:
nm_state_get_type;
nm_utils_ap_mode_security_valid;
nm_utils_bin2hexstr;
+ nm_utils_bond_mode_int_to_string;
+ nm_utils_bond_mode_string_to_int;
nm_utils_check_virtual_device_compatibility;
nm_utils_escape_ssid;
nm_utils_file_is_certificate;
diff --git a/src/settings/plugins/ifcfg-rh/reader.c b/src/settings/plugins/ifcfg-rh/reader.c
index f2da5416c0..c9c6b64474 100644
--- a/src/settings/plugins/ifcfg-rh/reader.c
+++ b/src/settings/plugins/ifcfg-rh/reader.c
@@ -3832,7 +3832,8 @@ handle_bond_option (NMSettingBond *s_bond,
}
if (!nm_setting_bond_add_option (s_bond, key, sanitized ? sanitized : value))
- PARSE_WARNING ("invalid bonding option '%s'", key);
+ PARSE_WARNING ("invalid bonding option '%s' = %s",
+ key, sanitized ? sanitized : value);
g_free (sanitized);
}
diff --git a/src/settings/plugins/ifcfg-rh/tests/network-scripts/Makefile.am b/src/settings/plugins/ifcfg-rh/tests/network-scripts/Makefile.am
index 8941da3a62..352db1e718 100644
--- a/src/settings/plugins/ifcfg-rh/tests/network-scripts/Makefile.am
+++ b/src/settings/plugins/ifcfg-rh/tests/network-scripts/Makefile.am
@@ -106,6 +106,7 @@ EXTRA_DIST = \
ifcfg-test-bond-main \
ifcfg-test-bond-slave \
ifcfg-test-bond-slave-ib \
+ ifcfg-test-bond-mode-numeric \
ifcfg-test-dcb \
ifcfg-test-dcb-default-app-priorities \
ifcfg-test-dcb-bad-booleans \
diff --git a/src/settings/plugins/ifcfg-rh/tests/network-scripts/ifcfg-test-bond-mode-numeric b/src/settings/plugins/ifcfg-rh/tests/network-scripts/ifcfg-test-bond-mode-numeric
new file mode 100644
index 0000000000..9989f58b97
--- /dev/null
+++ b/src/settings/plugins/ifcfg-rh/tests/network-scripts/ifcfg-test-bond-mode-numeric
@@ -0,0 +1,5 @@
+DEVICE=bond0
+ONBOOT=no
+TYPE=Bond
+BOOTPROTO=dhcp
+BONDING_OPTS="mode=4 miimon=100"
diff --git a/src/settings/plugins/ifcfg-rh/tests/test-ifcfg-rh.c b/src/settings/plugins/ifcfg-rh/tests/test-ifcfg-rh.c
index e05a4ccb20..c56be79638 100644
--- a/src/settings/plugins/ifcfg-rh/tests/test-ifcfg-rh.c
+++ b/src/settings/plugins/ifcfg-rh/tests/test-ifcfg-rh.c
@@ -11443,6 +11443,37 @@ test_write_bond_slave_ib (void)
g_object_unref (reread);
}
+static void
+test_read_bond_opts_mode_numeric (void)
+{
+ NMConnection *connection;
+ NMSettingConnection *s_con;
+ NMSettingBond *s_bond;
+ gboolean success;
+ GError *error = NULL;
+
+ connection = connection_from_file_test (TEST_IFCFG_DIR "/network-scripts/ifcfg-test-bond-mode-numeric",
+ NULL, TYPE_ETHERNET, NULL, &error);
+ g_assert_no_error (error);
+ g_assert (connection);
+
+ success = nm_connection_verify (connection, &error);
+ g_assert_no_error (error);
+ g_assert (success);
+
+ g_assert_cmpstr (nm_connection_get_interface_name (connection), ==, "bond0");
+
+ s_con = nm_connection_get_setting_connection (connection);
+ g_assert (s_con);
+ g_assert_cmpstr (nm_setting_connection_get_connection_type (s_con), ==, NM_SETTING_BOND_SETTING_NAME);
+
+ s_bond = nm_connection_get_setting_bond (connection);
+ g_assert (s_bond);
+ g_assert_cmpstr (nm_setting_bond_get_option_by_name (s_bond, NM_SETTING_BOND_OPTION_MODE), ==, "802.3ad");
+
+ g_object_unref (connection);
+}
+
#define DCB_ALL_FLAGS (NM_SETTING_DCB_FLAG_ENABLE | \
NM_SETTING_DCB_FLAG_ADVERTISE | \
NM_SETTING_DCB_FLAG_WILLING)
@@ -12525,6 +12556,7 @@ int main (int argc, char **argv)
test_write_bond_main ();
test_write_bond_slave ();
test_write_bond_slave_ib ();
+ g_test_add_func (TPATH "bond/bonding-opts-numeric-mode", test_read_bond_opts_mode_numeric);
/* bridging */
test_read_bridge_main ();