]> git.ipfire.org Git - people/stevee/network.git/blobdiff - functions.cli
Bump version to 006.
[people/stevee/network.git] / functions.cli
index 7986413ea08618c14ed2515e3c70641f3344630a..2d35e6420354108c82f203f31033940360cf3337 100644 (file)
 #                                                                             #
 ###############################################################################
 
-function cli_config() {
-       if cli_help_requested $@; then
-               cli_usage root-config
-               exit ${EXIT_OK}
-       fi
+IDENT="  "
 
-       if [ -n "${1}" ]; then
-               network_config_set $@
-       else
-               network_config_print
+function cli_help_requested() {
+       local argument="${1}"
+
+       if [ -n "${argument}" ]; then
+               if listmatch ${argument} help -h --help; then
+                       return ${EXIT_OK}
+               fi
        fi
+
+       return ${EXIT_ERROR}
 }
 
-function cli_device() {
-       if device_config_exists ${1}; then
-               local device=${1}
-               local action=${2}
-               shift 2
+function cli_run_help() {
+       local command="$@"
 
-               case "${action}" in
-                       down|up)
-                               device_${action} ${device} $@
+       print "Run \"${command} help\" to get more information."
+       return ${EXIT_OK}
+}
+
+function cli_device_headline() {
+       local device=${1}
+       assert isset device
+
+       local long=0
+       shift
+       while [ $# -gt 0 ]; do
+               case "${1}" in
+                       --long)
+                               long=1
                                ;;
                esac
-       else
-               local action=${1}
                shift
+       done
 
-               case "${action}" in
-                       create)
-                               device_${action} $@
-                               ;;
+       local type
+       if zone_exists ${device}; then
+               type="zone"
+       elif port_exists ${device}; then
+               type="port"
+       else
+               type="unknown"
+       fi
 
-                       discover)
-                               echo "# XXX need to implement --raw here"
-                               local device
-                               for device in ${devices}; do
-                                       cli_device_discover ${device} $@
-                               done
-                               ;;
+       local headline_prefix
+       case "${type}" in
+               zone)
+                       headline_prefix="Zone ${device}"
+                       ;;
+               port)
+                       headline_prefix="Port ${device} ($(device_get_type ${device}))"
+                       ;;
+               *)
+                       headline_prefix="Device ${device} ($(device_get_type ${device}))"
+                       ;;
+       esac
 
-                       show|"")
-                               local device
-                               for device in $(device_get $@); do
-                                       device_print ${device}
-                               done
-                               ;;
-                       *)
-                               cli_usage device
-                               ;;                              
-               esac
+       # Print the hook for all zones.
+       if [ "${type}" = "zone" ]; then
+               headline_prefix="${headline_prefix} ($(zone_get_hook ${device}))"
        fi
-}
+       cli_headline 1 "${headline_prefix}"
 
-function cli_device_discover() {
-       local device=${1}
-       shift
+       # Print the device status.
+       local status
+       case "$(device_get_status ${device})" in
+               ${STATUS_UP})
+                       status=${MSG_DEVICE_STATUS_UP}
+                       ;;
+               ${STATUS_DOWN})
+                       status=${MSG_DEVICE_STATUS_DOWN}
+                       ;;
+               ${STATUS_NOCARRIER})
+                       status=${MSG_DEVICE_STATUS_NOCARRIER}
+                       ;;
+               *)
+                       status=${MSG_DEVICE_STATUS_UNKNOWN}
+                       ;;
+       esac
+       cli_print_fmt1 1 "Status" "${status}"
+       if enabled long; then
+               cli_print_fmt1 1 "Address" "$(device_get_address ${device})"
+       fi
+       if device_is_up ${device}; then
+               cli_print_fmt1 1 "MTU" "$(device_get_mtu ${device})"
+       fi
+       if enabled long; then
+               device_is_promisc ${device} &>/dev/null
+               cli_print_fmt1 1 "Promisc" "$(cli_print_bool $?)"
+       fi
+
+       cli_space
+
+       # Print the device stats.
+       device_is_up ${device} && cli_device_stats 2 ${device}
+
+       if enabled long; then
+               # Virtual devices.
+               device_is_vlan ${device} && cli_device_vlan ${device}
 
-       local device_type=$(device_get_type ${device})
-       if [ "${device_type}" != "real" ]; then
-               return ${EXIT_OK}
+               # Bonded devices.
+               device_is_bonded ${device} && cli_device_bonded ${device}
+
+               # Bonding devices.
+               device_is_bonding ${device} && cli_device_bonding ${device}
        fi
+}
 
-       local raw
+function cli_device_stats() {
+       local level=${1}
+       local device=${2}
 
-       while [ $# -gt 0 ]; do
-               case "${1}" in
-                       --raw)
-                               raw=1
-                               ;;
-               esac
-               shift
-       done
+       # This section will print statistical data from the device.
+       local packets bytes errors
 
-       local up
-       device_is_up ${device} && up=1
-       device_set_up ${device}
+       cli_headline ${level} "Statistics"
+       local format="%-10s %9d packets %6s (%d errors)"
 
-       enabled raw || echo "${device}"
+       # RX
+       packets=$(device_get_rx_packets ${device})
+       bytes=$(device_get_rx_bytes ${device})
+       errors=$(device_get_rx_errors ${device})
 
-       local hook
-       local out
-       local ret
-       for hook in $(hook_zone_get_all); do
-               out=$(hook_zone_exec ${hook} discover ${device})
-               ret=$?
-
-               [ ${ret} -eq ${DISCOVER_NOT_SUPPORTED} ] && continue
-
-               if enabled raw; then
-                       case "${ret}" in
-                               ${DISCOVER_OK})
-                                       echo "${hook}: OK"
-                                       local line
-                                       while read line; do
-                                               echo "${hook}: ${line}"
-                                       done <<<"${out}"
-                                       ;;
-
-                               ${DISCOVER_ERROR})
-                                       echo "${hook}: FAILED"
-                                       ;;
-                       esac
-               else
-                       case "${ret}" in
-                               ${DISCOVER_OK})
-                                       echo "  ${hook} was successful."
-                                       local line
-                                       while read line; do
-                                               echo "  ${line}"
-                                       done <<<"${out}"
-                                       ;;
-
-                               ${DISCOVER_ERROR})
-                                       echo "  ${hook} failed."
-                                       ;;
-                       esac
-               fi
-       done
+       cli_print ${level} "${format}" "Received" "${packets}" "$(beautify_bytes ${bytes})" "${errors}"
 
-       echo # New line
+       # TX
+       packets=$(device_get_tx_packets ${device})
+       bytes=$(device_get_tx_bytes ${device})
+       errors=$(device_get_tx_errors ${device})
 
-       [ "${up}" = "1" ] || device_set_down ${device}
+       cli_print ${level} "${format}" "Sent"     "${packets}" "$(beautify_bytes ${bytes})" "${errors}"
+       cli_space
 }
 
-function cli_port() {
-       if cli_help_requested $@; then
-               cli_usage root-port
-               exit ${EXIT_OK}
-       fi
+function cli_device_vlan() {
+       local device=${1}
 
-       local action
-       local port
+       cli_headline 2 "VLAN"
 
-       if port_exists ${1}; then
-               port=${1}
-               action=${2}
-               shift 2
+       cli_print_fmt1 2 "Parent" "$(vlan_get_parent ${device})"
+       cli_print_fmt1 2 "VID" "$(vlan_get_id ${device})"
+       cli_space
+}
 
-               # Action aliases
-               case "${action}" in
-                       start)
-                               action="up"
-                               ;;
-                       stop)
-                               action="down"
-                               ;;
-                       show)
-                               action="status"
-                               ;;
-               esac
+function cli_device_bonded() {
+       local device=${1}
 
-               case "${action}" in
-                       edit|up|down|status)
-                               port_${action} ${port} $@
-                               ;;
-                       *)
-                               error "Unrecognized argument: ${action}"
-                               exit ${EXIT_ERROR}
-                               ;;
-               esac
-       else
-               action=${1}
-               shift
+       cli_headline 2 "Bonding information"
 
-               case "${action}" in
-                       create|destroy)
-                               port_${action} $@
-                               ;;
-                       *)
-                               error "Unrecognized argument: ${action}"
-                               exit ${EXIT_ERROR}
-                               ;;
-               esac
+       local master=$(bonding_slave_get_master ${port})
+       cli_print_fmt1 2 "Master" "${master}"
+
+       local mode=$(bonding_get_mode ${master})
+       if [ "${mode}" = "active-backup" ]; then
+               local active_slaves=$(bonding_get_slaves ${master} --active)
+               local active="false"
+               if list_match "${device}" ${active_slaves}; then
+                       active="true"
+               fi
+               cli_print_fmt1 2 "Active slave" "$(cli_print_yesno ${active})"
        fi
+
+       cli_space
 }
 
-function cli_zone() {
-       if cli_help_requested $@; then
-               cli_usage root-zone
-               exit ${EXIT_OK}
-       fi
+function cli_device_bonding() {
+       local device=${1}
+       assert isset device
 
-       local action
-       local zone
+       cli_headline 2 "Bonding information"
 
-       if zone_name_is_valid ${1}; then
-               zone=${1}
-               action=${2}
-               shift 2
+       local mode=$(bonding_get_mode ${device})
 
-               # Action aliases
-               case "${action}" in
-                       start)
-                               action="up"
-                               ;;
-                       stop)
-                               action="down"
+       cli_print_fmt1 2 "Mode" "${mode}"
+       if [ "${mode}" = "802.3ad" ]; then
+               local lacp_rate=$(bonding_get_lacp_rate ${device})
+               cli_print_fmt1 2 "LACP rate" "${lacp_rate}"
+       fi
+       cli_space
+
+       local slave slave_suffix
+       local active_slaves=$(bonding_get_slaves ${device} --active)
+       for slave in $(bonding_get_slaves ${device}); do
+               # Print the device status.
+               local status
+               case "$(device_get_status ${slave})" in
+                       ${STATUS_UP})
+                               status=${MSG_DEVICE_STATUS_UP}
                                ;;
-                       show)
-                               action="status"
+                       ${STATUS_DOWN})
+                               status=${MSG_DEVICE_STATUS_DOWN}
                                ;;
-               esac
-
-               case "${action}" in
-                       config|down|edit|port|status|up)
-                               zone_${action} ${zone} $@
+                       ${STATUS_NOCARRIER})
+                               status=${MSG_DEVICE_STATUS_NOCARRIER}
                                ;;
                        *)
-                               error "Unrecognized argument: ${action}"
-                               cli_usage root-zone-subcommands
-                               exit ${EXIT_ERROR}
+                               status=${MSG_DEVICE_STATUS_UNKNOWN}
                                ;;
                esac
-       else
-               action=${1}
-               shift
 
-               case "${action}" in
-                       create|remove)
-                               zone_${action} $@
-                               ;;
-                       ""|*)
-                               if [ -n "${action}" ]; then
-                                       error "Unrecognized argument: '${action}'"
-                                       echo
-                               fi
-
-                               cli_usage root-zone
-                               exit ${EXIT_ERROR}
-                               ;;
-               esac
-       fi
+               if list_match "${slave}" ${active_slaves}; then
+                       slave_suffix="(active)"
+               else
+                       slave_suffix=""
+               fi
+               cli_print_fmt1 2 "Slave ${slave}" "${status} ${slave_suffix}"
+       done
+       cli_space
 }
 
-function cli_start() {
-       if cli_help_requested $@; then
-               cli_usage root-start
-               exit ${EXIT_OK}
-       fi
+function cli_headline() {
+       local level=${1}
+       local format=${2}
+       shift 2
 
-       local zones=$(zones_get $@)
+       local ident=$(cli_ident ${level})
 
-       local zone
-       for zone in ${zones}; do
-               zone_up ${zone}
-       done
+       local out
+       printf -v out "${ident}${CLR_BLACK_B}${format}${CLR_RESET}\n" "$@"
+       printf "${out}"
 }
 
-function cli_stop() {
-       if cli_help_requested $@; then
-               cli_usage root-stop
-               exit ${EXIT_OK}
-       fi
+function cli_statusline() {
+       local level=${1}
+       shift
 
-       local zones=$(zones_get $@)
+       local head=${1}
+       shift
 
-       local zone
-       for zone in ${zones}; do
-               zone_down ${zone}
-       done
+       cli_print $(( ${level} - 1 )) "%-12s %s" "${head}" "$@"
 }
 
-function cli_restart() {
-       if cli_help_requested $@; then
-               cli_usage root-restart
-               exit ${EXIT_OK}
-       fi
-
-       cli_stop $@
+function cli_print() {
+       local level=${1}
+       local format=${2}
+       shift 2
 
-       # Give the system some time to calm down
-       sleep ${TIMEOUT_RESTART}
+       local ident=$(cli_ident $(( ${level} + 1 )))
 
-       cli_start $@
+       local out
+       printf -v out "${ident}${format}\n" "$@"
+       printf "${out}"
 }
 
-function cli_status() {
-       if cli_help_requested $@; then
-               cli_usage root-status
-               exit ${EXIT_OK}
-       fi
+function cli_print_fmt1() {
+       local level=${1}
+       shift
 
-       local zones=$(zones_get $@)
+       local space=$(( 34 - (${level} * ${#IDENT}) ))
+       local format="%-${space}s %s"
 
-       local zone
-       for zone in ${zones}; do
-               zone_status ${zone}
-       done
+       cli_print ${level} "${format}" "$@"
 }
 
-function cli_reset() {
-       if cli_help_requested $@; then
-               cli_usage root-reset
-               exit ${EXIT_OK}
+function cli_print_bool() {
+       if [ "${1}" = "${EXIT_TRUE}" ]; then
+               echo "true"
+       else
+               echo "false"
        fi
+}
 
-       warning_log "Will reset the whole network configuration!!!"
-
-       # Force mode is disabled by default
-       local force=0
-
-       while [ $# -gt 0 ]; do
-               case "${1}" in
-                       --force|-f)
-                               force=1
-                               ;;
-               esac
-               shift
-       done 
-
-       # If we are not running in force mode, we ask the user if he does know
-       # what he is doing.
-       if ! enabled force; then
-               if ! cli_yesno "Do you really want to reset the whole network configuration?"; then
-                       exit ${EXIT_ERROR}
-               fi
+function cli_print_yesno() {
+       if [ "${1}" = "${EXIT_TRUE}" ]; then
+               echo "yes"
+       else
+               echo "false"
        fi
+}
 
-       local zone
-       for zone in $(zones_get --all); do
-               zone_remove ${zone}
-       done
+function cli_print_enabled() {
+       enabled ${1}
 
-       local port
-       for port in $(ports_get --all); do
-               port_remove ${port}
-       done
+       cli_print_bool $?
+}
 
-       # Re-run the initialization functions
-       init_run
+function cli_print_warning() {
+       local level=${1}
+       shift
 
-       exit ${EXIT_OK}
+       cli_print ${level} "${CLR_YELLOW_B}%s${CLR_RESET}" "$@"
 }
 
-function cli_help_requested() {
-       local argument="${1}"
+function cli_space() {
+       printf "\n"
+}
 
-       if [ -n "${argument}" ]; then
-               if listmatch ${argument} help -h --help; then
-                       return ${EXIT_OK}
-               fi
-       fi
+function cli_ident() {
+       local level=${1}
+       assert isinteger level
 
-       return ${EXIT_ERROR}
+       local ident=""
+       while [ ${level} -gt 1 ]; do
+               ident="${ident}${IDENT}"
+               level=$(( ${level} - 1 ))
+       done
+
+       print "${ident}"
 }
 
-function cli_usage() {
-       local what=${1}
-
-       case "${what}" in
-               root)
-                       echo "${0}: [command] <options ...>"
-                       echo
-                       echo "  start  - ..."
-                       echo "  stop   - ..."
-                       echo "  restart - ..."
-                       echo "  status - ..."
-                       echo
-                       echo "  config - ..."
-                       echo
-                       echo "  device - ..."
-                       echo "  zone   - ..."
-                       echo
-                       ;;
-               root-config)
-                       echo    "${0}: ${what#root-} [KEY=VAL, ...]"
-                       echo
-                       echo    "  This command allows setting of global configuration parameters."
-                       echo
-                       echo    "  If no additional arguments are passed it will list the current configuration."
-                       echo
-                       echo    "  You can overwrite the settings like the following:"
-                       echo
-                       echo    "    ${0} ${what#root-} DEBUG=1 ..."
-                       echo
-                       ;;
-               root-reset)
-                       echo    "${0}: ${what#root-} [--force | -f]"
-                       echo
-                       echo    "  This command resets the network configuration."
-                       echo
-                       echo    "  Will delete all zones and ports."
-                       echo
-                       echo -e "  ${COLOUR_RED}USE WITH CAUTION!${COLOUR_NORMAL}"
-                       echo
-                       ;;
-               root-start|root-stop|root-restart)
-                       echo    "${0}: ${what#root-} [--local-only|--remote-only|--all|<zone>...]"
-                       echo
-                       echo    "  This commands ${what#root-}s all zones by default."
-                       echo    "  One can pass several parameters to only process a subset of all"
-                       echo    "  available zones:"
-                       echo
-                       echo -e "    ${COLOUR_BOLD}--local-only${COLOUR_NORMAL}"
-                       echo    "    Process all local zones which includes every zone without red."
-                       echo
-                       echo -e "    ${COLOUR_BOLD}--remote-only${COLOUR_NORMAL}"
-                       echo    "    Process all remote zones which means only the red ones."
-                       echo
-                       echo -e "    ${COLOUR_BOLD}--all${COLOUR_NORMAL}"
-                       echo    "    Process all zones. This is the default parameter."
-                       echo
-                       echo    "    Additionally, you can pass one or more zone names which will"
-                       echo    "    be processed."
-                       echo
-                       ;;
-               root-status)
-                       echo    "${0}: ${what#root-} [--local-only|--remote-only|--all|<zone>...]"
-                       echo
-                       echo    "  This commands shows status information of all zones by default."
-                       echo    "  One can pass several parameters to only process a subset of all"
-                       echo    "  available zones:"
-                       echo
-                       echo -e "    ${COLOUR_BOLD}--local-only${COLOUR_NORMAL}"
-                       echo    "    Process all local zones which includes every zone without red."
-                       echo
-                       echo -e "    ${COLOUR_BOLD}--remote-only${COLOUR_NORMAL}"
-                       echo    "    Process all remote zones which means only the red ones."
-                       echo
-                       echo -e "    ${COLOUR_BOLD}--all${COLOUR_NORMAL}"
-                       echo    "    Process all zones. This is the default parameter."
-                       echo
-                       echo    "    Additionally, you can pass one or more zone names which will"
-                       echo    "    be processed."
-                       echo
-                       ;;
-               root-zone)
-                       echo    "${0}: ${what#root-} <create|remove> <zone> [<type> <options...>]"
-                       echo
-                       echo    "  Create or remove a zone."
-                       echo
-                       echo -e "    ${COLOUR_BOLD}create <zone> <type> <options>${COLOUR_NORMAL}"
-                       echo    "    Create a new zone of type <type> where <zone> is an allowed"
-                       echo    "    zone name."
-                       echo
-                       echo -e "    ${COLOUR_BOLD}remove <zone>${COLOUR_NORMAL}"
-                       echo    "    Remove the zone <zone>."
-                       echo
-                       echo    "  You may also edit the configuration of the zones."
-                       echo
-                       echo -e "    ${COLOUR_BOLD}<zone> ...${COLOUR_NORMAL}"
-                       echo    "    Edit the zone <zone>."
-                       echo
-                       ;;
-               usage)
-                       echo
-                       echo "  Run '${0} help' to get information how to use this tool."
-                       echo
-                       ;;
-               *)
-                       error "No help available for this command '${what}'."
-                       echo
-                       ;;
-       esac
+function cli_yesno() {
+       local message="$@ [y/n] "
+       local yesno
 
-       echo "Network configuration tool. Report all bugs to <http://bugs.ipfire.org>."
-}
+       while true; do
+               printf "\n${message}"
+               read yesno
 
-function cli_status_headline() {
-       local zone=${1}
+               # Check for "yes".
+               if listmatch ${yesno} y Y yes YES Yes; then
+                       return ${EXIT_TRUE}
 
-       local state="${COLOUR_DOWN}DOWN${COLOUR_NORMAL}"
-       zone_is_up ${zone} && state="${COLOUR_UP}UP${COLOUR_NORMAL}"
+               # Check for "no".
+               elif listmatch ${yesno} n N no NO No; then
+                       return ${EXIT_FALSE}
+               fi
+       done
+}
 
-       echo -e "${zone} - ${state} - $(zone_get_hook ${zone})"
+function cli_get_key() {
+       local key="${1%%=*}"
+       echo "${key/--/}"
 }
 
-function cli_headline() {
-       echo
-       echo -e "${COLOUR_BOLD}$@${COLOUR_NORMAL}"
+function cli_get_val() {
+       echo "${@#*=}"
 }
 
-function cli_yesno() {
-       local message="$@ [y/N] "
-       local yesno
+function cli_usage() {
+       local command="$@"
+       local basename="$(basename ${0})"
 
-       echo
-       echo -ne "${message}"
-       read yesno
+       if ! isset command; then
+               command="${basename} help"
+       fi
+
+       echo "The given command was not understood by ${basename}." >&2
+       echo "Please run '${command}' for detailed help." >&2
+}
 
-       if listmatch ${yesno} y Y j J yes YES Yes; then
-               return ${EXIT_OK}
+function cli_show_man() {
+       local manpage=${1}
+       assert isset manpage
+
+       if ! binary_exists man; then
+               error "The man package is not installed on this system."
+               error "Please install 'man' in order to view the help."
+               exit ${EXIT_ERROR}
        fi
 
-       return ${EXIT_ERROR}
+       man ${manpage}
 }