Обнаружение C2-сервера через QUIC: подробное руководство по анализу сетевого трафика

Обнаружение C2-сервера через QUIC: подробное руководство по анализу сетевого трафика

Детальный разбор техник идентификации C2-каналов в QUIC-трафике. Анализ особенностей протокола, паттернов соединений и инструментов мониторинга для ИБ-специалистов.

image

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

Протокол QUIC (RFC 9000) является ярким примером этой тенденции. Вскоре после его появления фреймворк для управления команд и контроля (C2) Merlin с открытым исходным кодом, разработанный Ne0nd0g, добавил поддержку QUIC в качестве канала связи в июле 2018 года. В этом руководстве мы рассмотрим C2 через QUIC с точки зрения охотника за угрозами в сети, чтобы выявить конкретные шаблоны для обнаружения.

Наборы данных, использованные в этом руководстве, доступны для скачивания в конце статьи, где также есть ссылка на репозиторий GitHub, содержащий наш инструмент для анализа.

Контекст работы

Прежде чем углубляться в технические детали QUIC, нам нужно установить контекст. Даже понимание спецификации протокола может помочь нам понять, чего ожидать при анализе трафика, но мы должны помнить, что часто существует разница между "идеальным" и "реальным".

RFC – это спецификации, а не законы. Несмотря на наличие термина "рабочая группа" в их названии, IETF (Инженерный совет Интернета) на самом деле не является спецназом элитных гиков, которые проникают в дома разработчиков, чтобы арестовать их за игнорирование рекомендаций RFC. Разработчики могут и действительно часто отклоняются от предложений, чтобы удовлетворить свои собственные потребности. Особенно если эти разработчики создают программное обеспечение, которое изначально предназначено для обмана.

Рукопожатие QUIC

Мы можем анализировать только то, что видим. В случае с QUIC, если у нас нет возможности расшифровать общение, почти все, что мы можем увидеть, происходит во время рукопожатия.

Чтобы понять рукопожатие QUIC, полезно отталкиваться от чего-то знакомого – трехэтапного рукопожатия TCP и рукопожатия TLS. Хотя это не полная картина, первое важное изменение, о котором можно подумать, заключается в том, что QUIC объединил эти два отдельных рукопожатия в одно. Цель заключалась в том, чтобы в большинстве случаев сократить количество необходимых обменов с трех до одного – см. Изображение 1 ниже.

Изображение 1. Рукопожатие TCP + TLS 1.2 (слева) и рукопожатие QUIC (справа).




Начальные пакеты клиента

Как мы видим справа, рукопожатие QUIC начинается с начального (INIT) пакета от клиента. Этот пакет содержит несколько важных параметров инициализации соединения – см. Изображение 2 ниже.

Изображение 2. Длинный заголовок INIT-пакета клиента содержит несколько важных элементов информации, включая тип пакета (00 – Initial), а также ID клиента и назначения.

Этот начальный пакет также содержит раздел CRYPTO, который включает сообщение Client Hello, традиционно встречающееся в рукопожатиях TLS – см. Изображение 3 ниже.

Изображение 3. INIT-пакет клиента также содержит предложенные параметры, связанные с настройкой TLS.

Стоит упомянуть, что начальные пакеты QUIC были разработаны для предотвращения атак с усилением. Не только каждый пакет должен быть дополнен до как минимум 1200 байт, но они также должны включать поле токена, которое может помочь проверить адрес клиента. Это гарантирует, что ответы сервера не будут непреднамеренно усиливать поддельные запросы от злоумышленников, пытающихся провести DDoS-атаки.

Начальные пакеты сервера

После получения начальных пакетов от клиента сервер отвечает серией пакетов, которые проходят через различные уровни шифрования. Сначала он отправляет свой собственный Initial-пакет, который также содержит параметры инициализации соединения, а также CRYPTO-фреймы, содержащие TLS ServerHello, необходимые для завершения рукопожатия TLS. Этот пакет также включает ACK-фрейм, подтверждающий Initial-пакет клиента – см. Изображение 4 ниже.

Изображение 4. Обзор начального пакета сервера, содержащего как CRYPTO, так и ACK-фреймы.

Сразу после этого сервер отправляет один или несколько Handshake-пакетов, которые представляют собой важный промежуточный этап шифрования. Эти Handshake-пакеты содержат дополнительные CRYPTO-фреймы, несущие сообщения рукопожатия TLS сервера (сертификаты, завершающие сообщения и т.д.), и защищены ключами шифрования уровня Handshake, полученными из Initial-обмена – см. Изображение 5 ниже.

Изображение 5. Второй пакет сервера называется Handshake (Тип пакета 10) и, поскольку он теперь зашифрован, больше не отображает никакой информации в открытом виде.

Завершение рукопожатия

На этом этапе и клиент, и сервер предложили свои наборы параметров соединения и криптографической информации. Значения, которые совпадают, будут использоваться, а те, которые различаются, определяются в соответствии с правилами, указанными в RFC 9000. Например, если клиент и сервер предлагают разные значения максимального времени простоя, протокол автоматически выбирает более короткую продолжительность (RFC 9000, Раздел 10.1).

Рукопожатие завершается, когда обе стороны получили и проверили весь необходимый криптографический материал. Сервер сигнализирует об этом, отправляя клиенту фрейм HANDSHAKE_DONE, после чего клиент считает рукопожатие завершенным. Однако, если мы не предоставим ключи сессии, мы не сможем увидеть этот фрейм, так как он зашифрован и отправлен как 1-RTT пакет (RFC 9000, Раздел 19.20).

Свободный обмен данными

На этом этапе обе стороны могут свободно обмениваться полностью зашифрованными 1-RTT пакетами, содержащими данные приложения. Обратите внимание, что эти пакеты также известны как "защищенные полезные данные" – вы можете думать о них как о "нормальных" пакетах полезной нагрузки в QUIC. Они используются для большинства передач данных после завершения рукопожатия.

Название "1-RTT" происходит от того, что полный цикл обмена (клиент-сервер и обратно) требуется во время рукопожатия, прежде чем эти пакеты могут быть отправлены. Обратите внимание, что 1-RTT пакеты используют упрощенный формат "короткого заголовка", который опускает явное поле типа пакета, как показано на Изображении 6 ниже.

Изображение 6. Поскольку явное поле типа пакета опущено, тип пакета неявно является 1-RTT – наличие короткого заголовка само по себе указывает на то, что это 1-RTT пакет, используемый для передачи данных.

Connection ID

В дополнение к возможности свободного обмена данными в обоих направлениях, после успешного завершения рукопожатия становятся доступны несколько важных возможностей, включая миграцию соединения. Эта функция позволяет конечным точкам изменять свои сетевые параметры (например, IP-адрес или порт), сохраняя при этом соединение, и возможна благодаря одной из ключевых инноваций QUIC – Connection ID.

Connection ID служит основным идентификатором соединения в QUIC, заменяя традиционный 4-кортеж из исходного IP-адреса, исходного порта, IP-адреса назначения и порта назначения. Каждая конечная точка генерирует свой собственный Connection ID, и эти ID обмениваются во время рукопожатия. Когда сетевые параметры изменяются, соединение сохраняется, потому что пакеты отслеживаются по их Connection ID, а не по сетевым адресам.

Прежде чем завершить теоретический раздел, стоит отметить несколько других пакетов и фреймов, которые вы можете встретить при анализе QUIC.

0-RTT пакеты

0-RTT пакеты особенные – они позволяют клиенту отправлять данные на сервер до завершения рукопожатия, по сути, начиная общение сразу. Однако есть загвоздка: это возможно только в том случае, если клиент ранее подключался к серверу и сохранил некоторую информацию от этого соединения. Обратите внимание, что некоторые серверы могут отклонять 0-RTT пакеты, и в этом случае их нужно будет отправить повторно как 1-RTT пакеты.

RETRY пакеты

Пакеты Retry отправляются серверами в особых случаях, когда они хотят получить дополнительное подтверждение адреса клиента перед продолжением соединения. Когда клиент получает пакет Retry, он должен создать новый начальный пакет, включая токен из пакета Retry. Эти пакеты уникальны тем, что они не содержат никаких данных полезной нагрузки или номеров пакетов – они просто несут Connection ID и токен.

Фрейм CONNECTION_CLOSE

Фрейм CONNECTION_CLOSE в QUIC существует в двух вариантах: тип 0x1c для ошибок на уровне транспорта и тип 0x1d для ошибок на уровне приложения. При закрытии соединения конечная точка отправляет этот фрейм в соответствующем типе пакета (Initial, Handshake или 1-RTT) и переходит в состояние закрытия, где она прекращает обработку новых фреймов, но ненадолго продолжает отвечать на входящие пакеты тем же фреймом CONNECTION_CLOSE, чтобы обеспечить надежную доставку.

Мы охватили основную теорию, необходимую для эффективного понимания поведения C2 через QUIC и, следовательно, возможностей обнаружения.

Практический анализ

Настройка

Наша тестовая среда использовала две системы: машину с Windows 11 (10.0.0.4 или 192.168.2.115), на которой запущен агент Merlin, и виртуальную машину Ubuntu 22.04 (24.199.110.233), на которой размещены как сервер Merlin, так и CLI-компоненты.

Мы захватили три отдельных набора данных за 24 часа, изменяя только настройки задержки и джиттера (искажения) между каждым. Мы будем ссылаться на эти наборы данных по следующим меткам на протяжении всего отчета:

  • Короткий (задержка 30 с, искажение 3000 мс),
  • Средний (задержка 90 с, искажение 3000 мс),
  • Длинный (задержка 180 с, искажение 1000 мс).

Давайте начнем с рассмотрения наших результатов в RITA.

Обзор RITA

Ниже мы можем увидеть результаты для наших наборов данных: Короткий (Short) (Изображение 7), Средний (Medium) (Изображение 8) и Длинный (Long) (Изображение 9).

Изображение 7. Результаты RITA для Короткого набора данных.

Изображение 8. Результаты RITA для Среднего набора данных.

Изображение 9. Результаты RITA для Длинного набора данных.

Наиболее поразительное наблюдение заключается в том, что все три соединения, независимо от их настроек задержки, помечены как длительные соединения и получают оценку "Высокая" серьезность. Это происходит потому, что одно и то же QUIC-соединение сохраняется на протяжении всего сеанса. В отличие от других фреймворков C2, таких как HTTPS-маяк Cobalt Strike, которые завершают и восстанавливают соединения между проверками, Merlin поддерживает одно непрерывное QUIC-соединение на всех задержках.

Как мы обсуждали в предыдущем разделе, это одно QUIC-соединение идентифицируется постоянным Connection ID. Хотя эти ID важны для отслеживания соединений, они часто опускаются в заголовках пакетов полезной нагрузки, когда стандартный 4-кортеж (исходный IP, исходный порт, IP назначения, порт назначения) достаточен для маршрутизации пакетов. ID обмениваются во время рукопожатия и сохраняются в состоянии соединения, но не требуются в каждом пакете.

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

Исключением из этого является случай миграции соединения на стороне клиента. Но, поскольку большинство целевых систем обычно являются стационарными рабочими станциями, это не должно быть проблемой. Однако, если мы анализируем потенциальное нарушение портативного хоста, который, как известно, переключает типы соединений, это больше не остается верным.

Wireshark – Максимальный тайм-аут простоя

Одним из загадочных аспектов было то, почему эти соединения никогда не завершались по тайм-ауту, даже с задержками до 3 минут. Хотя QUIC-соединения действительно могут завершаться по тайм-ауту – клиент и сервер согласовывают значение тайм-аута простоя во время рукопожатия – что-то, предположительно, предотвращало это.

Давайте изучим наш захват Wireshark, чтобы понять поведение тайм-аута. Мы начнем с проверки согласованных значений максимального тайм-аута простоя в нашем Среднем наборе данных. Открыв начальный пакет (#3041, Initial-пакет от клиента к серверу), мы найдем эти значения в разделе QUIC IETF > CRYPTO > Client Hello > Extension: quic_transport_parameters, как показано на Изображении 10 ниже.

Изображение 10. Обзор предложенных клиентом параметров QUIC Transport Parameters.

Глядя на max_idle_timeout в пакете клиента выше, мы видим предложенное значение 30000 мс (30 секунд). Как упоминалось ранее, клиент и сервер должны согласовать значение тайм-аута, и если есть расхождение, самое короткое предложенное время становится эффективным тайм-аутом.

Хотя предложенное значение сервера уже зашифровано (в пакете рукопожатия), мы можем вывести его, посмотрев на исходный код Merlin здесь. Соответствующая конфигурация сервера показана на Изображении 11 ниже.

Изображение 11. MaxIdleTimeout определяет предложенный клиентом тайм-аут простоя (см. строку 526)

С сервером, предлагающим 42 месяца, и клиентом, предлагающим 30 секунд, последнее становится эффективным тайм-аутом для этого соединения.

Wireshark – Дельта времени между пакетами полезной нагрузки

Давайте рассмотрим наши пакеты полезной нагрузки, сосредоточившись на временных интервалах (дельта) между последовательными пакетами, как показано на Изображении 12 ниже. Это должно помочь нам понять, почему соединение сохраняется, несмотря на задержки, превышающие период тайм-аута.

Изображение 12. Обзор шаблона времени дельта для 1-RTT пакетов в Среднем наборе данных

Глядя на Изображение 12, мы видим серию из 6 пакетов от клиента к серверу, каждый из которых разделен интервалами примерно в 15 секунд (выделены красными прямоугольниками). Это предполагает, что Merlin разбивает 90-секундную задержку на шесть 15-секундных интервалов. Обратите внимание, что этот же шаблон встречается на протяжении всего файла трассировки.

Мы можем проверить это поведение, изучив наши другие наборы данных – Короткий набор данных с 30-секундной задержкой (Изображение 13) и Длинный набор данных со 180-секундной задержкой (Изображение 14).

Изображение 13. Обзор шаблона времени дельта для 1-RTT пакетов в нашем Коротком наборе данных.

Изображение 14. Обзор шаблона времени дельта для 1-RTT пакетов в нашем Длинном наборе данных.

Глядя на Изображения 13 и 14, мы подтверждаем наш шаблон: Короткий набор данных разбивает свою 30-секундную задержку на 2 интервала по 15 секунд, а Длинный набор данных разбивает свою 180-секундную задержку на 12 интервалов по 15 секунд. Независимо от настроек задержки, QUIC-агент Merlin, похоже, разбивает все общение на интервалы примерно в 15 секунд между пакетами от клиента к серверу. Это последовательное поведение объясняет, как Merlin поддерживает свое соединение, несмотря на задержки, превышающие период тайм-аута.

Хотя этот последовательный шаблон – пакеты, повторяющиеся с точными интервалами в 15 секунд на протяжении всего соединения – может служить сигнатурой для обнаружения, его реализация потребует анализа pcap, поскольку Zeek не сохраняет эти временные дельты. Поэтому давайте сосредоточимся на стратегиях обнаружения с использованием Zeek, который предлагает более практическую ценность для охоты за угрозами в сети.

Zeek – quic.log > uid > conn.log

Начиная с Zeek 6.1.0 (октябрь 2023 года), QUIC-соединения автоматически генерируют записи в quic.log. Файл журнала из нашего Среднего набора данных можно увидеть на Изображении 15 ниже. Для получения подробной информации о параметрах протокола и примерах вывода см. предоставленные ссылки здесь и здесь.

Изображение 15. Обзор quic.log Среднего набора данных.

Quic.log показывает 40 QUIC-соединений в нашем наборе данных, причем наше целевое соединение появляется вверху. Уникальный идентификатор соединения (uid: C2g6dk3BeKeu4IrGhk) – случайно начинающийся с "C2" – может быть использован для поиска дополнительных деталей в conn.log, как показано на Изображении 16.

Изображение 16. Conn.log Zeek для Среднего набора данных

Zeek – conn.log Duration

В этом случае, хотя conn.log предоставляет более детальную информацию о соединении, он не раскрывает ничего значительного сверх того, что уже показал нам RITA. Однако, когда мы расширяем наш поиск в conn.log, чтобы изучить все QUIC-соединения, появляется что-то примечательное – как показано на Изображении 17 ниже.

Изображение 17. Обзор conn.log для всех наших QUIC-соединений.

Очевидно, что продолжительность соединения, созданного Merlin, была значительно больше, чем у любых других соединений, зарегистрированных на этом хосте за тот же период времени. Чтобы лучше визуализировать этот шаблон, мы можем рассмотреть гистограмму с метками соединений на оси Y и логарифмической шкалой продолжительности на оси X, как показано на Изображении 18 ниже.

Изображение 18. Сравнение продолжительности нашего Merlin (оранжевый) со всеми другими QUIC-соединениями, не связанными с Merlin (синий).

Наша гистограмма подчеркивает, как продолжительность соединения Merlin выделяется. В то время как типичные QUIC-соединения в нашем наборе данных варьировались от 2,58 мс до 30,50 с, соединение Merlin сохранялось почти 24 часа. Наиболее поразительно то, что большинство легитимных соединений длились менее одной секунды – обратите внимание на логарифмическую шкалу.

Эта крайняя устойчивость QUIC-соединений кажется сильным индикатором для трафика C2. Однако мы должны отметить, что наша тестовая среда, с ее неиспользуемой целевой системой, может не полностью отражать корпоративные сценарии, где легитимный QUIC-трафик с длительной продолжительностью может быть более распространенным. Чтобы собрать более репрезентативные данные, мы проанализировали QUIC-соединения за 24-часовой период на рабочей станции с активным пользователем и несколькими UDP-сервисами – Изображение 19 ниже.

Изображение 19. Обзор QUIC-соединений (6423), замеченных в более репрезентативном 24-часовом файле трассировки

Распределение показывает, что подавляющее большинство QUIC-соединений кратковременны: 4364 соединения длились менее 0,1 секунды, а 1800 соединений длились от 1 секунды до 1 минуты. Только 9 соединений (0,14% от общего числа) сохранялись более часа, причем самое длинное соединение за 24-часовой период составило 4 часа и 11 минут.

Таким образом, даже в среде с активными пользователями QUIC-соединение, сохраняющееся почти 24 часа, скорее всего, остается необычным. Это имеет интуитивный смысл – типичное поведение рабочей станции генерирует QUIC-соединения, которые естественным образом завершаются из-за тайм-аутов приложений, шаблонов активности пользователей и управления ресурсами браузера.

Таким образом, хотя длительные соединения всегда следует оценивать в контексте, QUIC-соединение, продолжающееся почти 24 часа, заслуживает тщательного расследования, так как предполагает умышленное уклонение от стандартного поведения тайм-аутов. Я считаю, что этот конкретный подход – изучение наиболее устойчивых QUIC-соединений в наборе данных – может служить очень эффективным способом выявления потенциальных C2-соединений через QUIC – по крайней мере, на данный момент.

Вернемся к quic.log, чтобы обсудить один последний потенциальный вектор обнаружения.

Zeek – quic.log History

Возвращаясь к quic.log нашего Среднего набора данных на Изображении 15, Zeek предоставляет несколько других столбцов данных для QUIC-трафика. Особый интерес представляет последний столбец, History, который использует последовательность букв для записи хронологического порядка ключевых сетевых событий – показано на Изображении 20 ниже.

Изображение 20. Буквы в столбце History представляют события соединения, с заглавными буквами, обозначающими события, инициированные клиентом, и строчными – сервером.

Хотя технически они показывают всю историю соединения, эти значения в основном фиксируют события рукопожатия, так как большинство зарегистрированных событий (за исключением, возможно, C/c) происходят во время установления соединения.

Изучая наши наборы данных, Merlin создает характерные шаблоны истории – либо ISishIH, либо ISisIH. Они выделяются по двум причинам: они заметно короче, чем типичные QUIC-истории, и уникально начинаются с одной I, а не с двойной I, наблюдаемой во всех других соединениях во всех трех наборах данных.

После первоначального предположения, что этот сокращенный шаблон рукопожатия может быть связан с возобновлением соединения, я провел тесты с новыми парами хостов и перекомпилированными бинарными файлами – но необычный шаблон сохранился.

Затем я исследовал, может ли это поведение быть связано с конфигурацией по умолчанию модуля QUIC Merlin (quic-go 0.47). Однако тестовая реализация базового gRPC через QUIC с использованием того же модуля создала другой шаблон истории: IIiishZZZH.

Не найдя явных конфигураций рукопожатия в кодовой базе, я исследовал, могут ли необычные настройки QuicConfig Merlin вызывать это поведение как непреднамеренный побочный эффект. Однако даже после корректировки этих настроек для соответствия более традиционным реализациям, характерный шаблон рукопожатия Merlin оставался неизменным.

Как советует буддийская "Притча о ядовитой стреле", если вас поразила ядовитая стрела, жертве не нужно знать, кто выпустил стрелу или по какой причине, чтобы позволить целителю спасти вас от ее воздействия. Или в этом случае нам не нужно знать, что вызывает это необычное рукопожатие или почему, но просто то, что оно действительно необычно и, следовательно, может быть использовано как вектор обнаружения.

Пользовательский анализ на Python

Чтобы проверить этот потенциальный метод обнаружения, я написал скрипт на Python для анализа шаблонов столбца History в наших трех наборах данных Merlin и четырех контрольных наборах данных (без Merlin). Это позволило нам оценить точность обнаружения отпечатка.

Скрипт изучил 433 QUIC-соединения во всех семи наборах данных, причем три набора данных содержали соединения Merlin с 24.199.110.233. Он идентифицировал потенциальные серверы Merlin, ища уникальные шаблоны истории (ISishIH или ISisIH). Результаты этого анализа показаны на Изображении 21 ниже.

Изображение 21. Результаты нашего скрипта на Python, ищущего наличие отпечатка рукопожатия Merlin.

Результаты абсолютно точны, успешно идентифицируя единственное соединение Merlin в каждом экспериментальном наборе данных, не создавая ложных срабатываний в контрольных наборах. Хотя наш объем выборки из 433 соединений в семи наборах данных не является исчерпывающим, этот предварительный анализ предполагает, что уникальный шаблон рукопожатия QUIC Merlin может служить эффективной сигнатурой для обнаружения.

Наше исследование реализации C2 через QUIC в Merlin выявило три различные стратегии обнаружения.

RITA

Используя RITA, мы последовательно обнаруживали активность C2 через QUIC Merlin благодаря его устойчивому шаблону соединения. Это демонстрирует протокольно-независимую силу RITA – независимо от того, идет ли трафик через HTTP/1.1, HTTP/2 или HTTP/3, RITA фокусируется на универсальной характеристике, которая имеет наибольшее значение: продолжительность соединения.

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

Продолжительность, специфичная для QUIC (с использованием conn.log Zeek)

Хотя RITA изучает продолжительность всех протоколов, мы обнаружили дополнительную ценность в анализе продолжительности QUIC-соединений конкретно через conn.log Zeek. Наш анализ показал, что типичные QUIC-соединения длятся всего секунды, а многочасовые соединения крайне редки.

Это делает необычно устойчивые QUIC-соединения еще более заметными. Таким образом, сосредоточившись на продолжительности конкретно в наборе данных, содержащем только QUIC-соединения в вашей сети, можно потенциально идентифицировать C2-соединения через QUIC.

Это связано с тем, что агент Merlin был специально разработан для обеспечения отсутствия тайм-аутов, основываясь на настройках QuicConfig агента – см. Изображение 22 ниже.

Изображение 22. Даже в случае, когда задержка может превышать период тайм-аута простоя, агент Merlin отправит Keep-Alive PING через HTTP/2, чтобы предотвратить тайм-аут

Этот тщательный подход к поддержанию устойчивости, хотя и предназначенный для скрытности, на самом деле делает эти соединения более заметными. Иногда что-то может быть настолько незаметным, что становится заметным – "заметно незаметным", если хотите. Сети и приложения естественным образом испытывают тайм-ауты и сбросы соединений, что означает, что идеальная устойчивость сама по себе является аномалией.

В этом случае, чрезвычайно устойчивое QUIC-соединение, на мой взгляд, является самым надежным способом идентификации активности C2 через QUIC, опосредованной Merlin. По крайней мере, на момент написания. Плохая новость, конечно, заключается в том, что Merlin не потребуется много усилий, чтобы изменить это поведение и воссоздавать это соединение каждые пару часов. В этом случае они будут появляться как новые соединения в Zeek, так как их Connection ID и кортежи изменятся.

Хорошая новость, однако, заключается в том, что, когда дело доходит до RITA, это не имеет значения. RITA идентифицирует эти попытки замаскировать устойчивые соединения и будет суммировать совокупное время между двумя хостами за анализируемый период. Поскольку RITA также указывает службу (quic в данном случае), мы советуем всегда быть начеку в отношении устойчивых соединений через QUIC.

Отпечаток рукопожатия Merlin

Нашим третьим открытием стал характерный сокращенный шаблон рукопожатия Merlin. Этот уникальный отпечаток, видимый в quic.log Zeek, может быть обнаружен с помощью простого сопоставления шаблонов, предоставляя дополнительный метод для идентификации трафика C2 Merlin.

Заключение

Появление новых протоколов, таких как QUIC, продолжает знакомый цикл: злоумышленники ищут новые возможности для эксплуатации, а защитники разрабатывают новые стратегии обнаружения. Наш анализ демонстрирует, что эффективное обнаружение может возникать из протокольно-независимых шаблонов (таких как анализ продолжительности RITA), протокольно-специфического поведения (такого как отпечаток рукопожатия QUIC) и комбинации обоих (такой как анализ продолжительности, специфичный для QUIC).

Исследование подчеркивает важное понимание трафика команд и управления: истинная скрытность заключается не обязательно в минимизации шумного поведения, а в смешивании с легитимным трафиком. Человек, входящий в банк в лыжной маске, возможно, скрыл свою личность, но он почти наверняка привлек нежелательное внимание.

Мы расшифровали формулу идеальной защиты!

Спойлер: она начинается с подписки на наш канал

Введите правильный пароль — подпишитесь!