FoxIO раскрыла три TLS-уязвимости в веб-сервере GoAhead для IoT и OT

FoxIO раскрыла три TLS-уязвимости в веб-сервере GoAhead для IoT и OT

Себастьен Фери (Sébastien Féry) опубликовал в блоге FoxIO 26 октября 2026 года разбор трёх независимых ошибок в том, как встраиваемый веб-сервер GoAhead подключается к TLS-библиотекам. По словам автора, GoAhead используется в сотнях миллионов устройств: маршрутизаторов, коммутаторов, принтеров, шлюзов и промышленных контроллеров. В списке производителей, чьи устройства он называет, Palo Alto Networks, Comcast, D-Link, HP, Canon, Honeywell, GE, Oracle, Siemens, Rockwell, Digi, Lockheed Martin, Boeing и другие. Это перечень мест, где применяется GoAhead, а не утверждение, что продукты этих компаний уязвимы: каждая из ошибок затрагивает лишь часть развёртываний, в зависимости от сборки и настроек.

Первая ошибка (OpenSSL-совместимый бэкенд, критическая, CVSS 9.1, GOAHEAD-SA-2026-0006, CVE-2026-115881). GoAhead загружает список отозванных сертификатов (CRL) в хранилище, но никогда не включает проверку отзыва: флаг X509_V_FLAG_CRL_CHECK не выставляется, и OpenSSL возвращает успех, не заглядывая в список. Поэтому отозванный клиентский сертификат проходит рукопожатие взаимной TLS-аутентификации (mTLS), даже когда включена проверка издателя. При запуске никаких предупреждений нет: загрузка файла проходит успешно. Автор проверил это на GoAhead 6.1.0 с OpenSSL 3.6.2, отозванный сертификат, подписанный доверенным центром, успешно прошёл рукопожатие. Затронуты версии GoAhead с 3.4.5 по 6.1.0 с настроенным CRL. Опаснее всего сочетание VERIFY_PEER=1, доверенного набора CA и VERIFY_ISSUER=1: ранее доверенная, но отозванная учётная запись сохраняет доступ. Если проверка издателя выключена, дефект остаётся, но неизвестные издатели и так принимаются политикой.

Вторая ошибка (Mbed TLS, средняя, CVSS 5.9, GOAHEAD-SA-2026-0005). При настройке 2048-битной группы Диффи, Хеллмана из RFC 3526 через mbedtls_ssl_conf_dh_param_bin() для обоих буферов передана длина sizeof(dhm_g), хотя генератор занимает один байт. Должно быть sizeof(dhm_p), то есть 256 байт. В итоге Mbed TLS читает лишь первый байт модуля (0xFF) и отправляет клиенту в ServerKeyExchange однобайтовый параметр. Возможных значений общего секрета остаётся восемь (01, 02, 04, 08, 10, 20, 40, 80 в шестнадцатеричной записи), и пассивный наблюдатель может перебрать их и расшифровать записанный трафик TLS 1.2 с наборами DHE_RSA. В PoC автору хватило пяти попыток, чтобы воспроизвести секрет, совпавший с клиентским. Условие: клиент должен принять сломанные параметры. Протестированный клиент OpenSSL их отклонил (modulus too small), а вот «разрешающие» клиенты, например самописные или встроенные без проверки минимального размера, расшифровываемую сессию завершат. Сессии ECDHE и TLS 1.3 не затронуты. Затронуты GoAhead с 4.0.2 по 6.1.0; опечатка появилась в 2018 году при переходе на API с бинарными параметрами и пережила рефакторинг TLS в апреле 2024-го. В Mbed TLS 4.x наборы TLS_DHE_* удалены, так что этот путь там не работает.

Третья ошибка (устаревший верификатор LibreSSL, высокая, CVSS 7.4, GOAHEAD-SA-2026-0004, CVE-2026-115884). GoAhead ограничивает глубину цепочки сертификатов десятью (VERIFY_DEPTH), но LibreSSL 3.2.x и 3.3.2-3.3.6 по умолчанию используют старый верификатор X.509, который при построении цепочки обрывает цикл, не фиксируя ошибку глубины (в коде есть комментарий FIXME, с которого автор и начал разбираться с GoAhead). До GoAhead ошибка доходит как код 20 (не найден сертификат издателя), а он допускается при VERIFY_ISSUER=0, тогда как код 22 (цепочка слишком длинная) отвергается. В демонстрации на GoAhead 6.1.0 с LibreSSL 3.3.6 цепочка из 17 сертификатов с корнем в самоподписанном CA злоумышленника прошла рукопожатие, и защищённый ресурс вернул HTTP 200. Тот же код, собранный с LibreSSL 4.3.1, получил ошибку 22 на глубине 10 и отклонил цепочку. Демонстрация шла при VERIFY_PEER=1 и VERIFY_ISSUER=0; при включённом доверии к издателю цепочка отвергается. OpenSSL, BoringSSL, AWS-LC и LibreSSL 4.x этому триггеру не подвержены.

Хронология: об ошибках сообщили разработчикам 22 апреля (LibreSSL), 27 апреля (Mbed TLS) и 30 апреля 2026 года (OpenSSL); GoAhead 6.1.1 с исправлениями вышел 2 августа, бюллетени опубликованы 12 октября, запись в блоге, 26 октября. Код для воспроизведения лежит в репозитории FoxIO-LLC/blog_poc. Для поиска затронутых серверов автор предлагает смотреть в логах JA4S признаки соответствующих наборов шифров (пример отпечатка, t120100_009f_1ca028f07214) и использовать отпечатки JA4Scan-TLS, различающие бэкенды.

Ключевые факты

  • Три независимые ошибки в интеграции GoAhead с TLS-библиотеками: OpenSSL-совместимый бэкенд (критическая, CVSS 9.1), устаревший верификатор LibreSSL (высокая, 7.4), Mbed TLS (средняя, 5.9). Исправления в GoAhead 6.1.1 от 2 августа 2026 года.
  • OpenSSL-бэкенд грузит CRL, но не включает проверку отзыва: отозванные клиентские сертификаты проходят mTLS без предупреждений при запуске (затронуты GoAhead с 3.4.5 по 6.1.0 с настроенным CRL).
  • В Mbed TLS из-за опечатки в длине буфера 2048-битный DH-модуль превращается в один байт: остаётся восемь вариантов общего секрета, и пассивный наблюдатель может расшифровать сессии TLS 1.2 DHE_RSA, если клиент принимает такие параметры.
  • В LibreSSL 3.2.x и 3.3.2-3.3.6 цепочка из 17 сертификатов (при лимите 10) проходит рукопожатие, когда клиентские сертификаты обязательны, а проверка издателя отключена.
  • Уязвимость зависит от сборки и настроек; автор не сообщает об эксплуатации в реальных условиях, а PoC опубликован в репозитории FoxIO.

Почему это важно

GoAhead, по словам автора, стоит в сотнях миллионов устройств: от маршрутизаторов и принтеров до промышленных контроллеров. Ошибки не в самой криптографии, а в «склейке» сервера с TLS-библиотеками, и это тот класс дефектов, который трудно заметить: при запуске нет предупреждений, а рукопожатие просто успешно завершается. Самая тяжёлая из трёх (CVSS 9.1) лишает смысла отзыв клиентских сертификатов: отозванная идентичность сохраняет доступ.

Кому это важно

Производителям и интеграторам устройств на GoAhead, администраторам сетевого и промышленного оборудования с управлением через веб-интерфейс с взаимной TLS-аутентификацией, а также командам безопасности, которые инвентаризируют встраиваемые устройства. Важно помнить, что список компаний в тексте описывает, где применяется GoAhead, и не означает, что продукты именно этих производителей уязвимы.

Как это применить

Исправления есть в GoAhead 6.1.1: после загрузки CRL сервер теперь включает проверку отзыва, а опечатка в длине DH-буфера исправлена. Чтобы понять, касается ли проблема вашего парка, нужно выяснить, какой TLS-бэкенд (OpenSSL, LibreSSL, Mbed TLS) и какие параметры (VERIFY_PEER, VERIFY_ISSUER, настроенный CRL, наборы DHE_RSA) вшиты в сборку. Автор советует искать в логах JA4S отпечатки наборов шифров Mbed TLS с DHE (пример t120100_009f_1ca028f07214) и применять отпечатки JA4Scan-TLS, чтобы находить публично доступные серверы и определять их бэкенд. В тексте не сказано, выпустили ли производители устройств обновлённые прошивки, поэтому это нужно уточнять у них.

Можно ли доверять

Источник, первичный технический разбор автора, обнаружившего ошибки, с фрагментами кода, версиями, результатами тестов и ссылками на бюллетени GOAHEAD-SA-2026-0004, -0005 и -0006 (для 0004 и 0006 указаны номера CVE). Публичный PoC позволяет перепроверить выводы. Оценки CVSS приведены без векторов. Оговорка: это материал FoxIO о собственной находке, а масштаб «сотни миллионов устройств» относится к распространённости GoAhead в целом, а не к числу уязвимых устройств.

Риски и подводные камни

Выраженность риска зависит от конфигурации. Ошибка CRL ощутима при включённой проверке издателя; обход глубины цепочки в LibreSSL, только на старых версиях с отключённой проверкой издателя; расшифровка DH требует клиента, принимающего слабые параметры (протестированный клиент OpenSSL их отверг), а ECDHE и TLS 1.3 не затронуты. Сборки на LibreSSL могут унаследовать сразу две проблемы: дефект CRL и обход глубины. Источник не сообщает об эксплуатации в реальных условиях, поэтому оценивать масштаб реальных атак по тексту нельзя.