29P by GN⁺ 14시간전 | ★ favorite | 댓글 5개
  • SSH 세션이 멈췄을 때 프로세스를 강제 종료할 필요 없이, SSH에 내장된 이스케이프 시퀀스 메뉴를 통해 다양한 제어 가능
  • 세션 내에서 ↵Enter 입력후 ~?를 입력하면 숨겨진 명령어 목록이 표시되며, ~.으로 어떤 상황에서도 즉시 연결 종료 가능
  • 이 이스케이프 시퀀스는 SSH 클라이언트 자체에 내장되어 있어 서버나 연결이 끊어진 상태에서도 동작
  • 중첩 SSH 세션에서는 ~~를 사용해 내부 클라이언트로 시퀀스를 전달할 수 있음
  • 추가로 -C, -v, -D 등의 유용한 SSH 옵션도 함께 소개

SSH 이스케이프 시퀀스 메뉴

  • SSH 세션 내에서 ↵Enter를 누른 뒤 ~?를 입력하면 지원되는 이스케이프 시퀀스 목록 확인 가능
  • 주요 시퀀스 목록:
    • ~. — 연결 종료 (멀티플렉싱된 세션 포함)
    • ~B — 원격 시스템에 BREAK 신호 전송
    • ~C커맨드 라인 열기 (포트 포워딩 설정 가능, help 입력으로 안내 확인)
    • ~Rrekey 요청
    • ~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 -Cgzip 압축 활성화, 문서상으로는 빠른 네트워크에서 불필요하다고 되어 있지만 TUI 사용이나 대량 로그 출력 시 지연시간과 반응성 개선에 큰 효과
  • ssh -v상세 로깅 활성화 (-vv, -vvv로 더 많은 정보 출력 가능), 느린 연결이나 Raspberry Pi 같은 느린 장비 접속 시 연결이 멈춘 것인지 단순히 느린 것인지 판별에 유용
  • ssh -D 1234localhost:1234SOCKS 프록시 생성, 서버의 네트워크를 통해 접속 가능하여 서버 측 LAN 작업이나 간이 DIY VPN 용도로 활용 가능

장비를 정지 합니다
어......

와 진짜 첨보는 기능이네요; 이제 터미널을 안꺼도 되겠군요

와.. SSH를 십수년 쓰면서 첨 보는 기능이에요.
정말 메뉴가 뜨는군요.

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를 먼저 눌러야 함, 이게 서버로 전달될 수도 있음
  • 나는 SSH를 15년 넘게 써왔지만 이런 escape 시퀀스는 처음 알았음
    다음에 세션이 멈추면 ~.을 꼭 써볼 생각임. 터미널을 닫는 것보다 훨씬 낫겠음

    • SSH 연결이 자주 끊긴다면 CGNAT의 짧은 TCP timeout 때문일 수 있음
      VPN이나 Tailscale을 쓰면 해결 가능하고, 아니면 tcp_keepalive 파라미터를 조정해 연결을 유지할 수 있음
      예시 설정:
      net.ipv4.tcp_keepalive_time=240
      net.ipv4.tcp_keepalive_intvl=60
      net.ipv4.tcp_keepalive_probes=120
      
      이렇게 하면 CGNAT 환경에서도 세션이 유지됨
    • 나는 20년째 매주 ~.을 쓰고 있음. SSH에 -v 옵션을 주면 연결 문제 디버깅에도 유용함
    • SSH를 여러 단계로 연결할 때는 ~~.으로 두 번째 hop을 종료할 수 있음
    • 나도 거의 30년 가까이 써왔고, 그 전에는 rsh를 썼음. Berkeley r-commands 참고
    • ~.을 입력하기 전에는 반드시 Enter를 눌러 새 줄에서 시작해야 함
  • 나도 ~.은 오래 써왔지만 다른 escape는 몰랐음. 쉘 프롬프트에서는 바로 안 먹히니 cat 실행 후 ~?를 입력해야 함

    • 그래도 작동함. OpenSSH는 출력이 아니라 입력만 감시하므로 <enter>~.으로 종료 가능함
    • 나도 항상 ~.으로 세션을 끊었지만, ~가 새 줄에서만 작동한다는 건 몰랐음. ~^Z도 유용해 보임
      예전 telnet의 ctrl-[ 시퀀스가 떠오름
    • SSH 클라이언트는 원격 세션의 모드를 몰라도 escape를 인식함. Enter는 단지 새 escape 입력을 준비시키는 역할임
  • 이런 기능들은 사실 rsh에서 유래한 것임. 나이 든 사람이라 기억함

    • 사실 ~ 명령 스타일은 cu(1) 에서 먼저 나왔음. rsh보다 이전의 4.1BSD 시절임
    • 요즘은 scp를 rcp처럼 쓰려면 -O 옵션을 줘야 함
    • uucp!bangpath 시절을 기억하는 사람으로서 웃음이 나옴
  • SSH의 메뉴는 터널링할 때 유용함. 요즘은 Tailscale 같은 걸로 대체되긴 했지만 여전히 쓸모 있음

    • 나는 새 탭에서 “새 연결”을 열 때 ControlMaster 기능을 씀
      여러 SSH 세션을 하나로 멀티플렉싱해서 인증을 반복하지 않아도 되고, 탭 완성도 빠름
      단, 연결이 멈출 때는 약간 귀찮음
    • 나는 tuns.sh를 자주 씀. 로컬호스트를 외부에 노출할 수 있어서 편리함
  • “비밀”이라기보다 대부분의 사람이 manpage를 끝까지 읽지 않기 때문에 잘 모르는 기능임

  • ~ escape는 1970년대 UNIX cu에서도 쓰였음. SSH는 그 후손이라 볼 수 있음

  • ControlMaster 설정은 기본값이 불편하므로 아래처럼 설정 블록을 추가하면 좋음

    Host *
      ControlMaster auto
      ControlPath ~/.ssh/sockets/%r@%h:%p
      ControlPersist 10m
    

    이렇게 하면 동일 호스트로의 SSH/scp/rsync가 기존 연결을 재사용
    ~C escape로 세션 중간에 포트 포워딩을 추가할 수도 있음

    • ControlPersist를 1시간 정도로 늘려두면 짧은 로그인 간격에서도 연결이 유지됨
    • 이 댓글은 LLM이 쓴 것 같다는 농담도 있었음
  • 나도 SSH 세션이 멈췄을 때 [Enter] ~.으로만 복구할 수 있었음
    리눅스 전문가가 아니면 잘 모르는 숨은 기능 같음

알고는 있었지만 별로 쓸일이 없었습니다. (...)