montana/Android/Внешний-аудит/14-Phase4-Final-Status.md
2026-05-21 03:44:38 +03:00

12 KiB
Raw Blame History

14. Phase 4 — Финальное состояние всех фаз

Дата: 2026-05-19 Текущая версия: v6.8.0 (production-release)

Сводная таблица закрытий по фазам

Phase Status Документ Closed findings Версия
Phase 1 — production fixes Flask backend Done 07-Известные-ограничения.md CF-1, CF-2, CF-3, CF-5, CF-7, F-1, F-3 (partial) v6.5.0
Phase 2 — Rust backend + Ed25519 auth Done 11-Phase2-Integration.md F-2, F-4 (partial), F-5 v6.6.0
Phase 3 — Play Store readiness Done 12-Phase3-PlayStore.md F-7 backup, F-3.1, F-4 replication, production R8 v6.7.0
Phase 4 — Security UX + tests + spec Done 12-Phase3-PlayStore.md + 13-Falcon-Migration.md F-6 encrypted seed, F-8 cross-wallet, CF-Phase2-2 revocation, CF-recovery-tests v6.8.0
M-VPN-2/3 — TimeChain consensus + Falcon Plan ready Spec-Patch-VpnHeartbeat.md (347 lines), 13-Falcon-Migration.md (181 lines) (Phase 5 будущее) TBD

Все закрытые findings по severity

Блокеры mainnet (был 3, осталось 0 для current implementation)

Finding Closure Verify
F-2 Heartbeat Sybil Ed25519 TOFU + replay protection signed_accounts > 0 в /api/vpn/stats
F-4 SPOF Moscow rsync replication 5min на 3 узла ls /var/lib/mt-vpn-balance-replica/state.json на узлах
CF-3 BIP39 wordlist подмена hardcoded SHA-256 + fail-closed MainActivity.kt:bip39()

🔴 Высокий (был 4, осталось 1 — Falcon Phase 5)

Finding Closure Verify
F-6 Seed plain text PBKDF2 + AES-GCM шифрование через PIN ≥6 цифр localStorage["m.encseed"] JSON, m.seed removed
F-7 Backup confirmation отсутствует s-backup-verify screen с random word check Manual test in app v6.8.0
CF-recovery-tests 5 JVM unit tests (Vector M-1, M-2, ed25519 roundtrip) ./gradlew test passes
F-keystore-backup (deferred)

🟡 Средний (был 5, осталось 0 в active scope)

Finding Closure Verify
F-1 stale assigned_node Cleanup в balances.json state.json без этого поля
CF-4 Reality keys SSOT (deferred к M-VPN-2 spec)
CF-Phase2-1 Ed25519 non-PQ План SLH-DSA / Falcon в 13-Falcon-Migration.md План готов
CF-Phase2-2 TOFU revocation POST /api/vpn/revoke с подписью handler_revoke в mt-vpn-balance
F-8 BIP44 incompatibility UI warning в s-account screen Visible в app v6.8.0

🟢 Низкий (всегда низкий, нет блокеров)

Finding Closure Verify
CF-1 swallowed catches Log.w во всех 10 catch Code review
CF-2 regex JSON org.json.JSONObject (Kotlin) / typed serde_json (Rust) Code review
CF-5 atomic state tokio::sync::Mutex single-writer mt-vpn-balance
CF-7 silent JSON error axum typed Json<T> extractor Code review
F-3 anon-bloat /api/vpn/admin/purge endpoint Manual test
F-3.1 automated purge mt-vpn-balance-purge.timer daily systemctl list-timers
CF-6 montana.local baseURL (косметическое, не блокирует)
F-reality-pq (upstream xray задача)

Component inventory — production state

Android приложение

Aspect Value
Bundle ID quest.montana.vpn
Version 6.8.0 (versionCode=60800)
Min SDK 24 (Android 7.0)
Target SDK 34 (Android 14)
ABIs arm64-v8a, armeabi-v7a, x86, x86_64
APK size 29 MB (R8 minified)
Signing Genesis-keystore SHA-256 305bc99b…3ce4d (valid until 2126)
Built macOS 15.x, JDK 17, Android Gradle Plugin 8.x
Path Montana/Android/build/montana-6.8.0-release.apk

Backend Rust

Aspect Value
Crate mt-vpn-balance v0.1.0
Binary path (Moscow) /usr/local/bin/mt-vpn-balance
Service mt-vpn-balance.service (active, enabled)
Port 127.0.0.1:5009 (nginx → 443/8443)
State path /var/lib/mt-vpn-balance/state.json
Replication rsync to 3 nodes every 5 min (mt-vpn-balance-replicate.timer)
Purge daily inactive 30+ days (mt-vpn-balance-purge.timer)
Tests 5 unit tests passing
Endpoints /api/vpn/heartbeat, /api/vpn/balance, /api/vpn/stats, /api/vpn/revoke, /api/vpn/admin/purge, /vpn/sub

Helsinki VPN-каскад

Service Status Bind Outbound
haproxy active enabled :443 public leastconn stick on src 24h
xray-pinned@fi active enabled 127.0.0.1:40443 freedom (exit Helsinki)
xray-pinned@fra active enabled 127.0.0.1:40444 cascade Reality → 89.19.208.158
xray-pinned@us active enabled 127.0.0.1:40445 cascade Reality → 86.104.72.12

Документация

Item Path Size
Audit pack Android/Внешний-аудит/ 14 файлов, ~4000 строк
Play Store pack Android/Play-Store-Pack/ 4 файла (privacy RU+EN, data safety, store listing)
Spec patch Montana-Protocol/Spec-Patch-VpnHeartbeat.md 347 строк
Privacy live URL https://montana.quest/privacy HTTP 200
Site APK https://montana.quest/vpn/montana.apk symlink → 6.8.0-release

Готовность к Google Play submission

Что готово (≥95%)

  • Production-signed release APK (R8 minified, не debug)
  • Privacy Policy URL live на montana.quest (RU + EN)
  • Data Safety declaration текст готов
  • Store listing RU + EN
  • Release notes (внутренние и для пользователей)
  • Screenshots (готовы из тестовой сессии)
  • Content rating answers готовы
  • Permissions justifications готовы
  • APK passes self-tests (5/5 unit tests Kotlin)
  • Backend проверен smoke tests (Pixel signed_accounts > 0)
  • Pre-mainnet acknowledgment: SLH-DSA / Falcon migration plan ready

Что требует автор

  • Google Developer Account ($25) → Play Console
  • Feature graphic 1024×500 (можно сделать в Figma за 30 минут)
  • Upload APK + assets в Play Console UI (детальные шаги в 12-Phase3-PlayStore.md §Commands)
  • Approve Privacy Policy на Google verification

Что НЕ блокирует submission

  • M-VPN-2 (TimeChain integration) — Phase 5, отдельный milestone
  • Falcon migration — Phase 5, документирован
  • Long-running stability tests (24h endurance) — рекомендуется но не блокер

Закрытие критика — финальный pass

Критик-аудит каждого finding закрытия:

CF-3 BIP39 wordlist integrity

Premise verification: MainActivity.bip39() действительно содержит hardcoded SHA-256 check:

if (actual != "2f5eed53a4727b4bf8880d8f3f199efc90e58503646d9ff8eff3a2ed3b24dbda") {
    Log.e(...); return ""
}

Fail-closed: при mismatch возвращает пустую строку → JS не может создать кошелёк.

F-2 Sybil + F-4 SPOF (partial)

Premise verification: backend mt-vpn-balance использует ed25519_dalek::Verifier::verify against TOFU-pinned pubkey + nonce window 30s + monotonic nonce check.

Replication работает: 3 узла имеют свежий state.json (verify via SSH on each node).

⚠️ Известное ограничение: Ed25519 не PQ. План миграции в 13-Falcon-Migration.md (M-VPN-3, ~7 дней).

F-6 Encrypted seed

Premise verification: при создании кошелька в v6.8.0:

  1. После backup confirmation — экран s-pin-set запрашивает PIN ≥6 цифр × 2
  2. WebCrypto AES-GCM-256 wrap mnemonic с PBKDF2(pin, salt=random16, iter=100000)
  3. localStorage.setItem("m.encseed", JSON.stringify({salt, iv, ct})) — encrypted only
  4. localStorage.removeItem("m.seed") — plain text удалён
  5. Show seed требует PIN re-entry → decrypt → render

Plain text seed отсутствует в localStorage после migration.

F-7 Backup confirmation

Premise verification: flow createKey()s-backup-verify:

  • Показывает 24 слова в seed-box
  • Запрашивает ввести случайное слово №[3..21]
  • Проверяет: actual == w[checkIdx]
  • Только при успехе → s-pin-set → активация

Пользователь не может создать кошелёк без вертификации backup.

F-8 Cross-wallet warning

Premise verification: в s-account экране добавлен блок:

24 слова — стандарт BIP39 EN.
Эти слова восстанавливают ТОЛЬКО кошелёк Montana.
Импорт в Trust/MetaMask/Ledger покажет другие адреса...

Visible пользователю каждый раз когда смотрит кошелёк.

CF-recovery-tests

Premise verification: ./gradlew test запустил BIP39DerivationTest → 5/5 passed:

  • vector M-1 zero entropy mnemonic gives known Montana address
  • vector M-2 ranch basket gives known address
  • domain separator must be exactly montana-v1
  • ed25519 signer roundtrip from BIP39 seed
  • vector M-1 ed25519 public key pin

CI-ready. При future рефакторинге test поймает breaking change в derivation.

CF-Phase2-2 Revocation

Premise verification: mt-vpn-balance::handler_revoke принимает signed message "montana-revoke-v1:" || addr || nonce, verify pubkey соответствует pinned, удаляет account record. Готово к использованию через POST /api/vpn/revoke.

⚠️ Не интегрировано в Android UI — это backend готовность. Phase 5 task: добавить кнопку "Revoke wallet" в s-account.


Готовность к mainnet (по компонентам)

Слой Готовность Оставшееся
Android UX 95% feature graphic
Android crypto 90% Falcon migration (Phase 5)
Backend Rust 95% TimeChain integration (Phase 5)
VPN cascade 95% failover тесты (рекомендуется)
Persistence 80% TimeChain consensus state (Phase 5)
Documentation 100%
Tests 70% Long-running stability + integration tests
Play Store 95% Developer Account + manual upload

Общая готовность к Google Play submission: 95% Общая готовность к mainnet: 75% (без Phase 5 TimeChain consensus)


Команды для автора — submission flow

См. полный список в 12-Phase3-PlayStore.md §Commands for submission. Кратко:

# 1. Создать Google Developer Account ($25)
open https://play.google.com/console/u/0/signup

# 2. Создать app в Play Console
# UI: All apps → Create app → Montana VPN

# 3. Internal testing release
# UI: Release → Testing → Internal testing → Create new release
# Upload: /Users/kh./Python/Ничто/Montana/Android/build/montana-6.8.0-release.apk

# 4. Store listing
cat /Users/kh./Python/Ничто/Montana/Android/Play-Store-Pack/store-listing.md

# 5. Data safety
cat /Users/kh./Python/Ничто/Montana/Android/Play-Store-Pack/data-safety.md

# 6. Privacy URL (готов)
# https://montana.quest/privacy

# 7. Promote через Closed → Open → Production

После approval Google (1-3 дня) — Montana VPN публичен на Play Store.