SSH에 비밀 메뉴가 있다는 거 아세요?
(x.com/rebane2001)- 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를 백그라운드로 전환 (연결 종료 대기 중일 때) -
~~— 이스케이프 문자 자체를 전송 (두 번 입력)
-
- 이 시퀀스들은 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 용도로 활용 가능
Hacker News 의견들
-
나는 manpage를 적극 옹호하려고 했음. 대부분의 오픈소스 manpage는 품질이 높고, 일부는 정말 뛰어남
하지만man도구 자체에는 문제가 있음. 예를 들어 openssh 클라이언트의~?같은 escape 문법을 찾으려 했는데, manpage에서 검색이 안 됨
이유는 man이~문자를 이상한 유니코드 틸드로 바꿔버려서 grep이 불가능해짐.-문자도 마찬가지로 변환되어 검색이 안 됨
이건 명령줄 도구의 문서화로서는 치명적임. 이런 변환 기능은 기본값으로 꺼져 있어야 함- 문자 변환 문제는 모르겠지만,
ctrl-r을 눌러 문자 그대로 검색할 수 있음 (/<ctrl-r>~?) - Debian 기본 pager인
less에서는 잘 작동함 -
man -E ascii옵션으로 해결했음. 내 환경은 Cygwin 3.6.6이라 배포판 차이일 수도 있음 -
neovim을 pager로 쓰면~?검색이 잘 됨. 단, 정규식 escape(\~?)를 알아야 함 - macOS와 CentOS에서도
\~\?검색이 잘 됨
- 문자 변환 문제는 모르겠지만,
-
나는
~.단축키는 오래 써왔지만, 도움말 메뉴는 몰랐음
~를 두 번 입력하면 실제 틸드 문자를 보낼 수 있고, 일반 세션에서는 첫 문자로 입력되지 않는 한 escape로 인식되지 않음
즉,~가 줄의 첫 문자이자 새 줄 직후일 때만 escape로 작동함. UI 설계가 꽤 세심함- 젊은 독자들을 위해 설명하자면, 터미널의 echo 모드에서는 백스페이스가 실제로 입력 버퍼를 지우지 않음
그래서ls ~/^?^?^?^?^?~/a.out같은 출력이 나올 수 있음. SSH는 화면이 아니라 입력 스트림을 감시함 - 단점은 세션이 멈췄을 때
~.로 종료하려면 Enter를 먼저 눌러야 함, 이게 서버로 전달될 수도 있음
- 젊은 독자들을 위해 설명하자면, 터미널의 echo 모드에서는 백스페이스가 실제로 입력 버퍼를 지우지 않음
-
나는 SSH를 15년 넘게 써왔지만 이런 escape 시퀀스는 처음 알았음
다음에 세션이 멈추면~.을 꼭 써볼 생각임. 터미널을 닫는 것보다 훨씬 낫겠음- SSH 연결이 자주 끊긴다면 CGNAT의 짧은 TCP timeout 때문일 수 있음
VPN이나 Tailscale을 쓰면 해결 가능하고, 아니면tcp_keepalive파라미터를 조정해 연결을 유지할 수 있음
예시 설정:
이렇게 하면 CGNAT 환경에서도 세션이 유지됨net.ipv4.tcp_keepalive_time=240 net.ipv4.tcp_keepalive_intvl=60 net.ipv4.tcp_keepalive_probes=120 - 나는 20년째 매주
~.을 쓰고 있음. SSH에-v옵션을 주면 연결 문제 디버깅에도 유용함 - SSH를 여러 단계로 연결할 때는
~~.으로 두 번째 hop을 종료할 수 있음 - 나도 거의 30년 가까이 써왔고, 그 전에는 rsh를 썼음. Berkeley r-commands 참고
-
~.을 입력하기 전에는 반드시 Enter를 눌러 새 줄에서 시작해야 함
- SSH 연결이 자주 끊긴다면 CGNAT의 짧은 TCP timeout 때문일 수 있음
-
나도
~.은 오래 써왔지만 다른 escape는 몰랐음. 쉘 프롬프트에서는 바로 안 먹히니cat실행 후~?를 입력해야 함- 그래도 작동함. OpenSSH는 출력이 아니라 입력만 감시하므로
<enter>~.으로 종료 가능함 - 나도 항상
~.으로 세션을 끊었지만,~가 새 줄에서만 작동한다는 건 몰랐음.~^Z도 유용해 보임
예전 telnet의 ctrl-[ 시퀀스가 떠오름 - SSH 클라이언트는 원격 세션의 모드를 몰라도 escape를 인식함.
Enter는 단지 새 escape 입력을 준비시키는 역할임
- 그래도 작동함. OpenSSH는 출력이 아니라 입력만 감시하므로
-
이런 기능들은 사실 rsh에서 유래한 것임. 나이 든 사람이라 기억함
- 사실
~명령 스타일은 cu(1) 에서 먼저 나왔음. rsh보다 이전의 4.1BSD 시절임 - 요즘은
scp를 rcp처럼 쓰려면-O옵션을 줘야 함 - uucp!bangpath 시절을 기억하는 사람으로서 웃음이 나옴
- 사실
-
SSH의 메뉴는 터널링할 때 유용함. 요즘은 Tailscale 같은 걸로 대체되긴 했지만 여전히 쓸모 있음
- 나는 새 탭에서 “새 연결”을 열 때 ControlMaster 기능을 씀
여러 SSH 세션을 하나로 멀티플렉싱해서 인증을 반복하지 않아도 되고, 탭 완성도 빠름
단, 연결이 멈출 때는 약간 귀찮음 - 나는 tuns.sh를 자주 씀. 로컬호스트를 외부에 노출할 수 있어서 편리함
- 나는 새 탭에서 “새 연결”을 열 때 ControlMaster 기능을 씀
-
“비밀”이라기보다 대부분의 사람이 manpage를 끝까지 읽지 않기 때문에 잘 모르는 기능임
-
~escape는 1970년대 UNIX cu에서도 쓰였음. SSH는 그 후손이라 볼 수 있음 -
ControlMaster 설정은 기본값이 불편하므로 아래처럼 설정 블록을 추가하면 좋음
Host * ControlMaster auto ControlPath ~/.ssh/sockets/%r@%h:%p ControlPersist 10m이렇게 하면 동일 호스트로의 SSH/scp/rsync가 기존 연결을 재사용함
~Cescape로 세션 중간에 포트 포워딩을 추가할 수도 있음-
ControlPersist를 1시간 정도로 늘려두면 짧은 로그인 간격에서도 연결이 유지됨 - 이 댓글은 LLM이 쓴 것 같다는 농담도 있었음
-
-
나도 SSH 세션이 멈췄을 때
[Enter] ~.으로만 복구할 수 있었음
리눅스 전문가가 아니면 잘 모르는 숨은 기능 같음