# SSH escape-последовательности: оживление зависшего терминала

Индекс LLMS: [llms.txt](/llms.txt)

---

SSH-сессия зависла, `Ctrl+C` не помогает, `Ctrl+D` вываливает мусор — знакомая картина. Прежде чем закрывать терминал и терять сессию, попробуй встроенные escape-последовательности. Они работают на уровне SSH-клиента до того, как данные попадут на удалённый хост.

## Как вызвать escape-последовательность

Escape-символ по умолчанию — тильда (`~`). Комбинация срабатывает только в начале строки. Нажал Enter, затем `~`, затем нужный символ. Например, `~.` рвёт соединение.

> [!NOTE]
> Если тильда не срабатывает — проверь, что нажал Enter перед ней. В середине вывода терминала последовательность игнорируется.

## Справка по всем escape-последовательностям

```bash
ssh> ~?
```

Эта команда выводит список доступных escape-последовательностей прямо в терминал.

```
Supported escape sequences:
 ~.  - terminate connection (and any multiplexed sessions)
 ~B  - send a BREAK to the remote system
 ~C  - open a command line
 ~R  - request rekey
 ~V/~v  - decrease/increase verbosity (LogLevel)
 ~^Z  - suspend ssh
 ~#  - list forwarded connections
 ~&  - background ssh (when waiting for connections to terminate)
 ~?  - this message
 ~  - send the escape character by typing ~~
```

Запоминать всё не обязательно. Держи в голове три сценария — они закрывают 90% проблем.

## Аварийное отключение

```bash
# Пример: зависший scp или sftp
# Нажимаем Enter, затем:
~.
```

`~.` закрывает SSH-соединение немедленно, включая все мультиплексированные сессии. Работает даже если удалённый хост не отвечает. Не путай с `~^Z` (suspend) — тот фоновый процесс оставит сессию живой.

> [!WARNING]
> Принудительное отключение не отправляет SIGHUP на удалённую сторону. Если в сессии был важный процесс без nohup — он умрёт.

## Прерывание потока

```bash
# Завис вывод команды или медленный SCP
~V
```

`~V` (Shift+v) понижает уровень логирования. Обратная команда — `~v` — повышает детализацию. На практике полезно, когда видишь поток бессмысленных отладочных сообщений и хочешь их скрыть.

Более радикальный вариант — `~B`. Отправляет BREAK на удалённую систему. Это может прервать зависший процесс, который слушает serial-порт. Используй осознанно: не все системы корректно обрабатывают BREAK.

## Встроенный командный режим

```bash
# Enter, затем:
~C
```

Попадаешь в командную строку SSH-клиента. Здесь можно управлять туннелями на лету без переподключения.

```bash
ssh> -L 8080:localhost:80
# Добавили локальный порт 8080 -> remote:80

ssh> -R 2222:localhost:22
# Добавили реверс-прокси на удалённом хосте

ssh> -D 1080
# SOCKS-прокси на порту 1080

ssh> -KL 8080
# Удалить проброшенный локальный порт

ssh> help
```

> [!TIP]
> Командный режим удобен, когда забыл пробросить порт до подключения. Не нужно переподключаться — добавил прямо из сессии.

Формат: `-L [bind_addr:]port:host:hostport` и `-R [bind_addr:]port:host:hostport`. Бинд-адрес `localhost` ограничит проброс локальным интерфейсом.

## Принудительный rekey

```bash
~R
```

Принудительно инициирует повторное согласование ключей сессии. Иногда полезно, если замечаешь странные задержки или подозреваешь проблемы с шифрованием. На практике встречается редко, но знать стоит.

## Сводная таблица escape-последовательностей

| Последовательность | Действие |
|---|---|
| `~.` | Аварийное отключение |
| `~V` | Понизить verbosity |
| `~v` | Повысить verbosity |
| `~C` | Командная строка (туннели) |
| `~R` | Принудительный rekey |
| `~B` | Отправить BREAK |
| `~?` | Показать справку |
| `~^Z` | Приостановить ssh |
| `~#` | Список проброшенных соединений |
| `~&` | Фоновый режим (при закрытии) |
| `~~` | Отправить literal тильду |

## Изменение escape-символа

Если по работе нужен тильда в удалённой сессии (например, подключение к Cisco-оборудованию), меняй символ:

```bash
ssh -e '^Z' user@host
```

Теперь escape-последовательности вызываются через `^Z` вместо `~`. Встречается в специфических сценариях — не трогай без необходимости.

> [!NOTE]
> Поменять символ на лету в уже активной сессии нельзя. Только при подключении через флаг `-e`.

## Типичные грабли

1. `~` не срабатывает — забыл нажать Enter перед ней.
2. Сессия зависла, но ты не уверен, что SSH ещё жив — попробуй `~.` вслепую. Хуже не станет.
3. Multiplexing-сессия (`ssh -M`) привязана к управляющему сокету. `~.` закроет все связанные сессии разом.
4. Если используешь PuTTY — escape-последовательности другие. Там `~.` отправляет literal тильду и точку. Работает `Ctrl+]` и затем `close`.

## Когда escape-последовательности не помогут

- Сеть физически недоступна — только разрыв.
- Удалённый процесс поглотил stdin — ssh ничего не получит.
- Проблема на уровне терминального эмулятора — killall ssh, потом проверь tmux/screen.

SSH escape-последовательности — инструмент первой линии при зависании сессии. Держи в памяти `~.` для отключения и `~C` для туннелей — этого хватит на каждый день.
