第879回の

/dev/ttySx
がたくさん作られるため、udevで名前を付けたり、ser2netで管理することが有用になる
SSL/TLSで経路を暗号化する
改めて紹介すると、ser2netはYAML形式でシリアルコンソール設定を管理できる多機能なシリアルコンソールサーバーです。マシン上やリモートにある複数のシリアルコンソールポートを、telnetベースのプロトコルで公開できます。これによりシリアルコンソールケーブルをつなぎ替えることなく、複数のユーザーがそのポートを共有できます。
第879回では基本的な使い方として、任意のシリアルポートをser2netで公開する方法と複数ユーザーの共有・
root
)
まずはSSL//etc/
」accepter
だけを変更します。最低限の設定は
accepter: telnet,ssl,2000
同時にサーバー証明書一式を生成します。これはopensslなどを用いて生成した任意の証明書一式を利用できますが、今回は自己署名証明書を使いましょう。実はser2netが使用しているgensioライブラリには、このあたりのツールが一通り揃っています。動作確認にもgensioのツールを使うと便利ですので、まずはそれをインストールしましょう。
$ sudo apt install gensio-bin $ sudo gtlssh-keygen --keydir /etc/ser2net --commonname "$(hostname)-ser2net" serverkey ser2net Key created at /etc/ser2net/ser2net.key. Server certificate /etc/ser2net/ser2net.crt created. $ ls -la /etc/ser2net/ total 16 drwxr-xr-x 2 root root 4096 Sep 20 14:15 . drwxr-xr-x 109 root root 4096 Sep 20 14:15 .. -rw-r--r-- 1 root root 595 Sep 20 14:15 ser2net.crt -rw------- 1 root root 119 Sep 20 14:15 ser2net.key $ file /etc/ser2net/ser2net.crt /etc/ser2net/ser2net.crt: PEM certificate $ sudo systemctl restart ser2net.service
証明書一式は/etc/
」gensiot
コマンドを使ってみましょう。
$ gensiot telnet,ssl,localhost,2000 open error on telnet,ssl,localhost,2000: Certificate is not valid
指定するオプションてはプロトコル,ssl,接続先アドレス,接続先ポート番号
」
$ gensiot 'telnet,ssl(CA=/etc/ser2net/ser2net.crt),localhost,2000' ser2net port telnet,ssl,2000 device serialdev, /dev/ttyUSB0, 115200n81,local [115200N81,CLOCAL,HANGUP_WHEN_DONE] (Ubuntu) (以下略)
無事に接続できたことでしょう。なお、gensiotの切断方法はCtrl-\ q
」q
」
もしどうしてもtelnetコマンドを使いたい場合は、telnet-sslパッケージをインストールしましょう。これはtelnetコマンドにsslオプションを追加するバイナリです。
$ sudo apt install telnet-ssl $ telnet -z ssl,secure,cacert=ser2net.crt localhost 2000 Trying 127.0.0.1... Connected to 127.0.0.1. Escape character is '^]'. ser2net port telnet,ssl,2000 device serialdev, /dev/ttyUSB0, 115200n81,local [115200N81,CLOCAL,HANGUP_WHEN_DONE] (Ubuntu) (以下略)
ポイントは-z ssl,secure,cacert=ser2net.
」/etc/
」
クライアント証明書を使ってユーザー認証する
ser2netのSSL/ser2net.
)
- accepterに
「 ssl(clientauth)
」を指定する - accepterに
「 certauth
」を指定する
前者はTLS/
それに対して後者はgensioが提供する
まず、例のごとく/etc/
を次のように修正します。
accepter: telnet,mux,certauth,ssl,2000
「mux」
次にクライアント側で認証用の鍵ペアを生成しましょう。
クライアント$ gtlssh-keygen --keydir . --commonname shibata keygen shibata Key created at ./shibata.key. Certificate created. Put ./shibata.crt into: .gtlssh/allowed_certs on remote systems you want to log into without a password.
SSHで言うところの公開鍵に該当する
クライアント側の保存方法は次の2種類のいずれかです。
- 「
~/.gtlssh/
」keycerts/ホスト名.{key,crt} として保存する - 「
~/.gtlssh/
」default.{key,crt} として保存する
複数の鍵を運用したい場合は、ホスト名ごとに別のファイル名を作ります。合致するホスト名がない場合は~/.gtlssh/
」default.{key,crt}
として保存することにしましょう。
クライアント$ mkdir -p ~/.gtlssh/ クライアント$ chmod 700 ~/.gtlssh/ クライアント$ mv shibata.key ~/.gtlssh/default.key クライアント$ cp shibata.crt ~/.gtlssh/default.crt クライアント$ openssl pkey -in ~/.gtlssh/default.key -text -noout | head -n 2 Private-Key: (2048 bit, 2 primes) modulus:
さらにクライアント側には前節で作成したサーバーの証明書も保存しておきます。
クライアント$ mkdir -p ~/.gtlssh/server_certs/ クライアント$ cp ser2net.crt ~/.gtlssh/server_certs/ホスト名,ポート番号.crt クライアント$ gtlssh-keygen rehash ~/.gtlssh/server_certs/ クライアント$ ls -l ~/.gtlssh/server_certs/ total 4 lrwxrwxrwx 1 shibata member 11 Oct 19 14:13 12f7e1ca.0 -> ser2net,2000.crt -rw-r--r-- 1 shibata member 595 Oct 19 14:13 ser2net,2000.crt
クライアント側に保存する場合は、そのファイル名をホスト名,ポート番号.crt
」IPアドレス,2000.
」ipv4,IPアドレス,ポート番号.crt
」gtlssh-keygen rehash
」
なお、サーバーの証明書は最初の接続時に見つからなかったら、フィンガープリントを表示して保存してくれます。SSHにおける~/.ssh/
のような形になると考えれば良いでしょう。よって証明書のコピー自体は実施しなくてもいいのですが、明確にこのサーバー証明書を使うと意識するためにもコピーする癖を付けましょう。
サーバー側には公開鍵をコピーして保存します。こちらはまず、ユーザー名
サーバー$ sudo mkdir -p /usr/share/ser2net/auth/shibata/allowed_certs/ サーバー$ sudo mv shibata.crt /usr/share/ser2net/auth/shibata/allowed_certs/ サーバー$ sudo gtlssh-keygen rehash /usr/share/ser2net/auth/shibata/allowed_certs/ サーバー$ ls -l /usr/share/ser2net/auth/shibata/allowed_certs/ total 4 lrwxrwxrwx 1 root root 11 Oct 19 04:49 964d1b2a.0 -> shibata.crt -rw-r--r-- 1 shibata shibata 1200 Oct 19 04:48 shibata.crt
ファイル名もユーザー名.crt
」gtlssh-keygen rehash
」
これで準備が完了しました。クライアント側から次のようにアクセスしてみましょう。
クライアント$ gtlssh -p 2000 ホスト名 gensio err log: Error verifying certificate: self-signed certificate Certificate for ホスト名 ホスト名,2000 is not present, fingerprint is: 8D:61:41:B0:B1:8C:BB:B5:43:E5:C2:A8:53:35:7D:9D:DD:BF:DD:8E Please validate the fingerprint and verify if you want it added to the set of valid servers. Add this certificate? (y/n): y ser2net port telnet,mux,certauth,ssl,2000 device serialdev, /dev/ttyUSB0, 115200n81,local [115200N81,CLOCAL,HANGUP_WHEN_DONE] (Ubuntu) (以下略)
上記の例ではサーバー証明書をクライアント側にコピーしなかった場合の結果を表示しています。もしクライアント側に存在しない場合は、フィンガープリントと
いずれにせよ無事にコンソールが表示されたら成功です。切断はgensiotと同じくCtrl-\ q
」q
」
特定のコンソールを特定のユーザーだけ利用できるようにする
ser2netでユーザー用のポートと、管理用ポートを公開していたとします。その時、管理用ポートは特定のユーザーにのみアクセスを許可したいこともあるでしょう。これはallowed-users
」
options:
banner: *banner
kickolduser: false
max-connections: 3
allowed-users: shibata
「allowed-users
」allowed-users
」
mDNSでシリアルポート情報を公開する
ser2netはmDNSもサポートしています。ただし
実際に使ってみましょう。まずmDNS機能を使うためには、サーバー側にlibavahi-daemonをインストールしておく必要があります。
$ sudo apt install libavahi-daemon
次にオプションでmdns機能を有効化しましょう。
options:
mdns: true
あとは適当なマシンからavahi-utilsパッケージに含まれる、avahi-browseコマンドを実行します。
$ avahi-browse -rt _iostream._tcp + ens160 IPv6 con1 _iostream._tcp local + ens160 IPv4 con1 _iostream._tcp local = ens160 IPv6 con1 _iostream._tcp local hostname = [ホスト名.local] address = [IPv6アドレス] port = [2000] txt = ["gensiostack=telnet,mux,certauth,ssl,tcp" "provider=ser2net"] = ens160 IPv4 con1 _iostream._tcp local hostname = [ホスト名.local] address = [IPv4アドレス] port = [2000] txt = ["gensiostack=telnet,mux,certauth,ssl,tcp" "provider=ser2net"]
con1はホスト名.local
」
ser2netに登録したシリアルポートが増えるほど、ここのリストも増えます。mDNSの情報をもとに
mDNSに表示する項目は多少調整が可能です。詳細はser2net.mdns-type: _名前._tcp
」_iostream._tcp
」._tcp
」