3P by neo 8달전 | favorite | 댓글 1개

HTTP/2 CONTINUATION Flood 취약점: 기술적 세부 사항

  • CONTINUATION Flood는 여러 HTTP/2 프로토콜 구현에서 발견된 취약점 범주로, Rapid Reset 공격보다 더 심각한 위협을 제기함.
  • 공격으로 인한 결과는 서버 충돌부터 성능 저하에 이르기까지 다양하며, 공격 요청은 HTTP 접근 로그에 나타나지 않음.

서문

  • 2023년 10월 HTTP/2 Rapid Reset 공격에 대해 알게 되었고, HTTP/2에 대한 보안 분석 관점에서 연구를 시작하기로 결정함.

HTTP/2에 대한 간단한 소개

  • HTTP/1.1과 HTTP/2의 주요 차이점은 후자가 이진 프로토콜이며, 클라이언트와 서버가 텍스트 라인 대신 _프레임_을 교환한다는 것임.
  • HEADERS 프레임과 CONTINUATION 프레임에 대한 설명이 필요함.

HEADERS 프레임

  • HEADERS 프레임은 요청과 응답의 HTTP 헤더를 전송하는 데 사용되며, HPACK 인코딩 알고리즘을 사용하여 헤더 데이터를 압축함.
  • 프레임에는 END_HEADERSEND_STREAM과 같은 플래그가 설정될 수 있음.

CONTINUATION 프레임

  • CONTINUATION 프레임은 HEADERS 프레임과 매우 유사하지만 END_HEADERS 플래그만 가지며, 이 플래그가 설정되면 헤더 스트림이 끝났음을 의미함.

CONTINUATION Flood 취약점

  • 클라이언트가 새로운 HTTP/2 스트림을 시작하고 HEADERSCONTINUATION 프레임을 보내지만 END_HEADERS 플래그가 절대 설정되지 않는 경우, 서버는 무한한 헤더 스트림을 분석하고 메모리에 저장해야 함.
  • HTTP/1.1에서는 헤더 크기 제한과 요청/헤더 타임아웃으로 무한 헤더로부터 보호되지만, 많은 HTTP/2 서버에서 이러한 보호 조치가 누락되거나 잘못 구현되었음.

CPU 소모: Golang 사례

  • Golang은 CONTINUATION Flood로 인한 CPU 소모의 예로, http2MetaHeadersFrame이라는 추상 클래스를 사용하여 HEADERS 프레임과 CONTINUATION 프레임을 처리함.
  • HPACK 디코더는 헤더 크기 제한에 도달하면 헤더 방출을 중단하도록 설정되어 있지만, END_HEADERS 플래그가 없으면 함수가 반환되지 않고 계속 헤더를 디코딩함.

메모리 부족

  • 메모리 부족은 가장 심각한 케이스 중 하나로, CONTINUATION 프레임을 사용하여 구축된 헤더 목록의 크기를 제한하지 않는 구현이 있음.
  • 헤더 타임아웃이 없는 구현에서는 단일 HTTP/2 연결만으로 서버를 충돌시킬 수 있음.

달성 가능한 단언문 충돌: Node.js (특별한 경우)

  • Node.js는 CONTINUATION 프레임의 무한 스트림을 적절히 처리하지만, 헤더 스트림 도중 연결이 끊어질 때 데이터 경쟁 버그가 발생함.
  • Node.js는 Http2Session 소멸자 내에서 메모리 할당을 추적하고, 연결이 끊어질 때 current_nghttp2_memory_ 값이 동시에 업데이트되어 충돌이 발생할 수 있음.

이전 HTTP/2 취약점과의 비교

  • 과거에는 여러 HTTP/2 취약점이 보고되었으며, CONTINUATION Flood는 이전 취약점들과 다른 방식으로 작동함.
  • CONTINUATION Flood는 비어 있는 헤더를 보내는 대신 서버에 의해 설정된 프레임 크기 제한까지 많은 임의의 헤더를 보냄.

최종 비고

  • HTTP/2 트래픽은 모든 인간 HTTP 트래픽의 약 60%를 차지하며, 영향을 받는 프로젝트의 중요성을 고려할 때 인터넷의 상당 부분이 쉽게 악용될 수 있는 취약점에 영향을 받았음.
  • 이 취약점이 야생에서 악용되었다면, 서버 관리자가 적절한 HTTP/2 지식 없이는 디버깅하기 매우 어려웠을 것임.

GN⁺의 의견

  • 이 취약점은 서버의 가용성을 심각하게 저해할 수 있으며, 특히 로그에 기록되지 않기 때문에 추적과 대응이 어려움.
  • 서버 관리자는 정기적으로 보안 업데이트를 적용하고, 트래픽 분석 도구를 사용하여 비정상적인 패턴을 감지해야 함.
  • 이러한 취약점은 사이버 보안 커뮤니티에 경각심을 일으키고, 보다 안전한 프로토콜 설계와 구현의 중요성을 강조함.
  • 비판적으로 볼 때, 이 취약점은 널리 사용되는 프로토콜의 기본 설계 결함을 드러내며, 이는 인터넷의 기본 인프라에 대한 신뢰성 문제를 제기함.
  • 관련 분야의 지식을 가진 전문가가 아니라면, 이와 같은 복잡한 취약점을 이해하고 대응하는 것이 어려울 수 있으므로, 보안 교육과 인식 향상이 필요함.
Hacker News 의견
  • 해당 이슈를 최근에 Bandit에서 해결함

    • 한 달 전 Bandit에서 같은 문제를 해결했다는 개인적인 경험.
    • 링크를 통해 구체적인 코드 위치 제공.
    • 구현자의 관점에서 이 문제는 매우 명백하며, 다른 구현체들도 이미 방어책을 마련했을 것으로 생각했음.
    • 그러나 수십 개의 구현체를 확인한 결과, 심지어 주요 HTTP/2 서버들에서도 이러한 보호 장치가 없거나 잘못 구현되어 있었음.
  • 개발 문화에 대한 비판

    • 개발자들이 자동으로 동적으로 확장되는 것에 너무 익숙해져서, 어떤 것이 얼마나 커질 수 있는지에 대해 생각하지 않는 문화가 문제라고 지적.
    • 이러한 문제는 HTTP/2에만 국한되지 않지만, HTTP/2의 복잡성이 문제를 더욱 악화시킬 수 있음.
    • 과거 HTTP/1.x 시절에는 C 같은 언어를 사용하며 버퍼 길이 관리에 지속적인 주의가 필요했고, 요청 헤더 할당을 무한정 확장하는 일은 없었음.
  • 영향을 받지 않는 서버/리버스 프록시 목록

    • 이전 기사에서 언급된 영향을 받지 않는 웹 서버 및 리버스 프록시 목록.
    • Nginx, Jetty, HAProxy, NetScaler, Varnish 등이 영향을 받지 않음.
  • HTTP/1.1의 안전성에 대한 고민

    • 저희 사이트가 하루 종일 주목을 받았다고 언급.
    • 저희 사이트의 트래픽이 적은 경우, HTTP/1.1을 사용하는 것이 더 안전한지에 대한 의문 제기.
  • 저자에 대한 칭찬

    • 저자가 넓은 시야로 접근하고, 발견한 내용을 책임감 있게 보고하며, 읽기 쉬운 방식으로 공유한 것에 대한 칭찬.
  • Slowloris v2에 대한 언급

    • 이 문제를 천천히 발생시키면 'slowloris v2'라고 부를 수 있을 것이라는 농담.
  • 오타에 대한 언급

    • 'serveral retries'라는 오타를 재미있어 함.
  • HTTP/2에 대한 비판적인 시각

    • HTTP/2를 어떻게 애플리케이션 계층 프로토콜에 '업그레이드'를 위한 전송 계층으로 밀어넣을 수 있는지에 대한 비판.