diff options
author | Jiří Klimeš <jklimes@redhat.com> | 2014-06-19 11:25:17 +0200 |
---|---|---|
committer | Jiří Klimeš <jklimes@redhat.com> | 2014-07-11 11:32:39 +0200 |
commit | 88f547c6c4ee2123d544ce5b4610b1d6c6e4a95d (patch) | |
tree | 8a4411eddf33c112a3de82c78878bad97377bcfc | |
parent | 831c1ad1cb1d8393131d5d59eac696ba91a12d4c (diff) | |
download | NetworkManager-jk/dev-delete-rh1034150.tar.gz |
cli: add 'nmcli device delete <ifname>' command (rh #1034150)jk/dev-delete-rh1034150
It only works for software devices. When called for a hardware device,
an error is returned and the device is not deleted.
https://bugzilla.redhat.com/show_bug.cgi?id=1034150
-rw-r--r-- | cli/completion/nmcli | 5 | ||||
-rw-r--r-- | cli/src/devices.c | 126 | ||||
-rw-r--r-- | man/nmcli.1.in | 12 |
3 files changed, 137 insertions, 6 deletions
diff --git a/cli/completion/nmcli b/cli/completion/nmcli index 343c732205..e6dc5b5d2d 100644 --- a/cli/completion/nmcli +++ b/cli/completion/nmcli @@ -1164,7 +1164,7 @@ _nmcli() ;; d|de|dev|devi|devic|device) if [[ ${#words[@]} -eq 2 ]]; then - _nmcli_compl_COMMAND "$command" status show connect disconnect wifi wimax + _nmcli_compl_COMMAND "$command" status show connect disconnect delete wifi wimax elif [[ ${#words[@]} -gt 2 ]]; then case "$command" in s|st|sta|stat|statu|status) @@ -1174,7 +1174,8 @@ _nmcli() ;; sh|sho|show| \ c|co|con|conn|conne|connec|connect| \ - d|di|dis|disc|disco|discon|disconn|disconne|disconnec|disconnect) + d|di|dis|disc|disco|discon|disconn|disconne|disconnec|disconnect| \ + de|del|dele|delet|delete) if [[ ${#words[@]} -eq 3 ]]; then _nmcli_compl_COMMAND_nl "${words[2]}" "$(_nmcli_dev_status DEVICE)" fi diff --git a/cli/src/devices.c b/cli/src/devices.c index 2812e0f7b0..36aab74fc1 100644 --- a/cli/src/devices.c +++ b/cli/src/devices.c @@ -278,14 +278,15 @@ usage (void) fprintf (stderr, _("Usage: nmcli device { COMMAND | help }\n\n" #if WITH_WIMAX - "COMMAND := { status | show | connect | disconnect | wifi | wimax }\n\n" + "COMMAND := { status | show | connect | disconnect | delete | wifi | wimax }\n\n" #else - "COMMAND := { status | show | connect | disconnect | wifi }\n\n" + "COMMAND := { status | show | connect | disconnect | delete | wifi }\n\n" #endif " status\n\n" " show [<ifname>]\n\n" " connect <ifname>\n\n" " disconnect <ifname>\n\n" + " delete <ifname>\n\n" " wifi [list [ifname <ifname>] [bssid <BSSID>]]\n\n" " wifi connect <(B)SSID> [password <password>] [wep-key-type key|phrase] [ifname <ifname>]\n" " [bssid <BSSID>] [name <name>] [private yes|no]\n\n" @@ -351,6 +352,20 @@ usage_device_disconnect (void) } static void +usage_device_delete (void) +{ + fprintf (stderr, + _("Usage: nmcli device delete { ARGUMENTS | help }\n" + "\n" + "ARGUMENTS := <ifname>\n" + "\n" + "Deletes the software device.\n" + "The command removes the interface. It only works for software devices\n" + "(like bonds, bridges, etc.). Hardware devices cannot be deleted by the\n" + "command.\n\n")); +} + +static void usage_device_wifi (void) { fprintf (stderr, @@ -1589,6 +1604,106 @@ error: } static void +delete_device_cb (NMDevice *device, GError *error, gpointer user_data) +{ + NmCli *nmc = (NmCli *) user_data; + + if (error) { + g_string_printf (nmc->return_text, _("Error: Device '%s' (%s) deletion failed: %s"), + nm_device_get_iface (device), + nm_object_get_path (NM_OBJECT (device)), + error->message ? error->message : _("(unknown)")); + nmc->return_value = NMC_RESULT_ERROR_UNKNOWN; + } + quit (); +} + +static NMCResultCode +do_device_delete (NmCli *nmc, int argc, char **argv) +{ + NMDevice **devices; + NMDevice *device = NULL; + const char *ifname = NULL; + char *ifname_ask = NULL; + int i; + + /* Set default timeout for delete operation. */ + if (nmc->timeout == -1) + nmc->timeout = 10; + + if (argc == 0) { + if (nmc->ask) + ifname = ifname_ask = nmc_readline (PROMPT_INTERFACE); + + if (!ifname_ask) { + g_string_printf (nmc->return_text, _("Error: No interface specified.")); + nmc->return_value = NMC_RESULT_ERROR_USER_INPUT; + goto error; + } + } else + ifname = *argv; + + if (!ifname) { + g_string_printf (nmc->return_text, _("Error: No interface specified.")); + nmc->return_value = NMC_RESULT_ERROR_USER_INPUT; + goto error; + } + + if (next_arg (&argc, &argv) == 0) { + g_string_printf (nmc->return_text, _("Error: extra argument not allowed: '%s'."), *argv); + nmc->return_value = NMC_RESULT_ERROR_USER_INPUT; + goto error; + } + + nmc->get_client (nmc); + if (!nm_client_get_manager_running (nmc->client)) { + g_string_printf (nmc->return_text, _("Error: NetworkManager is not running.")); + nmc->return_value = NMC_RESULT_ERROR_NM_NOT_RUNNING; + goto error; + } + + if (!nmc_versions_match (nmc)) + goto error; + + devices = get_devices_sorted (nmc->client); + for (i = 0; devices[i]; i++) { + NMDevice *candidate = devices[i]; + const char *dev_iface = nm_device_get_iface (candidate); + + if (!g_strcmp0 (dev_iface, ifname)) + device = candidate; + } + g_free (devices); + + if (!device) { + g_string_printf (nmc->return_text, _("Error: Device '%s' not found."), ifname); + nmc->return_value = NMC_RESULT_ERROR_NOT_FOUND; + goto error; + } + + if (!nm_device_is_software (device)) { + g_string_printf (nmc->return_text, _("Error: Device '%s' is a hardware device. It can't be deleted."), ifname); + nmc->return_value = NMC_RESULT_ERROR_USER_INPUT; + goto error; + } + + /* + * Use nowait_flag instead of should_wait, because exiting has to be postponed + * till delete_device_cb() is called, giving NM time to check our permissions. + */ + nmc->nowait_flag = (nmc->timeout == 0); + nmc->should_wait = TRUE; + nm_device_delete (device, delete_device_cb, nmc); + + /* Start progress indication */ + if (nmc->print_output == NMC_PRINT_PRETTY) + progress_id = g_timeout_add (120, progress_cb, device); + +error: + return nmc->return_value; +} + +static void show_acces_point_info (NMDevice *device, NmCli *nmc) { NMAccessPoint *active_ap = NULL; @@ -2684,6 +2799,13 @@ do_devices (NmCli *nmc, int argc, char **argv) } nmc->return_value = do_device_disconnect (nmc, argc-1, argv+1); } + else if (matches (*argv, "delete") == 0) { + if (nmc_arg_is_help (*(argv+1))) { + usage_device_delete (); + goto usage_exit; + } + nmc->return_value = do_device_delete (nmc, argc-1, argv+1); + } else if (matches (*argv, "wifi") == 0) { if (nmc_arg_is_help (*(argv+1))) { usage_device_wifi (); diff --git a/man/nmcli.1.in b/man/nmcli.1.in index 08f07b4ab7..308dbeccc2 100644 --- a/man/nmcli.1.in +++ b/man/nmcli.1.in @@ -21,7 +21,7 @@ .\" .\" Copyright (C) 2010 - 2014 Red Hat, Inc. .\" -.TH NMCLI "1" "28 February 2014" +.TH NMCLI "1" "11 July 2014" .SH NAME nmcli \- command\(hyline tool for controlling NetworkManager @@ -683,7 +683,7 @@ of its latest state. .B device - show and manage network interfaces .br .TP -.SS \fICOMMAND\fP := { status | show | connect | disconnect | wifi | wimax } +.SS \fICOMMAND\fP := { status | show | connect | disconnect | delete | wifi | wimax } .sp .RS .TP @@ -713,6 +713,14 @@ connections without user/manual intervention. .br If '--wait' option is not specified, the default timeout will be 10 seconds. .TP +.B delete <ifname> +.br +Delete a device. The command removes the interface from the system. Note that +this only works for software devices like bonds, bridges, teams, etc. +Hardware devices (like Ethernet) cannot be deleted by the command. +.br +If '--wait' option is not specified, the default timeout will be 10 seconds. +.TP .B wifi [list [ifname <ifname>] [bssid <BSSID>]] .br List available Wi\(hyFi access points. The \fIifname\fP and \fIbssid\fP options |