From b46ed879198e911521373391c27982034699dfe5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ji=C5=99=C3=AD=20Klime=C5=A1?= Date: Tue, 10 Feb 2015 15:33:35 +0100 Subject: [PATCH] nmcli: allow adding 'generic' connections via nmcli connection add MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 'nmcli connection edit' already allows adding and editing generic connections (added by 2a2af5825a6db62e7a88bb249cf7876551ed7fa3). (cherry picked from commit 0ff9b75387b7ac2fd0235b23699990834426c467) Signed-off-by: Jiří Klimeš --- clients/cli/connections.c | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/clients/cli/connections.c b/clients/cli/connections.c index 8d138bd..3c95c03 100644 --- a/clients/cli/connections.c +++ b/clients/cli/connections.c @@ -4006,6 +4006,7 @@ complete_connection_by_type (NMConnection *connection, GError **error) { NMSettingConnection *s_con; + NMSettingGeneric *s_generic; NMSettingWired *s_wired; NMSettingInfiniband *s_infiniband; NMSettingWireless *s_wifi; @@ -5232,6 +5233,10 @@ cleanup_olpc: if (!success) return FALSE; + } else if (!strcmp (con_type, NM_SETTING_GENERIC_SETTING_NAME)) { + /* Add 'generic' setting */ + s_generic = (NMSettingGeneric *) nm_setting_generic_new (); + nm_connection_add_setting (connection, NM_SETTING (s_generic)); } else { g_set_error (error, NMCLI_ERROR, NMC_RESULT_ERROR_USER_INPUT, _("Error: '%s' is not a valid connection type."), -- 2.1.0 From 1f7be4951900ca3004cb258225bc924f49deefd2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ji=C5=99=C3=AD=20Klime=C5=A1?= Date: Fri, 18 Sep 2015 10:42:10 +0200 Subject: [PATCH 1/3] libnm-core/libnm-util: fix an assertion in adsl setting MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit (process:7799): GLib-CRITICAL **: g_ascii_strdown: assertion 'str != NULL' failed (cherry picked from commit 3d64d45d16d761802e92cc3d83a89e3dd572d36d) Signed-off-by: Jiří Klimeš --- libnm-core/nm-setting-adsl.c | 7 +++++-- libnm-util/nm-setting-adsl.c | 7 +++++-- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/libnm-core/nm-setting-adsl.c b/libnm-core/nm-setting-adsl.c index 2e71f8e..7d78f06 100644 --- a/libnm-core/nm-setting-adsl.c +++ b/libnm-core/nm-setting-adsl.c @@ -267,6 +267,7 @@ set_property (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec) { NMSettingAdslPrivate *priv = NM_SETTING_ADSL_GET_PRIVATE (object); + const char *str; switch (prop_id) { case PROP_USERNAME: @@ -282,11 +283,13 @@ set_property (GObject *object, guint prop_id, break; case PROP_PROTOCOL: g_free (priv->protocol); - priv->protocol = g_ascii_strdown (g_value_get_string (value), -1); + str = g_value_get_string (value); + priv->protocol = str ? g_ascii_strdown (str, -1) : NULL; break; case PROP_ENCAPSULATION: g_free (priv->encapsulation); - priv->encapsulation = g_ascii_strdown (g_value_get_string (value), -1); + str = g_value_get_string (value); + priv->encapsulation = str ? g_ascii_strdown (str, -1) : NULL; break; case PROP_VPI: priv->vpi = g_value_get_uint (value); diff --git a/libnm-util/nm-setting-adsl.c b/libnm-util/nm-setting-adsl.c index 5355011..51560a7 100644 --- a/libnm-util/nm-setting-adsl.c +++ b/libnm-util/nm-setting-adsl.c @@ -287,6 +287,7 @@ set_property (GObject *object, guint prop_id, const GValue *value, GParamSpec *pspec) { NMSettingAdslPrivate *priv = NM_SETTING_ADSL_GET_PRIVATE (object); + const char *str; switch (prop_id) { case PROP_USERNAME: @@ -302,11 +303,13 @@ set_property (GObject *object, guint prop_id, break; case PROP_PROTOCOL: g_free (priv->protocol); - priv->protocol = g_ascii_strdown (g_value_get_string (value), -1); + str = g_value_get_string (value); + priv->protocol = str ? g_ascii_strdown (str, -1) : NULL; break; case PROP_ENCAPSULATION: g_free (priv->encapsulation); - priv->encapsulation = g_ascii_strdown (g_value_get_string (value), -1); + str = g_value_get_string (value); + priv->encapsulation = str ? g_ascii_strdown (str, -1) : NULL; break; case PROP_VPI: priv->vpi = g_value_get_uint (value); -- 2.1.0 From 9bca3b7a37f00b94e3feec0ab400cfa5dfe60831 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ji=C5=99=C3=AD=20Klime=C5=A1?= Date: Fri, 18 Sep 2015 11:08:28 +0200 Subject: [PATCH 2/3] cli: initialize adsl.protocol in editor when creating a new connection MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The protocol is required and it is nice to have a valid initial value for the property. (cherry picked from commit 5502d8691a0e1b7174a0be85951f155fa587e400) Signed-off-by: Jiří Klimeš --- clients/cli/connections.c | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/clients/cli/connections.c b/clients/cli/connections.c index 3c95c03..e8391ea 100644 --- a/clients/cli/connections.c +++ b/clients/cli/connections.c @@ -8378,6 +8378,14 @@ editor_init_new_connection (NmCli *nmc, NMConnection *connection) nmc_setting_custom_init (base_setting); } + /* ADSL */ + if (g_strcmp0 (con_type, NM_SETTING_ADSL_SETTING_NAME) == 0) { + /* Initialize a protocol */ + g_object_set (NM_SETTING_ADSL (base_setting), + NM_SETTING_ADSL_PROTOCOL, NM_SETTING_ADSL_PROTOCOL_PPPOE, + NULL); + } + /* Always add IPv4 and IPv6 settings for non-slave connections */ setting = nm_setting_ip4_config_new (); nmc_setting_custom_init (setting); -- 2.1.0 From b590a318398decb31c9b21f481dbc7e28e0ecc8e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ji=C5=99=C3=AD=20Klime=C5=A1?= Date: Fri, 18 Sep 2015 12:05:49 +0200 Subject: [PATCH 3/3] cli: allow creating ADSL connections with 'nmcli connection add' (rh #1264089) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit https://bugzilla.redhat.com/show_bug.cgi?id=1264089 (cherry picked from commit 290c1626b9788aa90861ca423c0dffb59fe29876) Signed-off-by: Jiří Klimeš --- clients/cli/connections.c | 141 +++++++++++++++++++++++++++++++++++++++++++ clients/cli/nmcli-completion | 19 +++++- man/nmcli.1.in | 12 ++++ 3 files changed, 171 insertions(+), 1 deletion(-) diff --git a/clients/cli/connections.c b/clients/cli/connections.c index e8391ea..b6614ae 100644 --- a/clients/cli/connections.c +++ b/clients/cli/connections.c @@ -397,6 +397,10 @@ usage_connection_add (void) " olpc-mesh: ssid \n" " [channel <1-13>]\n" " [dhcp-anycast ]\n\n" + " adsl: username \n" + " protocol pppoa|pppoe|ipoatm\n" + " [password ]\n" + " [encapsulation vcmux|llc]\n\n" " IP_OPTIONS:\n" " [ip4 ] [gw4 ]\n" " [ip6 ] [gw6 ]\n\n")); @@ -2904,6 +2908,29 @@ check_infiniband_mode (char **mode, GError **error) return check_valid_enumeration (mode, modes, "mode", _("InfiniBand transport mode"), error); } +/* Checks ADSL protocol */ +static gboolean +check_adsl_protocol (char **protocol, GError **error) +{ + const char *protos[] = { NM_SETTING_ADSL_PROTOCOL_PPPOA, + NM_SETTING_ADSL_PROTOCOL_PPPOE, + NM_SETTING_ADSL_PROTOCOL_IPOATM, + NULL }; + + return check_valid_enumeration (protocol, protos, "protocol", _("ADSL protocol"), error); +} + +/* Checks ADSL encapsulation */ +static gboolean +check_adsl_encapsulation (char **encapsulation, GError **error) +{ + const char *modes[] = { NM_SETTING_ADSL_ENCAPSULATION_VCMUX, + NM_SETTING_ADSL_ENCAPSULATION_LLC, + NULL }; + + return check_valid_enumeration (encapsulation, modes, "encapsulation", _("ADSL encapsulation"), error); +} + static gboolean check_and_convert_vlan_flags (const char *flags, guint32 *flags_int, GError **error) { @@ -3871,6 +3898,33 @@ do_questionnaire_olpc (char **channel, char **dhcp_anycast) } } +#define PROMPT_ADSL_ENCAP "(" NM_SETTING_ADSL_ENCAPSULATION_VCMUX "/" NM_SETTING_ADSL_ENCAPSULATION_LLC ") [none]: " +static void +do_questionnaire_adsl (char **password, char **encapsulation) +{ + gboolean once_more; + GError *error = NULL; + + /* Ask for optional 'adsl' arguments. */ + if (!want_provide_opt_args (_("ADSL"), 2)) + return; + + if (!*password) + *password = nmc_readline (_("Password [none]: ")); + + if (!*encapsulation) { + do { + *encapsulation = nmc_readline (_("ADSL encapsulation %s"), PROMPT_ADSL_ENCAP); + once_more = !check_adsl_encapsulation (encapsulation, &error); + if (once_more) { + g_print ("%s\n", error->message); + g_clear_error (&error); + g_free (*encapsulation); + } + } while (once_more); + } +} + static gboolean split_address (char* str, char **ip, char **rest) { @@ -4023,6 +4077,7 @@ complete_connection_by_type (NMConnection *connection, NMSettingBridgePort *s_bridge_port; NMSettingVpn *s_vpn; NMSettingOlpcMesh *s_olpc_mesh; + NMSettingAdsl *s_adsl; g_return_val_if_fail (error == NULL || *error == NULL, FALSE); @@ -5233,6 +5288,74 @@ cleanup_olpc: if (!success) return FALSE; + } else if (!strcmp (con_type, NM_SETTING_ADSL_SETTING_NAME)) { + /* Build up the settings required for 'adsl' */ + gboolean success = FALSE; + char *username_ask = NULL; + const char *username = NULL; + char *protocol_ask = NULL; + const char *protocol = NULL; + const char *password_c = NULL; + char *password = NULL; + const char *encapsulation_c = NULL; + char *encapsulation = NULL; + nmc_arg_t exp_args[] = { {"username", TRUE, &username, !ask}, + {"protocol", TRUE, &protocol, !ask}, + {"password", TRUE, &password_c, FALSE}, + {"encapsulation", TRUE, &encapsulation_c, FALSE}, + {NULL} }; + + if (!nmc_parse_args (exp_args, FALSE, &argc, &argv, error)) + return FALSE; + + if (!username && ask) + username = username_ask = nmc_readline (_("Username: ")); + if (!username) { + g_set_error_literal (error, NMCLI_ERROR, NMC_RESULT_ERROR_USER_INPUT, + _("Error: 'username' is required.")); + goto cleanup_adsl; + } + +#define PROMPT_ADSL_PROTO "(" NM_SETTING_ADSL_PROTOCOL_PPPOA "/" NM_SETTING_ADSL_PROTOCOL_PPPOE "/" NM_SETTING_ADSL_PROTOCOL_IPOATM "): " + if (!protocol && ask) + protocol = protocol_ask = nmc_readline (_("Protocol %s"), PROMPT_ADSL_PROTO); + if (!protocol) { + g_set_error_literal (error, NMCLI_ERROR, NMC_RESULT_ERROR_USER_INPUT, + _("Error: 'protocol' is required.")); + goto cleanup_adsl; + } + if (!check_adsl_protocol (&protocol_ask, error)) + goto cleanup_adsl; + + /* Also ask for all optional arguments if '--ask' is specified. */ + password = g_strdup (password_c); + encapsulation = g_strdup (encapsulation_c); + if (ask) + do_questionnaire_adsl (&password, &encapsulation); + + if (!check_adsl_encapsulation (&encapsulation, error)) + goto cleanup_adsl; + + /* Add ADSL setting */ + s_adsl = (NMSettingAdsl *) nm_setting_adsl_new (); + nm_connection_add_setting (connection, NM_SETTING (s_adsl)); + + g_object_set (s_adsl, + NM_SETTING_ADSL_USERNAME, username, + NM_SETTING_ADSL_PROTOCOL, protocol, + NM_SETTING_ADSL_PASSWORD, password, + NM_SETTING_ADSL_ENCAPSULATION, encapsulation, + NULL); + + success = TRUE; +cleanup_adsl: + g_free (username_ask); + g_free (password); + g_free (protocol_ask); + g_free (encapsulation); + if (!success) + return FALSE; + } else if (!strcmp (con_type, NM_SETTING_GENERIC_SETTING_NAME)) { /* Add 'generic' setting */ s_generic = (NMSettingGeneric *) nm_setting_generic_new (); @@ -5470,6 +5593,20 @@ gen_func_bond_mon_mode (const char *text, int state) } static char * +gen_func_adsl_proto (const char *text, int state) +{ + const char *words[] = { "pppoe", "pppoa", "ipoatm", NULL }; + return nmc_rl_gen_func_basic (text, state, words); +} + +static char * +gen_func_adsl_encap (const char *text, int state) +{ + const char *words[] = { "vcmux", "llc", NULL }; + return nmc_rl_gen_func_basic (text, state, words); +} + +static char * gen_func_master_ifnames (const char *text, int state) { int i; @@ -5557,6 +5694,10 @@ nmcli_con_add_tab_completion (const char *text, int start, int end) generator_func = gen_func_bond_mode; else if (g_str_has_suffix (rl_prompt, PROMPT_BOND_MON_MODE)) generator_func = gen_func_bond_mon_mode; + else if (g_str_has_suffix (rl_prompt, PROMPT_ADSL_PROTO)) + generator_func = gen_func_adsl_proto; + else if (g_str_has_suffix (rl_prompt, PROMPT_ADSL_ENCAP)) + generator_func = gen_func_adsl_encap; if (generator_func) match_array = rl_completion_matches (text, generator_func); diff --git a/clients/cli/nmcli-completion b/clients/cli/nmcli-completion index 4146eae..9f34b83 100644 --- a/clients/cli/nmcli-completion +++ b/clients/cli/nmcli-completion @@ -353,7 +353,7 @@ _nmcli_compl_ARGS() # user friendly. Only complete them, if the current word already starts with an "8". _nmcli_list "802-3-ethernet 802-11-wireless 802-11-olpc-mesh" else - _nmcli_list "ethernet wifi wimax gsm cdma infiniband bluetooth vpn olpc-mesh vlan bond bond-slave bridge bridge-slave team team-slave pppoe" + _nmcli_list "ethernet wifi wimax gsm cdma infiniband bluetooth vpn olpc-mesh vlan bond bond-slave bridge bridge-slave team team-slave pppoe adsl" fi return 0 fi @@ -522,6 +522,18 @@ _nmcli_compl_ARGS() return 0 fi ;; + encapsulation) + if [[ "${#words[@]}" -eq 2 ]]; then + _nmcli_list "vcmux llc" + return 0 + fi + ;; + protocol) + if [[ "${#words[@]}" -eq 2 ]]; then + _nmcli_list "pppoa pppoe ipoatm" + return 0 + fi + ;; *) return 1 ;; @@ -1010,6 +1022,11 @@ _nmcli() OPTIONS_TYPED=(username password service mtu mac) OPTIONS_MANDATORY=(username) ;; + a|ad|ads|adsl) + OPTIONS_TYPE=adsl + OPTIONS_TYPED=(username password protocol encapsulation) + OPTIONS_MANDATORY=(username protocol) + ;; *) # for an unknown connection type, we stop completion here return 0 diff --git a/man/nmcli.1.in b/man/nmcli.1.in index 6df844d..a680901 100644 --- a/man/nmcli.1.in +++ b/man/nmcli.1.in @@ -619,6 +619,18 @@ to be sent back out through the slave the frame was received on (default: yes) .RE .RS .TP +.B adsl: +.IP "\fIusername \fP" 42 +\(en ADSL user name +.IP "\fIprotocol pppoa|pppoe|ipoatm\fP" 42 +\(en ADSL protocol +.IP "\fI[password ]\fP" 42 +\(en ADSL password +.IP "\fI[encapsulation vcmux|llc]\fP" 42 +\(en ADSL encapsulation +.RE +.RS +.TP .B IP_OPTIONS: .IP "\fI[ip4 ] [gw4 ]\fP" 42 \(en IPv4 addresses -- 2.1.0