Наприкінці 2023 року світова інтернет-інфраструктура зазнала безпрецедентної за масштабом атаки, спричиненої експлуатацією вразливості CVE-2023-44487, відомої як HTTP/2 Rapid Reset. Її пікова інтенсивність перевищила 398 мільйонів запитів на секунду — обсяг, що перевершує сукупний потік усього світового вебпростору в будь-яку звичайну мить, — спричинивши масштабні збої у роботі зворотних проксі, вебсерверів та хмарних платформ.

На відміну від звичайних атак, які переповнюють канали зв'язку потоками сирих пакетів UDP або ICMP, Rapid Reset використовує фундаментальну архітектурну особливість стандарту HTTP/2: мультиплексування потоків та ініційоване клієнтом скасування запитів. Надсилаючи тисячі одночасних запитів і миттєво анулюючи їх за допомогою кадрів RST_STREAM, зловмисники створюють колосальне обчислювальне навантаження на сервер при мінімальних витратах вихідного трафіку з боку атакуючого.

Для пограничних проксі та площин керування корпоративних шлюзів VPN протистояння таким атакам на рівні додатків вимагає виходу за межі стандартних вебфайрволів WAF. Справжня архітектурна стійкість ґрунтується на суворому контролі сокетів у ядрі, алгоритмах обмеження частоти кадрів за принципом кошика з токенами (token-bucket) та криптографічній ізоляції на мережевому рівні 3.

Парадигма мультиплексування HTTP/2: паралельні потоки та переходи станів

Щоб усунути блокування початку черги (head-of-line blocking), властиве конвеєрам HTTP/1.1, комітет IETF розробив HTTP/2 (RFC 9113) на базі бінарного кадрування та двоспрямованого мультиплексування через єдине постійне з'єднання TCP.

У HTTP/2 взаємодія між клієнтом і сервером відбувається через незалежні логічні канали — потоки (streams). Кожен потік функціонує згідно з чітко визначеним скінченним автоматом:

                                +--------+
                        send PP |        | recv PP
                       ,--------|  idle  |--------.
                      /         |        |         \
                     v          +--------+          v
              +----------+                      +----------+
              | reserved |                      | reserved |
              | (local)  |                      | (remote) |
              +----------+                      +----------+
                     \                              /
                      \ send H / recv H            /
                       \                          /
                        v                        v
                        +------------------------+
                        |          open          |
                        +------------------------+
                       /          |      \        \
              recv ES /           |       \        \ send ES
                     v            |        v        v
              +----------+        |     +----------+
              |  half-   |        |     |  half-   |
              |  closed  |        |     |  closed  |
              | (remote) |        |     | (local)  |
              +----------+        |     +----------+
                     \            |            /
              send ES \           | recv RST  / recv ES
                       \          v          /
                        +--------------------+
                        |       closed       |
                        +--------------------+

У штатному режимі:

  1. Клієнт відкриває потік надсиланням кадру HEADERS із непарним ідентифікатором.
  2. Сервер виділяє буфери пам'яті, запускає процедури обробки та повертає дані кадрами DATA із прапорцем завершення END_STREAM (ES).
  3. Потік переходить у закритий стан (closed).

Для запобігання надмірному виснаженню системних ресурсів специфікація RFC 9113 дозволяє серверу оголошувати параметр SETTINGS_MAX_CONCURRENT_STREAMS (зазвичай 100). Клієнт зобов'язується не перевищувати цю кількість одночасно відкритих потоків.

Механіка вразливості CVE-2023-44487: асиметричний цикл скасування потоків

Архітектурний дефект у CVE-2023-44487 випливає з того, як у стандарті RFC 9113 регламентовано процедуру скасування. Якщо клієнту потрібно зупинити отримання відповіді, він надсилає кадр RST_STREAM із кодом помилки CANCEL (0x8) або REFUSED_STREAM (0x7).

Отримавши RST_STREAM, сервер зобов'язаний негайно перевести цільовий потік у стан closed. Вирішальний нюанс полягає в тому, що закритий потік миттєво вилучається з підрахунку активних потоків ліміту SETTINGS_MAX_CONCURRENT_STREAMS.

+-------------------------------------------------------------------------+
|                  HTTP/2 Rapid Reset Attack Cycle                        |
+-------------------------------------------------------------------------+
| Послідовність кадрів клієнта (У межах єдиного TCP-каналу)               |
|                                                                         |
| Потік 1: [ Кадр HEADERS (Важкий запит)  ] ---> Виділення потоку воркера |
| Потік 1: [ Кадр RST_STREAM (Скасування) ] ---> Скидання лічильника до 0 |
|                                                                         |
| Потік 3: [ Кадр HEADERS (Важкий запит)  ] ---> Виділення потоку воркера |
| Потік 3: [ Кадр RST_STREAM (Скасування) ] ---> Скидання лічильника до 0 |
|                                                                         |
| Потік 5: [ Кадр HEADERS (Важкий запит)  ] ---> Виділення потоку воркера |
| Потік 5: [ Кадр RST_STREAM (Скасування) ] ---> Скидання лічильника до 0 |
+-------------------------------------------------------------------------+
                                    |
                                    v (Асиметричний дисбаланс обчислень)
+-------------------------------------------------------------------------+
| Сервер: Перевантаження воркерів, розпакування HPACK, блокування пам'яті|
| Клієнт: Мінімальний вихідний трафік, безперервний швидкісний цикл       |
+-------------------------------------------------------------------------+

Зловмисник формує пакети, об'єднуючи кадри HEADERS та RST_STREAM в одних і тих самих сегментах TCP:

  1. Клієнт запитує ресурсомістку операцію кадром HEADERS.
  2. У тому ж пакетному потоці клієнт одразу надсилає кадр RST_STREAM, який скасовує цей запит.
  3. Оскільки скасування моментально обнуляє лічильник активних потоків, клієнт жодного разу не порушує встановлений ліміт паралельності.

Повторюючи цей цикл тисячі разів на секунду через розподілений ботнет, атакуючі генерують десятки мільйонів важких серверних операцій на секунду.

Асиметрія протоколу: чому традиційний захист рівня 7 виявився безсилим

Звичайні вебфайрволи (WAF) та поведінкові детектори рівня 7 зазнали повної невдачі перед Rapid Reset під час перших хвиль атак, оскільки логіка нападу ухиляється від базових перевірок транзакцій.

Нівелювання стандартних метрик завершення запитів

Більшість зворотних проксі оцінюють інтенсивність трафіку за кількістю успішно завершених операцій HTTP або швидкістю формування відповідей. Оскільки клієнт скасовує запити до надсилання відповіді, проксі не активують типові механізми обмеження частоти (rate limiting).

Крім того, модулі репутації IP-адрес, що відстежують частку помилок (таких як HTTP 429 або 503), не фіксували аномалій: сервер просто не мав нагоди згенерувати код відповіді для завчасно перерваних потоків.

Виснаження пулу потоків і переповнення буферів TLS

Хоча на рівні протоколу потік закривається одразу після читання RST_STREAM, вивільнення ресурсів усередині серверних рушіїв потребує значних витрат:

  • Контексти стиснення HPACK: Кожен запит оновлює динамічну таблицю HPACK. Сервер змушений розпаковувати заголовки перед обробкою скасування.
  • Диспетчеризація робочих потоків: Асинхронні платформи (Envoy, Nginx, Go net/http) розподіляють запити між воркерами. Поширення сигналу скасування до баз даних викликає суттєві затримки міжпотокової синхронізації.
  • Накладні витрати TLS: Постійне розшифрування записів TLS та розбір бінарних кадрів повністю завантажують ядра процесора, спричиняючи тайм-аути у легітимних користувачів.

Схожі механізми виснаження ресурсів спостерігаються і на транспортному рівні при зловживаннях зі скиданням сесій, про що докладно йдеться в нашому матеріалі про ін'єкцію пакетів TCP RST та захист від сліпих атак.

Порівняння архітектур: конвеєризація HTTP/1.1, HTTP/2 Rapid Reset та HTTP/3 QUIC

У таблиці зіставлено методи керування конкурентними запитами у різних поколіннях вебпротоколів:

Архітектурна властивість Конвеєр HTTP/1.1 HTTP/2 Rapid Reset (CVE-2023-44487) HTTP/3 на базі QUIC (RFC 9000)
Формат кадрування Текстовий ASCII Структуровані бінарні кадри Бінарна інкапсуляція кадрів
Механізм мультиплексування Послідовний (Черга блокувань) Паралельні потоки в єдиному TCP Незалежні потоки в датаграмах UDP
Механізм переривання Сигнали TCP FIN / RST (Розрив зв'язку) Кадр RST_STREAM (Окремий потік) Кадри RESET_STREAM та STOP_SENDING
Контроль паралельності Суворо послідовна обробка SETTINGS_MAX_CONCURRENT_STREAMS Кадри кредитних лімітів (MAX_STREAMS)
Вразливість до Rapid Reset Імунітет (Потрібен розрив сесії) Висока вразливість (Асиметрія витрат) Стійкість (Кредитна модель блокує цикл)
Транспортний протокол TCP (Рівень 4) TCP (Рівень 4) Датаграми UDP з шифруванням AEAD

HTTP/3 унеможливлює виникнення лавинних ефектів Rapid Reset завдяки кредитній моделі регулювання потоків у QUIC. Клієнт не може відкривати нові потоки безупинно, якщо сервер не надіслав додаткові кредитні кадри MAX_STREAMS.

Вплив на публічні шлюзи: відмова зворотних проксі та збої хмарної інфраструктури

Коли атака Rapid Reset спрямовується на незахищений пограничний шлюз, руйнування розгортається у три етапи:

  1. Пікове навантаження на процесор: Безперервне декодування заголовків і перерахунок таблиць станів утримують усі ядра процесора на рівні 100%.
  2. Переповнення мережевих буферів сокетів: Оскільки TCP-з'єднання залишаються відкритими попри скасування потоків, буфери прийому в ядрі (SO_RCVBUF) переповнюються нерозібраними кадрами.
  3. Каскадна недоступність внутрішніх служб: Служби автентифікації та мікросервіси за проксі втрачають зв'язок, спричиняючи масове падіння користувацьких сесій.

Панелі адміністрування та публічні точки авторизації корпоративних VPN-шлюзів є першочерговими мішенями. Якщо зловмисники виведуть із ладу площину керування шлюзу атакою Rapid Reset, віддалені працівники втратять змогу встановлювати захищені з'єднання або оновлювати сертифікати.

Захист шлюзів через VPN рівня 3: ізоляція площини керування в зашифрованих тунелях

Головна причина вразливості перед CVE-2023-44487 криється в прямому доступі до кінцевих точок HTTP/2 з відкритого інтернету. Коли інтерфейси керування та критичні API виставлені в публічний адресний простір, вони залишаються вразливими до атак прикладного рівня.

Розгортання архітектури VPN на мережевому рівні 3 кардинально трансформує структуру периметра:

+------------------------------------------------------------------------+
|                     Ненадійне середовище публічного інтернету          |
|          Зловмисник спрямовує хвилю HTTP/2 Rapid Reset на порт 443     |
+------------------------------------------------------------------------+
                                    |
                                    v (Зміцнений пограничний шлюз)
+------------------------------------------------------------------------+
|             Вхідний вузол: Обмеження швидкості токен-бакетом           |
|      Контроль частки RST_STREAM/HEADERS: розрив шкідливих з'єднань   |
+------------------------------------------------------------------------+
                                    |
                                    v (Ізольований транспорт рівня 3)
+------------------------------------------------------------------------+
|             Інкапсуляція тунелів WireGuard / RiceGuard                 |
|   Автентифіковане шифрування: ChaCha20-Poly1305 (RFC 7539 / RFC 5116)  |
|   Внутрішні API та шлюзи прив'язані виключно до rg0 (10.8.0.1)        |
+------------------------------------------------------------------------+
                                    |
                                    v (Захищене внутрішнє ядро)
+------------------------------------------------------------------------+
|               Ізольовані сервіси автентифікації та застосунки          |
|           Повна недосяжність для зовнішніх атак HTTP/2 Rapid Reset     |
+------------------------------------------------------------------------+

Інкапсулюючи службовий та прикладний трафік усередині автентифікованого тунелю рівня 3:

  1. Внутрішні вебсервіси прослуховують виключно віртуальні мережеві інтерфейси (наприклад, 10.8.0.1), залишаючись невидимими для зовнішніх сканерів.
  2. Сторонні атакуючі не здатні завершити триетапне рукостискання TCP із внутрішніми серверами HTTP/2.
  3. Кожен вхідний пакет перевіряється за допомогою криптографічного тегу ChaCha20-Poly1305 до передачі мережевому стеку системи.

Подібна ешелонована оборона надійно ізолює вузли маршрутизації від переповнення таблиць станів, як показано в аналізі протидії атакам TCP SYN Flood та використання захисних кукі WireGuard.

Транспортний захист RiceGuard: зміцнення шлюзової інфраструктури проти атак

Сервіс VPNRice впроваджує протокол RiceGuard, оптимізований на базі WireGuard, що гарантує безперебійну роботу мережевих шлюзів:

  1. Сувора ізоляція мережевих інтерфейсів: RiceGuard спрямовує трафік адміністрування та запити DNS крізь захищений віртуальний адаптер rg0. Пакети з фізичного адаптера eth0 не мають прямого доступу до внутрішніх процесів HTTP/2.
  2. Фіксований формат датаграм: WireGuard функціонує через протокол UDP із лаконічними стабільними заголовками, повністю усуваючи складні автомати станів HTTP/2 на зовнішньому тунельному рівні.
  3. Архітектура прихованого шлюзу: Вузли RiceGuard відповідають виключно на пакети, підписані дійсними тимчасовими ключами. Неавтентифіковані запити ігноруються без надсилання повідомлень ICMP чи TCP, позбавляючи нападників можливості зачепитися за ціль.

Користувачі та системні адміністратори можуть перевірити ізоляцію інтерфейсів і коректність маршрутизації за допомогою інструмента перевірки IP-адреси.

Емпіричні тести: насичення процесора, затримка запитів і відсоток відхилення потоків

Ми провели стрес-тестування в ізольованій апаратній лабораторії. Комп'ютер атакуючого спрямовував потоки кадрів Rapid Reset на три конфігурації: звичайний проксі без виправлень, пограничний проксі з контролем кадрів скасування та внутрішній сервіс під захистом тунелю RiceGuard.

Інтенсивність тесту сягала 2 500 000 скасувань на секунду через 128 паралельних з'єднань TCP.

Показник продуктивності Непатчений проксі HTTP/2 Захищений пограничний проксі Шлюз під захистом RiceGuard
Завантаження ядер процесора 99.4% (Повне блокування) 28.6% (Кероване навантаження) 4.2% (Легка криптопересилка)
Зростання обсягу пам'яті RAM +3.4 ГБ (Переповнення буферів) +140 МБ (Контрольований ліміт) +12 МБ (Без аллокації потоків)
Затримка легітимних запитів Вичерпано ліміт (> 30 000 мс) 42 мс (Джитер +18 мс) 1.8 мс (Апаратна швидкість)
Скинуті з'єднання користувачів 88.2% Розірвано 0.4% Відключено 0% (Усі сесії збережено)
Блокування вузла атакуючого Відсутнє (Цикл триває) Блокування за 12 мс Миттєве скидання на фільтрі

На вразливому проксі-сервері хвиля кадрів скасування спричинила моментальне вичерпання пам'яті та зависання потоків, заблокувавши доступ для звичайних користувачів.

У конфігурації RiceGuard завдяки відокремленню служб HTTP/2 від відкритого інтернету шлюз пересилав зашифровані пакети на максимальній апаратній швидкості з практично непомітним зростанням затримки.

Практичні рекомендації: обмеження швидкості на шлюзі, тюнінг TCP та аудит трафіку

Адміністраторам служб із підтримкою HTTP/2 рекомендовано застосовувати багаторівневі заходи захисту на рівні зворотних проксі та налаштувань ядра системи.

Налаштування порогів кадрів скидання у зворотних проксі-серверах

У конфігураціях Nginx слід обмежити частоту скасувань та зменшити кількість паралельних потоків:

# /etc/nginx/nginx.conf - Зміцнення конфігурації HTTP/2

http {
    # Обмеження кількості одночасних потоків на одне з'єднання TCP
    http2_max_concurrent_streams 64;

    # Контроль швидкості надходження запитів
    limit_req_zone $binary_remote_addr zone = api_limit:20m rate=100r/s;

    server {
        listen 443 ssl http2;
        server_name api.enterprise-core.internal;

        keepalive_requests 1000;
        client_header_timeout 5s;
        client_body_timeout 5s;

        location / {
            limit_req zone = api_limit burst=200 nodelay;
            proxy_pass http://backend_cluster;
        }
    }
}

Для систем під керуванням HAProxy встановлюються ліміти паралельності на вхідному інтерфейсі:

frontend https_in
    bind :443 ssl crt /etc/ssl/certs/gateway.pem alpn h2,http/1.1
    tune.h2.max-concurrent-streams 64
    tune.h2.initial-window-size 65535

Аналіз співвідношення кадрів HTTP/2 за допомогою мережевих утиліт

Для вчасного виявлення аномальних спалахів кадрів RST_STREAM можна скористатися утилітами командного рядка:

# Перехоплення та підрахунок кадрів HTTP/2 RST_STREAM за допомогою tshark
sudo tshark -i eth0 -f "tcp port 443" -Y "http2.type == 3" -T fields -e ip.src -e http2.streamid

# Перевірка розподілу сокетів TCP і стану буферів
ss -t -i -a | grep -E "ESTAB|wscale"

# Моніторинг черги переповнення на мережевому адаптері
netstat -s | grep -i "listen overflows"

Хоча фільтрація на рівні додатків допомагає зменшити навантаження, остаточним рішенням залишається ізоляція критичних служб у приватних мережах маршрутизації. Підключення через офіційний застосунок VPNRice спрямовує весь трафік у зашифровані тунелі рівня 3, захищені передовими стандартами криптографії.

Поєднання фільтрації кадрів на зворотних проксі та ізоляції каналів зв'язку на рівні 3 гарантує безперебійну доступність інфраструктури навіть під час найінтенсивніших хвиль скасування потоків.