- SSH セッションがフリーズしたとき、プロセスを強制終了しなくても、SSH に組み込まれたエスケープシーケンスメニューでさまざまな制御が可能
- セッション内で
↵Enter を入力してから ~? を入力すると、隠しコマンド一覧が表示され、~. でどんな状況でも即座に接続を終了可能
- このエスケープシーケンスは SSH クライアント自体に組み込まれているため、サーバーや接続が切れている状態でも動作
- ネストした SSH セッションでは
~~ を使って 内側のクライアントにシーケンスを渡すことが可能
- さらに
-C、-v、-D などの 便利な SSH オプションもあわせて紹介
SSH エスケープシーケンスメニュー
- SSH セッション内で
↵Enter を押した後に ~? を入力すると、サポートされているエスケープシーケンス一覧を確認可能
- 主なシーケンス一覧:
~. — 接続終了(多重化されたセッションを含む)
~B — リモートシステムに BREAK シグナルを送信
~C — コマンドラインを開く(ポートフォワーディング設定可能、help を入力すると案内を確認可能)
~R — rekey 要求
~V/v — verbosity(LogLevel)の増減
~^Z — SSH を一時停止(suspend)
~# — フォワードされた接続一覧を表示
~& — SSH をバックグラウンドに移行(接続終了待ちのとき)
~~ — エスケープ文字そのものを送信(2 回入力)
- これらのシーケンスは SSH クライアント自体に組み込まれているため、SSH サーバーが応答しない場合や接続が切れた状態でも動作
- 最も便利なのは
~. で、セッションがフリーズしたときに どんな状況でも即座に終了可能
- エスケープシーケンスは 改行(newline)の直後にのみ認識される
ネストした SSH セッションでの利用
- SSH セッション内でさらに SSH 接続した ネスト環境では、
~~ を使って内側のクライアントへシーケンスを渡せる
- 例:
pinkie@stable:~$ ssh ponyville # stable
pinkie@ponyville:~$ ssh manehatten # stable › ponyville
pinkie@manehatten: ~$ # stable › ponyville › manehatten
pinkie@manehatten:~$ Connection to manehatten closed. # ↵Enter `~~.`
pinkie@ponyville:~$ # stable › ponyville
pinkie@ponyville:~$ ssh manehatten stable › ponyville
pinkie@manehatten: ~$ # stable › ponyville › manehatten
pinkie@manehatten:~$ Connection to ponyville closed. # ↵Enter `~.`
pinkie@stable:~$ # stable
stable → ponyville → manehatten の順に接続している状態で
~~. を入力すると 最も内側のセッション(manehatten)だけが終了し、ponyville に戻る
~. を入力すると 中間セッション(ponyville)まで終了し、stable に戻る
おまけの SSH オプション
ssh -C — gzip 圧縮を有効化。ドキュメント上では高速なネットワークでは不要とされているが、TUI の利用や大量のログ出力時には レイテンシと応答性の改善に大きな効果
ssh -v — 詳細ログを有効化(-vv、-vvv でさらに多くの情報を出力可能)。遅い接続や Raspberry Pi のような低速な機器へ接続する際、接続が止まっているのか単に遅いだけなのかの 判別に有用
ssh -D 1234 — localhost:1234 に SOCKS プロキシを作成。サーバーのネットワーク経由で接続できるため、サーバー側 LAN での作業や 簡易 DIY VPN の用途にも活用可能
5件のコメント
わあ、本当に初めて見る機能ですね。これでもうターミナルを閉じなくてもよさそうです
わあ……SSHを十数年使ってきて初めて見る機能です。
本当にメニューが出るんですね。
装置を停止します
えー……
Hacker Newsの意見
私は manpage を積極的に擁護したいと思っていた。たいていのオープンソースの manpage は品質が高く、中には本当に素晴らしいものもある
ただし
manツール自体には問題がある。たとえば OpenSSH クライアントの~?のようなエスケープ構文を探そうとしても、manpage では検索できない理由は、man が
~文字を妙な Unicode のチルダに変換してしまい、grep できなくなるからだ。-文字も同様に変換され、検索できなくなるこれは コマンドラインツールのドキュメント としては致命的だ。こうした変換機能はデフォルトで無効にしておくべきだ
ctrl-rを押して リテラル検索 できる (/<ctrl-r>~?)lessでは問題なく動くman -E asciiオプションで解決した。私の環境は Cygwin 3.6.6 なので、ディストリごとの差かもしれないneovimを pager にすると~?の検索はうまくいく。ただし正規表現のエスケープ (\\~?) を知っている必要がある\\~\\?の検索は問題なく動く私は
~.ショートカットは長く使ってきたが、ヘルプメニュー は知らなかった~を 2 回入力すると実際のチルダ文字を送ることができ、通常のセッションでは先頭文字として入力されない限りエスケープとは認識されないつまり、
~が 行の先頭文字であり、改行の直後 にあるときだけエスケープとして動作する。UI 設計がかなり丁寧だそのため
ls ~/^?^?^?^?^?~/a.outのような出力になることがある。SSH は画面ではなく入力ストリームを監視している~.で終了するには 先に Enter を押さなければならない ことで、これがサーバーに送られる可能性がある私は SSH を 15 年以上使ってきたが、この エスケープシーケンス は初めて知った
次にセッションが固まったら
~.をぜひ使ってみるつもりだ。ターミナルを閉じるよりずっといいVPN や Tailscale を使えば解決できるし、そうでなければ
tcp_keepaliveパラメータを調整して接続を維持できる設定例: こうすると CGNAT 環境でもセッションを維持できる
~.を使っている。SSH に-vオプションを付けると 接続問題のデバッグ にも役立つ~~.で 2 番目の hop を終了できる~.を入力する前には必ず Enter を押して新しい行 から始めなければならない私も
~.は長く使ってきたが、ほかのエスケープは知らなかった。シェルプロンプトではすぐには効かないので、catを実行してから~?を入力する必要がある<enter>~.で終了できる~.でセッションを切っていたが、~が新しい行でしか動作しないことは知らなかった。~^Zも便利そうだ昔の telnet の ctrl-[ シーケンスを思い出す
Enterは単に新しいエスケープ入力を準備する役割を果たしているだけだこうした機能は実は rsh 由来 のものだ。年配なので覚えている
~コマンドスタイルは cu(1) で先に登場した。rsh より前、4.1BSD の時代だscpを rcp のように使うには-Oオプションを付ける必要があるSSH のメニューは トンネリング するときに便利だ。今では Tailscale のようなものに置き換えられつつあるが、それでもまだ有用だ
複数の SSH セッションを 1 つに 多重化 できるので、認証を繰り返さなくて済み、タブ補完も速くなる
ただし、接続が固まったときは少し面倒だ
「秘密」というより、たいていの人が manpage を最後まで読まない のであまり知られていない機能だ
~エスケープは 1970 年代の UNIX cu でも使われていた。SSH はその子孫と見なせるControlMaster の設定はデフォルト値が不便なので、次のような設定ブロックを追加するとよい
こうすると同じホストへの SSH/scp/rsync が 既存の接続を再利用 する
~Cエスケープでセッションの途中にポートフォワーディングを追加することもできるControlPersistを 1 時間くらいまで延ばしておくと、短いログイン間隔でも接続を維持できる私も SSH セッションが固まったときは
[Enter] ~.でしか復旧できなかったLinux の専門家でなければあまり知らない 隠れた機能 のようだ
知ってはいましたが、あまり使う機会はありませんでした。(...)