Title: Wallet: SSS format — classic Shamir + share binding (versioned, authenticated); SLIP-39 optional Status: superseded Superseded by: decision-2026-01-17-cloud-backup-supersedes-sss.md Owner: Artur Date: 2026-01-14
Context:
- В recovery 2-of-3 (U+S+G) нужно делить сид на шарды (k=2, n=3) так, чтобы:
- нельзя было подменить/перемешать шарды между кошельками/профилями/сессиями незаметно;
- формат был простым и предсказуемым для реализации и тест-векторов;
- сервер оставался курьером шифртекста (non-custodial).
- SLIP-39 удобен для ручного восстановления (мнемоники), но добавляет UX/форматную нагрузку; сейчас recovery — машинный (через приложения U/G).
Decision:
- Принять classic Shamir Secret Sharing (Shamir over GF(256)/bytes) для split/merge seed (k=2, n=3).
- Сделать обязательное binding + versioning для каждого шарда через аутентифицированную обёртку:
- шард никогда не хранится/передаётся как “голые” байты Shamir, только как ciphertext в AEAD (AES-GCM / ChaCha20-Poly1305);
- в AEAD AAD (или внутри зашифрованного заголовка) включаем минимум:
sss_format_versionwallet_idsss_profile_id(идентификатор набора шардов/ротации)k,n,share_index,shard_role(U/S/G)- опционально:
guard_id,created_at
- при попытке “скрестить” шарды между кошельками/профилями/ролями — AEAD аутентификация должна падать (детект до merge).
- SLIP-39 оставить опцией, если появится требование ручного восстановления (человек вводит слова). Это отдельный UX-путь, не блокирующий текущий.
OOB (out-of-band) подтверждение — что это:
- OOB подтверждение — проверка recovery-запроса гвардом по независимому каналу, не зависящему от сервера/приложения: звонок владельцу, заранее оговорённый код, личный контакт, второе устройство/мессенджер и т.п.
- Цель: (1) удостовериться, что запрос инициировал владелец, (2) тревожить владельца при атаке, (3) снизить риск социального инжиниринга/компрометации канала push.
Consequences:
- Формат шардов становится версируемым и проверяемым: легче мигрировать/ротировать и ловить ошибки интеграции.
- Реализация обязана везде использовать AEAD с AAD (локально для U/G, на сервере для хранения S-shard), иначе binding теряется.
- SLIP-39 не внедряем сейчас, чтобы не усложнять UX и крипто-спеку без требования.
Links:
- Flow:
wallet/flows/flow-wallet-recovery-2of3.md - Recovery decision (2-of-3):
wallet/decisions/decision-2026-01-13-recovery-2of3.md
Next:
-
Зафиксировать точный binary layout заголовка (fields + sizes) и
sss_format_version=1 - Выбрать/проверить библиотеку Shamir (GF(256)) и добавить test vectors (split/merge + negative tests на подмену metadata)
-
Описать ротацию
sss_profile_id(перевыпуск шардов, rewrap S-shard при смене guard pubkey)