diff options
author | Christian Poessinger <christian@poessinger.com> | 2020-06-19 17:07:42 +0200 |
---|---|---|
committer | Christian Poessinger <christian@poessinger.com> | 2020-06-19 17:07:42 +0200 |
commit | e3fdb3c4f2b2b94e241ecd82dcb032020bbc1718 (patch) | |
tree | 43a869c1dc2f406d02bca7d55bacc1418dae3048 | |
parent | a686e090b2bd19ce27d3d09318d63208448e0707 (diff) | |
parent | 9130507c08a88a46325efe7e95ed74126ec6cec8 (diff) | |
download | vyos-1x-e3fdb3c4f2b2b94e241ecd82dcb032020bbc1718.tar.gz vyos-1x-e3fdb3c4f2b2b94e241ecd82dcb032020bbc1718.zip |
Merge branch 'console-server' of github.com:c-po/vyos-1x into current
* 'console-server' of github.com:c-po/vyos-1x:
console-server: T2490: set service priority to 990
op-mode: console-server: T2490: rename "connect console-server" to "connect console"
console-server: T2490: server must listen only on localhost
op-mode: add "show ip ports" to list local opened ports
console-server: T2490: add SSH support for direct device access
op-mode: console-server: T2490: get connection info
console-server: T2490: remove superfluous "port" node from XML definition
console-server: T2490: rename CLI to console-server
console-server: T2490: add SSH support
console-server: T2490: log to journald
console-server: T2490: move CLI parsing to get_config_dict()
console-server: T2490: replace ser2net with conserver
op-mode: T2490: add "connect serial-proxy" CLI command
console-server: T2490: add default CLI values
console-server: T2490: rename CLI to "serial-proxy"
console-server: T2490: use new USB ports "by-bus"
console-server: T2490: use "ls" for completion helper
console-server: T2490: initial support
-rw-r--r-- | data/templates/conserver/conserver.conf.tmpl | 37 | ||||
-rw-r--r-- | debian/control | 3 | ||||
-rw-r--r-- | interface-definitions/service_console-server.xml.in | 90 | ||||
-rw-r--r-- | op-mode-definitions/show-console-server.xml | 49 | ||||
-rw-r--r-- | op-mode-definitions/show-ip-ports.xml | 17 | ||||
-rwxr-xr-x | src/conf_mode/service_console-server.py | 109 | ||||
-rw-r--r-- | src/etc/systemd/system/conserver-server.service.d/override.conf | 10 | ||||
-rw-r--r-- | src/systemd/dropbear@.service | 14 | ||||
-rw-r--r-- | src/systemd/dropbearkey.service | 11 |
9 files changed, 340 insertions, 0 deletions
diff --git a/data/templates/conserver/conserver.conf.tmpl b/data/templates/conserver/conserver.conf.tmpl new file mode 100644 index 000000000..4e7b5d8d7 --- /dev/null +++ b/data/templates/conserver/conserver.conf.tmpl @@ -0,0 +1,37 @@ +### Autogenerated by service_console-server.py ### + +# See https://www.conserver.com/docs/conserver.cf.man.html for additional options + +config * { + primaryport 3109; + daemonmode false; +} + +default * { + motd "VyOS Console Server"; + rw *; +} + +## +## list of consoles we serve +## +{% for key, value in device.items() %} +{# Depending on our USB serial console we could require a path adjustment #} +{% set path = '/dev' if key.startswith('ttyS') else '/dev/serial/by-bus' %} +console {{ key }} { + master localhost; + type device; + device {{ path }}/{{ key }}; + baud {{ value.speed }}; + parity {{ value.parity }}; + options {{ "!" if value.stop_bits == "1" }}cstopb; +} +{% endfor %} + +## +## list of clients we allow +## +access * { + trusted localhost; + allowed localhost; +} diff --git a/debian/control b/debian/control index 104a267ea..bf330c35c 100644 --- a/debian/control +++ b/debian/control @@ -59,6 +59,9 @@ Depends: python3, iputils-arping, libvyosconfig0, beep, + dropbear, + conserver-server, + conserver-client, isc-dhcp-server, isc-dhcp-relay, keepalived (>=2.0.5), diff --git a/interface-definitions/service_console-server.xml.in b/interface-definitions/service_console-server.xml.in new file mode 100644 index 000000000..348d591dd --- /dev/null +++ b/interface-definitions/service_console-server.xml.in @@ -0,0 +1,90 @@ +<?xml version="1.0"?> +<interfaceDefinition> + <node name="service"> + <children> + <node name="console-server" owner="${vyos_conf_scripts_dir}/service_console-server.py"> + <properties> + <help>Serial Console Server</help> + <priority>990</priority> + </properties> + <children> + <tagNode name="device"> + <properties> + <help>System serial interface name (ttyS or ttyUSB)</help> + <completionHelp> + <script>ls -1 /dev | grep ttyS</script> + <script>ls -1 /dev/serial/by-bus</script> + </completionHelp> + <valueHelp> + <format>ttySxxx</format> + <description>Regular serial interface</description> + </valueHelp> + <valueHelp> + <format>usbxbxpx</format> + <description>USB based serial interface</description> + </valueHelp> + <constraint> + <regex>^(ttyS\d+|usb\d+b.*p.*)$</regex> + </constraint> + </properties> + <children> + #include <include/interface-description.xml.i> + <leafNode name="speed"> + <properties> + <help>Serial port baud rate</help> + <completionHelp> + <list>300 1200 2400 4800 9600 19200 38400 57600 115200</list> + </completionHelp> + <constraint> + <regex>(300|1200|2400|4800|9600|19200|38400|57600|115200)</regex> + </constraint> + </properties> + </leafNode> + <leafNode name="data-bits"> + <properties> + <help>Serial port data bits (default: 8)</help> + <completionHelp> + <list>7 8</list> + </completionHelp> + <constraint> + <regex>(7|8)</regex> + </constraint> + </properties> + </leafNode> + <leafNode name="stop-bits"> + <properties> + <help>Serial port stop bits (default: 1)</help> + <completionHelp> + <list>1 2</list> + </completionHelp> + <constraint> + <regex>(1|2)</regex> + </constraint> + </properties> + </leafNode> + <leafNode name="parity"> + <properties> + <help>Parity setting (default: none)</help> + <completionHelp> + <list>even odd none</list> + </completionHelp> + <constraint> + <regex>(even|odd|none)</regex> + </constraint> + </properties> + </leafNode> + <node name="ssh"> + <properties> + <help>SSH remote access to this console</help> + </properties> + <children> + #include <include/port-number.xml.i> + </children> + </node> + </children> + </tagNode> + </children> + </node> + </children> + </node> +</interfaceDefinition> diff --git a/op-mode-definitions/show-console-server.xml b/op-mode-definitions/show-console-server.xml new file mode 100644 index 000000000..e47b6cfaa --- /dev/null +++ b/op-mode-definitions/show-console-server.xml @@ -0,0 +1,49 @@ +<?xml version="1.0"?> +<interfaceDefinition> + <node name="connect"> + <children> + <tagNode name="console"> + <properties> + <help>Connect to device attached to serial console server</help> + <completionHelp> + <path>service console-server device</path> + </completionHelp> + </properties> + <command>/usr/bin/console "$3"</command> + </tagNode> + </children> + </node> + <node name="show"> + <children> + <node name="log"> + <children> + <leafNode name="console-server"> + <properties> + <help>Show log for serial console server</help> + </properties> + <command>/usr/bin/journalctl -u conserver-server.service</command> + </leafNode> + </children> + </node> + <node name="console-server"> + <properties> + <help>Show Console-Server information</help> + </properties> + <children> + <leafNode name="ports"> + <properties> + <help>Examine console ports and configured baud rates</help> + </properties> + <command>/usr/bin/console -x</command> + </leafNode> + <leafNode name="user"> + <properties> + <help>Show users on various consoles</help> + </properties> + <command>/usr/bin/console -u</command> + </leafNode> + </children> + </node> + </children> + </node> +</interfaceDefinition> diff --git a/op-mode-definitions/show-ip-ports.xml b/op-mode-definitions/show-ip-ports.xml new file mode 100644 index 000000000..a74b68ffc --- /dev/null +++ b/op-mode-definitions/show-ip-ports.xml @@ -0,0 +1,17 @@ +<?xml version="1.0"?> +<interfaceDefinition> + <node name="show"> + <children> + <node name="ip"> + <children> + <leafNode name="ports"> + <properties> + <help>Show IP ports in use by various system services</help> + </properties> + <command>sudo /usr/bin/netstat -tulnp</command> + </leafNode> + </children> + </node> + </children> + </node> +</interfaceDefinition> diff --git a/src/conf_mode/service_console-server.py b/src/conf_mode/service_console-server.py new file mode 100755 index 000000000..7f6967983 --- /dev/null +++ b/src/conf_mode/service_console-server.py @@ -0,0 +1,109 @@ +#!/usr/bin/env python3 +# +# Copyright (C) 2018-2020 VyOS maintainers and contributors +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License version 2 or later as +# published by the Free Software Foundation. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see <http://www.gnu.org/licenses/>. + +import os + +from sys import exit + +from vyos.config import Config +from vyos.configdict import dict_merge +from vyos.template import render +from vyos.util import call +from vyos import ConfigError + +config_file = r'/run/conserver/conserver.cf' + +# Default values are necessary until the implementation of T2588 is completed +default_values = { + 'data_bits': '8', + 'parity': 'none', + 'stop_bits': '1' +} + +def get_config(): + conf = Config() + base = ['service', 'console-server'] + + if not conf.exists(base): + return None + + # Retrieve CLI representation as dictionary + proxy = conf.get_config_dict(base, key_mangling=('-', '_')) + # The retrieved dictionary will look something like this: + # + # {'device': {'usb0b2.4p1.0': {'speed': '9600'}, + # 'usb0b2.4p1.1': {'data_bits': '8', + # 'parity': 'none', + # 'speed': '115200', + # 'stop_bits': '2'}}} + + # We have gathered the dict representation of the CLI, but there are default + # options which we need to update into the dictionary retrived. + for device in proxy['device'].keys(): + tmp = dict_merge(default_values, proxy['device'][device]) + proxy['device'][device] = tmp + + return proxy + +def verify(proxy): + if not proxy: + return None + + for device in proxy['device']: + keys = proxy['device'][device].keys() + if 'speed' not in keys: + raise ConfigError(f'Serial port speed must be defined for "{tmp}"!') + + if 'ssh' in keys: + ssh_keys = proxy['device'][device]['ssh'].keys() + if 'port' not in ssh_keys: + raise ConfigError(f'SSH port must be defined for "{tmp}"!') + + return None + +def generate(proxy): + if not proxy: + return None + + render(config_file, 'conserver/conserver.conf.tmpl', proxy) + return None + +def apply(proxy): + call('systemctl stop dropbear@*.service conserver-server.service') + + if not proxy: + if os.path.isfile(config_file): + os.unlink(config_file) + return None + + call('systemctl restart conserver-server.service') + + for device in proxy['device']: + if 'ssh' in proxy['device'][device].keys(): + port = proxy['device'][device]['ssh']['port'] + call(f'systemctl restart dropbear@{device}.service') + + return None + +if __name__ == '__main__': + try: + c = get_config() + verify(c) + generate(c) + apply(c) + except ConfigError as e: + print(e) + exit(1) diff --git a/src/etc/systemd/system/conserver-server.service.d/override.conf b/src/etc/systemd/system/conserver-server.service.d/override.conf new file mode 100644 index 000000000..3c753f572 --- /dev/null +++ b/src/etc/systemd/system/conserver-server.service.d/override.conf @@ -0,0 +1,10 @@ +[Unit] +After= +After=vyos-router.service +ConditionPathExists=/run/conserver/conserver.cf + +[Service] +Type=simple +ExecStart= +ExecStart=/usr/sbin/conserver -M localhost -C /run/conserver/conserver.cf +Restart=on-failure diff --git a/src/systemd/dropbear@.service b/src/systemd/dropbear@.service new file mode 100644 index 000000000..606a7ea6d --- /dev/null +++ b/src/systemd/dropbear@.service @@ -0,0 +1,14 @@ +[Unit] +Description=Dropbear SSH per-connection server +Requires=dropbearkey.service +Wants=conserver-server.service +ConditionPathExists=/run/conserver/conserver.cf +After=dropbearkey.service vyos-router.service conserver-server.service + +[Service] +Type=forking +ExecStartPre=/usr/bin/bash -c '/usr/bin/systemctl set-environment PORT=$(cli-shell-api returnActiveValue service console-server device "%I" ssh port)' +ExecStart=-/usr/sbin/dropbear -w -j -k -r /etc/dropbear/dropbear_rsa_host_key -c "/usr/bin/console %I" -P /run/conserver/dropbear.%I.pid -p ${PORT} +PIDFile=/run/conserver/dropbear.%I.pid +KillMode=process +Restart=on-failure diff --git a/src/systemd/dropbearkey.service b/src/systemd/dropbearkey.service new file mode 100644 index 000000000..770641c8b --- /dev/null +++ b/src/systemd/dropbearkey.service @@ -0,0 +1,11 @@ +[Unit] +Description=Dropbear SSH Key Generation +ConditionPathExists=|!/etc/dropbear/dropbear_rsa_host_key + +[Service] +ExecStart=/usr/bin/dropbearkey -t rsa -f /etc/dropbear/dropbear_rsa_host_key +RemainAfterExit=yes + +[Install] +WantedBy=multi-user.target + |