- PVSM.RU - https://www.pvsm.ru -
Как я сделал форк Fenix для сайтов, чьи TLS-цепочки не принимаются обычной сборкой Firefox, и почему это не «защита от MITM».
Началось всё с обычной пользовательской проблемы: некоторые сайты, в том числе банковские, не открывались в привычных мне браузерах. Из тех, что я проверил, подключение проходило в Яндекс Браузере и браузере с поддержкой ГОСТ. В мобильном Firefox соединение останавливалось на проверке сертификата.
Можно было просто пользоваться другим браузером. Но мне стало интересно, что именно не сходится в цепочке и можно ли добавить поддержку так, чтобы было видно, где и почему она включается.
Так появился matre$ka: форк Fenix на базе Firefox для Android с небольшим патчем GeckoView. Он добавляет ограниченную поддержку цепочек Russian Trusted и интерфейс, который показывает, когда сработало это дополнительное доверие.
Сразу важная оговорка: проект не устраняет атаки типа man-in-the-middle и не делает банковский сайт безопасным. Это изменение набора центров сертификации, которым браузер готов доверять в определённых случаях. Такой механизм решает проблему совместимости, но одновременно расширяет модель доверия.
При TLS-соединении браузер проверяет сертификат сервера и путь сертификации: конечный сертификат, возможные промежуточные сертификаты и доверенный корень. Валидация включает, среди прочего, подписи, сроки действия и связь издателя с субъектом. Доверенный корень — исходное условие этой проверки: если добавить новый trust anchor, изменится множество цепочек, которые браузер способен принять. Это часть модели безопасности, а не косметическая настройка. Подробнее процесс описан в RFC 5280 [1].
В этой работе «MITM» часто употребляют слишком широко. Если сеть или прокси подменяет соединение сертификатом, который не ведёт к доверенному CA, корректно настроенный клиент должен отклонить его. Но если в доверенное хранилище добавлен CA, способный выпускать сертификаты для нужного имени, одна лишь проверка цепочки уже не отличит такой сертификат от легитимного. Поэтому фраза «добавили сертификат — защитились от MITM» неверна. Вопрос всегда в том, кому делегировано право удостоверять сайты, для каких имён и как контролируется актуальность этого решения.
Обычная сборка Firefox не принимает часть цепочек, используемых сайтами на Russian Trusted. Цель matre$ka — дать браузеру возможность проверить такие цепочки, не отключая проверку TLS целиком и не направляя трафик через собственный прокси.
Встроены два российских корневых сертификата. Для явно перечисленных хостов дополнительная проверка может построить цепочку до этих корней. Также в текущей конфигурации включён fallback для доменов .ru и .рф: хост может отсутствовать в списке, но цепочка всё равно должна провериться до одного из встроенных корней. Произвольный самоподписанный сертификат или любой сертификат, который просто прислал сервер, от этого доверенным не становится.
Это важный нюанс: список хостов полезен для интерфейса и явных правил, но fallback расширяет область действия доверия. Я не описываю этот режим как строгий allowlist. Если нужен режим, в котором новые домены не получают дополнительного доверия без ручного добавления, fallback следует выключить.
В Fenix есть слой, собирающий конфигурацию из трёх источников: списка, поставляемого с приложением, удалённого списка хостов и пользовательских записей. Удалённое обновление передаётся по HTTPS и может дополнять хосты, но не корни. Корневые сертификаты остаются в APK — сервер со списком не может незаметно добавить новый CA.
Затем Android-часть передаёт компактный bundle в GeckoView через API, добавленный патчем. Внутри Gecko изменение применяется к проверке сертификатной цепочки: сертификат-кандидат должен быть одним из встроенных DER-сертификатов, распознаваться как CA, а доверие применяется только для подходящего хоста. Обычная проверка цепочки остаётся необходимой.
Патч лежит отдельным файлом в репозитории. Это позволяет отдельно просматривать изменение Gecko, проверять его применимость к закреплённой базе Firefox и собирать форк поверх исходников. Открытый код помогает понять, что делает реализация, но сам по себе не равен независимому аудиту и не доказывает, что опубликованный APK побайтно воспроизводится из дерева исходников.
Если сайт использует дополнительную цепочку, браузер может показать янтарный индикатор. Это сигнал о состоянии списка и сертификатного сценария, а не оценка репутации сайта. Он не означает «здесь безопасно» и не обнаружит все возможные виды перехвата или вредоносного поведения.
В проекте также есть отдельный storage-контекст для новых вкладок на российских хостах. Контекст задаётся при создании GeckoSession и отделяет cookies через origin attributes, а часть web storage использует отдельные директории. Это не отдельный профиль: runtime и физический файл cookies.sqlite общие, HTTP-кэш и разрешения тоже не разделяются. Уже открытая обычная вкладка не переключается в другой контекст после перехода на .ru или .рф.
Изоляция storage и доверие TLS — два самостоятельных изменения. Первое снижает смешивание части состояния между группами вкладок. Оно не ограничивает CA и не мешает MITM.
Любой новый trust anchor увеличивает поверхность доверия. Если соответствующий закрытый ключ скомпрометирован, CA ошибочно выдаёт сертификат или пользователь устанавливает подменённый APK, последствия могут затронуть сайты, попадающие под правила. Ограничение по домену уменьшает область применения, но не устраняет эти риски.
В текущем проекте есть ещё несколько практических ограничений:
корни обновляются только вместе с APK; удалённый список не может менять их;
список хостов может устареть, поэтому приложение помечает его после заданного срока;
fallback для .ru и .рф включён по умолчанию и принимает цепочки к встроенным корням даже без записи хоста;
корни и их отпечатки входят в состав релиза; их можно сверить с исходниками, а обновляются они только вместе с APK;
проект не добавляет GOST TLS и не гарантирует работу каждого сайта;
сборка экспериментальная, а проекту нужны независимый аудит и регулярные проверки на физических устройствах.
Поэтому для банковских операций нужно проверять адрес сайта и предупреждения браузера, не устанавливать APK из зеркал и не считать отсутствие ошибки доказательством безопасности. Сам проект не является рекомендацией использовать эту сборку для финансовых операций.
Исходники, патч, инструкции сборки и APK опубликованы в репозитории [2]. Для первой версии доступен релиз ARM64 [3], включая файл SHA256SUMS. Контрольную сумму следует сверять с файлом из того же релиза, а подпись APK — проверять apksigner.
Важное различие: опубликованный fingerprint сертификата подписи — это отпечаток ключа издателя, а не SHA-256 самого APK. Сверка checksum подтверждает целостность относительно опубликованного файла; она не подтверждает, что доверенный корень в приложении является правильным. Для этого нужны независимая сверка сертификатов и аудит кода.
Основа проекта — Firefox/Fenix 160.0a1, Android 8+, ABI arm64-v8a. Это независимый форк: Mozilla его не выпускает и не одобряет. Подробности реализации и известные ограничения перечислены в README.
Практический результат — ещё один вариант для сайтов, которые раньше не проходили проверку цепочки в мобильном Firefox. Теперь можно посмотреть, какое правило сработало, где лежит патч и какие ограничения у решения. Но технически это не «закрытие проблемы MITM». Это осознанное добавление доверия к ещё одному корневому CA для ограниченной группы соединений, с отдельным fallback-правилом и всеми рисками такой модели.
Мне хотелось, чтобы ответ на вопрос «почему браузер этому сертификату доверяет?» можно было найти в патче, конфигурации и релизе. Следующий полезный шаг для проекта — независимая проверка корневых сертификатов, логики проверки цепочки и соответствия опубликованного APK исходникам.
Материалы: исходный код [2] · патч Gecko [4] · релиз APK [3] · RFC 5280 [1]
Автор: PuFFeG
Источник [5]
Сайт-источник PVSM.RU: https://www.pvsm.ru
Путь до страницы источника: https://www.pvsm.ru/open-source/460941
Ссылки в тексте:
[1] RFC 5280: https://www.rfc-editor.org/rfc/rfc5280.html
[2] репозитории: https://github.com/PuFFeG/matreshka-browser
[3] релиз ARM64: https://github.com/PuFFeG/matreshka-browser/releases/tag/v160.0a1
[4] патч Gecko: https://github.com/PuFFeG/matreshka-browser/blob/main/patches/core/matreshka-trust.patch
[5] Источник: https://habr.com/ru/articles/1099568/?utm_source=habrahabr&utm_medium=rss&utm_campaign=1099568
Нажмите здесь для печати.