배경
CDN 및 클라우드 공급업체는 인터넷에서 대량의 트래픽을 전송하고 광범위한 모니터링 도구를 사용하여 성능과 안정성을 보장합니다. 여기에는 네트워크, 서버, 응용 프로그램 등 다양한 트래픽 전달 계층을 포괄하는 도구가 포함됩니다. TCP/IP는 이 트래픽의 대부분을 차지합니다(UDP 기반 QUIC는 세계적으로 증가하고 있지만 TCP에 비해 여전히 전체 트래픽의 일부입니다).
소켓은 데이터가 전송되는 클라이언트와 서버 연결을 연결하는 운영 체제 추상화입니다. 따라서 네트워크 문제는 각 소켓에 저장된 데이터에 직접 반영됩니다. 예를 들어 네트워크 정체가 발생하면 응답 시간이 느려지고 RTT(왕복 시간)가 증가할 수 있습니다. 또한 네트워크 대역폭을 사용할 수 있지만 응용 프로그램이 너무 많은 요청으로 인해 과부하가 발생하여 사용 가능한 대역폭을 충분히 활용하기에 충분한 데이터로 버퍼를 채울 수 없어 응용 프로그램에 제한적인 이상이 발생할 수 있습니다. 서버가 여러 소켓을 동시에 처리하는 경우가 많기 때문에 리소스 경합이 발생하여 CPU 및 메모리와 같은 시스템 리소스에 부담이 가해질 수 있습니다.
따라서 TCP 소켓의 성능을 대규모로 모니터링하면 느린 응답 시간이나 연결 끊김 같은 트래픽 동작에 대한 중요한 이해를 얻을 수 있으며 개선이 가능한 경우를 식별할 수 있습니다.
기존 도구
Linux의 “ss” 유틸리티는 소켓 통계를 얻는 데 사용되는 일반적인 도구입니다. “netstat”과 유사하게, ss는 소켓 상태, 프로토콜 및 주소에 대한 필터를 허용함으로써 정보를 얻는 더 빠르고 유연한 메커니즘을 제공합니다. 우리는 ss로도 소켓 모니터링 여정을 시작했습니다. 소켓과 관련 메트릭의 목록을 빠르게 얻을 수 있는 강력한 도구이지만, ss의 주요 과제는 소켓이 많은 시스템에서 사용할 경우 상당한 리소스를 소비할 수 있다는 점입니다. 이로 인해 시스템 성능에 영향을 미치고 다른 프로세스의 속도가 느려질 수 있습니다. 또한 ss 출력은 일관성이 없는 키, 즉 값 사용량으로 인해 구문 분석에 적합하지 않으며 수천 대의 서버에서 수집된 데이터를 스트리밍하는 기능을 상당히 복잡하게 만듭니다.
ss를 사용한 소켓 수집의 첫 번째 버전은 선택한 캐시 서버에서 실행되는 bash 스크립트였으며 “ss –tcp –info”의 출력을 파일로 내보냅니다. 그런 다음 이 파일은 파이썬 스크립트가 이를 읽고 구문 분석하여 Elasticsearch에 삽입하는 방호 호스트에 rsync-ed 됩니다. 이것은 일을 끝냈지만 우리가 필요로하는 규모에 근접하지 않았습니다. 이 작업의 다음 반복은 HTTP 인터페이스에서 호출되는 캐시 서버에 파이썬 스크립트를 라이브 상태로 두고 집계된 통계를 다시 반환하여 Elasticsearch 클러스터에 삽입하는 것이었습니다. 이 방법은 중앙 백오피스 위치에서 개별 캐시 서버로 구문 분석 병목 현상을 확장했지만 소켓 수가 상당히 많은 서버에서 메모리 사용률이 높아졌습니다. 궁극적으로, 우리는 시스템의 ss 부분에 대한 경량 교체의 필요성을 인식했습니다.
이 새로운 툴에 대한 주요 요구 사항은 가볍고 CDN 서버에 있는 많은 소켓에 맞게 확장할 수 있어야 하며 프로토콜 버퍼와 같은 효율적인 메커니즘을 사용하여 데이터를 다시 스트리밍할 수 있어야 한다는 것입니다. MeasurementLab의 TCP-info 도구는 Golang에서 구현된 훌륭한 유틸리티입니다. 그러나 시간이 지남에 따라 동일한 소켓을 추적하도록 설계되었습니다. 많은 양의 소켓 연결을 감안할 때, 우리는 개별 소켓을 추적하지 않도록 설계를 선택했습니다. 대신, 각 폴링 루프가 독립적이어서 열린 소켓의 현재 상태에 대한 스냅샷을 제공합니다. 여기서의 주요 목표는 개별 소켓이 아닌 시스템의 전반적인 성능을 추적하는 것입니다.
xTCP
이러한 과제를 해결하기 위해, 우리는 오픈 소스 xTCP (추출, 내보내기, X 레이 TCP)를 소개합니다. xTCP는 소켓 데이터를 대규모로 캡처하고 스트리밍하는 Golang 유틸리티입니다. xTCP는 Netlink를 사용하여 소켓 정보를 캡처하고 데이터를 프로토버프에 패키징한 다음 UDP 포트(카프카로 전송될 예정)를 통해 전송하거나 NSQ에 씁니다.
NetLink는 사용자 공간과 커널 공간 간의 통신을 위한 일반 인터페이스를 제공합니다. 소켓 모니터링 도구 ss, tcp-info는 Netlink 프로토콜 제품군의 일부인 NetLink_inet_DIAG를 사용하여 커널에서 사용자 공간으로 소켓 정보를 가져옵니다(man 페이지에서 참고: NetLink_inet_DIAG는 Linux 2.6.14에 도입되었으며 AF_inet 및 AF_inet6 소켓만 지원됩니다. Linux 3.3에서는 NetLink_sock_DIAG로 이름이 변경되었으며 AF_UNIX 소켓을 지원하도록 확장되었습니다.)
xTCP는 커널 TCP inet_DIAG 데이터를 빠른 속도로 추출하고 프로토버프를 통해 해당 데이터를 내보냅니다. 약 120k 소켓이 있는 시스템에서 Netlink 메시지는 약 5-6MB이지만 ss의 ASCII 출력은 약 60MB입니다. 또한 ss는 기본적으로 커널에서 ~3KB 청크 단위로 읽습니다. XTCP는 32KB 청크를 읽어 시스템 호출을 최소화합니다. xTCP는 여러 작업자를 사용하여 Netlink 소켓 데이터를 동시에 읽어 큐를 가능한 한 빨리 비우고 동시에 스트리밍을 위해 Netlink 메시지를 구문 분석합니다. 이러한 모든 최적화는 xTCP의 설치 공간을 운영 캐시 서버에서 실행하기에 더 작게 만듭니다.
Edgio에서 사용
클라이언트 성능을 분석하기 위해 xTCP 데이터를 많이 사용합니다. 일반적으로 RTT를 추적하고 POP(Point of Presence) 및 ASN으로 집계된 재전송을 수행합니다.
에이징 속도와 달리 TTL을 사용하면 특정 항목의 캐시 기능을 변경할 수 있습니다. TTL 함수를 사용하여 설정한 기간 동안 항목이 디스크에 있는 동안에는 노후화되지 않으므로 제거될 가능성은 거의 없습니다. TTL이 만료된 후에는 기존 LRU 방식이나 Fast aging 또는 Slow Aging(운용자의 설정 방법에 따라 다름)으로 아이템의 에이징을 시작할 수 있다. 아래 그림에서 에이징이 느린 TTL은 캐시 제거 임계값을 초과하지 않는 지점까지 디스크에 항목을 유지했습니다. 반대편에서 TTL은 라이브 비디오 스트림이 적어도 이벤트 기간 동안 캐시되었지만 그 후에는 빠른 에이징을 사용하여 디스크에서 빠르게 제거되었습니다.
미국의 대형 공급업체에 대한 POP AGA 및 CHB에 대해 샘플링된 소켓 개수, RTT, 재전송 및 RTTCP 대시보드의 예입니다.
이전 블로그 게시물에서는 성능이 저하되고 BBR 메커니즘이 가장 유용하다고 판단되는 고객을 위해 BBR을 자동으로 활성화하기 위한 동적 혼잡 제어 튜닝을 위한 파이프라인을 발표했습니다. xTCP 데이터가 분석의 주요 소스입니다.
우리는 정체의 영향과 같은 복잡한 질문에 답하기 위해 xTCP 데이터를 사용하는 새로운 방법과 성능을 예측하고 이상 현상을 탐지하기 위한 머신 러닝을 끊임없이 찾고 있습니다. 우리는 향후 블로그 게시물에서 소켓 데이터 분석에 대한보고 할 계획입니다.
현재 xTCP는 오픈 소스 네트워크 모니터링 도구 제품군의 vFlow(sFlow, NetFlow, IPFIX Collector)에 합류하고 있습니다. 이 솔루션이 소켓 데이터 수집을 위한 인프라 성능 모니터링 커뮤니티에 도움이 되기를 바라며 이 툴을 더욱 발전시키는 데 적극적으로 참여하기를 기대합니다.
승인
xTCP의 성공과 폭넓은 사용성은 Edgio의 개인과 팀이 기여한 결과입니다. 특히 xTCP의 초기 개발자인 David Seddon에게 감사드립니다. xTCP에 대한 테스트, 인제스팅, 대시보드 및 피드백을 제공해 주신 모든 내부 코드 검토자 및 기고자에게 특별한 감사를 드립니다.