87 lines
7.6 KiB
Markdown
87 lines
7.6 KiB
Markdown
# TrueNAS — Восстановление ZFS пула при kernel panic (space map corruption)
|
||
|
||
> Создано 2026-08-17. Зеркало скила `truenas-zfs-panic-recovery`.
|
||
|
||
## Когда это нужно
|
||
|
||
Пул TrueNAS не импортируется и вызывает **kernel panic / boot loop**:
|
||
```
|
||
panic - not syncing: zfs: adding existent segment to range tree
|
||
ZFS: space_map_load / metaslab_activate / zio_dva_allocate → zfs_panic_recover
|
||
```
|
||
Это **повреждение space map (метаданных ZFS)**. НЕ обязательно потеря данных, но структура пула повреждена. Read-write импорт паникует, т.к. читает битые space maps.
|
||
|
||
## Ключевая идея
|
||
|
||
**Read-only import НЕ читает space maps и НЕ паникует** (mav/iXsystems: "read-only imports don't even read space maps"). Стратегия: обойти панику → readonly-импорт → выгрузить данные → пересоздать пул.
|
||
|
||
**Пул НЕ «чинится»** — только выгрузка данных и пересоздание.
|
||
|
||
## Проверенные шаги (2026-08-17, TrueNAS SCALE 24.10)
|
||
|
||
### 1. Загрузка без паники — единственный рабочий способ:
|
||
|
||
**Физически отключить все диски проблемного пула** → boot-pool поднимается, паники нет → дошли до shell/WebUI → **воткнуть диски обратно (горячо)** в те же порты.
|
||
|
||
**Что НЕ работает (проверено):**
|
||
- Тюнабели в GRUB `zfs.zfs_recover=1 zfs.zil_replay_disable=1` — не помогли
|
||
- `rd.break=pre-mount` и `rd.break` — не помогли
|
||
- `zfsforce=1` — не помогает
|
||
|
||
### 2. Readonly-импорт (под root):
|
||
|
||
```bash
|
||
/usr/sbin/zpool import -o readonly=on RED_2TB
|
||
```
|
||
→ `Import was successful, but unable to mount some datasets` — это нормально/ожидаемо.
|
||
|
||
### 3. Монтирование datasets (2026-08-18: подтверждено под root)
|
||
|
||
Если корневая ФС readonly мешает создавать mountpoint-ы (`cannot mount '/RED_2TB': failed to create mountpoint: Read-only file system`) — сначала сделать root ФС rw, затем смонтировать всё:
|
||
```bash
|
||
mount -o remount,rw /
|
||
zfs mount -a
|
||
```
|
||
После этого дочерние datasets (`storage`, `backup`, `Photos`, `Edu`, `docker`, `old-bu`, `TimeMachine/guest`, `iocage/*`) видны на `/RED_2TB/*` (все `ro` — readonly; для чтения rsync это ок). Проверка: `df -h /RED_2TB` покажет ~4.6T (НЕ 1.1T родительского), `ls /RED_2TB/storage` не пуст.
|
||
> ⚠️ Монтирование — **только под root**. Под `truenas_admin` `zfs mount -a` даёт `Insufficient privileges`.
|
||
|
||
### 4. Выгрузка:
|
||
|
||
```bash
|
||
rsync -aHAX --info=progress2 /RED_2TB/ /mnt/IRONWOLF/ > /tmp/rsync2.log 2>&1 &
|
||
```
|
||
Лучше в tmux. Затем `zpool destroy` + пересоздать пул.
|
||
|
||
**⚠️ ВАЖНО (2026-08-18): использовать именно `rsync`, НЕ `zfs send | zfs recv`.** `zfs send` на пуле с повреждённой space map падает (`signal received` / `Bad file descriptor` / `IOT (core dumped)`, exit 1) — ZFS не может прочитать данные на лету при stream-чтении. rsync переживает ошибки чтения отдельных файлов (exit 23) и копирует остальное.
|
||
|
||
**⚠️ Почему первая попытка rsync дала только 355G (разгадано 2026-08-18):** дочерние datasets НЕ были смонтированы, поэтому `/RED_2TB/storage` и др. были пустыми mountpoint-дирами; rsync скопировал только ~355G из родительского dataset. **Сначала смонтировать datasets (`zfs mount -a`), потом rsync** — иначе скопируется лишь несколько сотен ГБ.
|
||
|
||
**Целевой диск для выгрузки (2026-08-17):** **IronWolf 12TB** подключён к материнке (`sdc`, by-id `WV700FQ5`, 10.9T, свободен/не в пуле) — создай на нём пул-приёмник и копируй туда. Места достаточно (10.9T > 4.6T данных).
|
||
|
||
**Что на RED_2TB спасать (структура datasets от 2026-08-17):**
|
||
- Критично (пользовательские данные): `storage` (3.24T), `backup` (287G), `Photos` (146G), `Edu` (214G), `TimeMachine` (+`guest`, 277G), `old-bu` (65.5G), `openbsd` (10.2G).
|
||
- Конфиги (если нужно): `docker` (2.98G), `iocage/*` jails (plex, emby, homeassistant, transmission, worker), `ix-apps` (24G).
|
||
- Служебное не критично: `RED_2TB/.system/*`.
|
||
- Итого ~4.6T. Для «100% восстановления с правами»: `rsync -aHAX` или `zfs send | zfs recv`.
|
||
|
||
### 5. Пул НЕ чинится in-place — только пересоздание
|
||
|
||
`zpool attach` (идея зеркала на 2 WD2TB) НЕ выполним в текущем состоянии — attach это write → паника. Всегда: спасти → destroy → recreate.
|
||
|
||
## Подводные камни
|
||
|
||
- `zpool` не в PATH для zsh-юзеров (`command not found`) — использовать `/sbin/zpool` или `/usr/sbin/zpool`.
|
||
- `zpool import` требует **root** (`some devices require root privileges`). `truenas_admin` НЕ root, sudo просит пароль. **На конец 2026-08-17 это главный блокер** — для импорта/монтирования/выгрузки нужен root (через WebUI-админ, консоль, или включив `PermitRootLogin` в SSH).
|
||
- **WD 2TB#1 (`sdd2` simplex-член RED_2TB) сейчас отключён** — чтобы загрузиться без паники его отсоединяли. RED_2TB импортируется без него (mirror-1 жив), но его данные частично недоступны. Учесть при восстановлении.
|
||
- `zpool import -n RED_2TB` — нелегальный синтаксис без `-F` (`-n` только с `-F`).
|
||
- **НЕ повторять `import -F` настойчиво** — углубляет риск. Сначала readonly.
|
||
- `zpool import -f -F -X` НЕ работает для этой паники (TrueNAS forum).
|
||
- **⚠️ ЛОВУШКА «zfs send -n» (dry-run) НЕ подтверждает права send:** под `truenas_admin` `zfs send -n` возвращал exit 0 без ошибок — обманчиво. Реальный `zfs send` даёт `permission denied`. Дочерние datasets доступны только root (ACL root-only). Не доверять dry-run для проверки прав send.
|
||
- Данные могут показать `Permission denied` если сами данные повреждены (в тяжёлых случаях — частичное восстановление).
|
||
- **Проверить RAM** — на non-ECC (P8H77-V) повреждение space map часто от плохой памяти. memtest.
|
||
- Буквы дисков shift-аются — сверять по by-id/модели, не по буквам.
|
||
|
||
## Root cause
|
||
|
||
`adding existent segment to range tree` = openzfs #15030 / #13483. Триггер: члены пула отвалились при перетыкании/перезагрузке, либо RAM corruption (non-ECC).
|