x86 리눅스(Linux) 타임스탬프, 30% 더 빠르게!

by DD
1개월 전
조회수 14

저지연 파이프라인(Low-latency Pipeline)에서 타임스탬프(Timestamp) 오버헤드(Overhead)를 줄이기 위한 x86 Linux 환경에서의 최적화 시도

vDSO(Virtual Dynamic Shared Object)를 우회하여 TSC(Timestamp Counter)를 직접 읽는 방식의 자체 타이머 구현

성능 개선(Performance Improvement)을 위해 TSC(Timestamp Counter)를 활용한 타이머 구현 및 캐싱(Caching) 기법 적용

L1/L2 캐시 미스(Cache Miss)로 인한 테일 레이턴시(Tail Latency) 문제와 해결 방안 제시

타임스탬프(Timestamp) 성능 병목 현상 분석

게시물에서는 오픈텔레메트리(OpenTelemetry)를 활용한 저지연 파이프라인(Low-latency Pipeline)에서 타임스탬프(Timestamp)의 성능 저하 문제를 지적한다. 특히, `std::chrono::system_clock::now()`와 `std::chrono::steady_clock::now()`를 사용하여 타임스탬프(Timestamp)를 측정하는 과정에서 46~49ns의 오버헤드(Overhead)가 발생함을 확인했다. 이는 vDSO(Virtual Dynamic Shared Object)를 통한 시스템 콜(System Call) 호출 비용으로, 저지연 환경에서는 치명적인 문제로 이어진다.

TSC(Timestamp Counter)를 활용한 성능 개선

저자는 TSC(Timestamp Counter)를 직접 읽어 vDSO(Virtual Dynamic Shared Object)를 우회하는 방식을 제안한다. TSC(Timestamp Counter)는 CPU 내부에 내장된 64비트 카운터로, 링 전환(Ring Transition) 없이 빠른 시간 측정이 가능하다. rdtsc 명령어를 사용하여 TSC(Timestamp Counter) 값을 읽고, 주파수 추정(Frequency Estimation) 또는 주기 추정(Period Estimation) 방식을 통해 나노초(Nanosecond) 단위로 변환한다. 이 방식을 통해 기존 방식 대비 최대 40%의 성능 향상을 달성했다.

vDSO(Virtual Dynamic Shared Object)를 우회하는 자체 타이머 구현

게시물에서는 vDSO(Virtual Dynamic Shared Object)의 데이터 페이지(Data Page) 레이아웃(Layout)을 활용하여 자체 타이머를 구현하는 방법을 제시한다. getauxval(3) 함수를 통해 vDSO(Virtual Dynamic Shared Object)의 base address를 얻고, 이를 기반으로 vvar page의 주소를 계산하여 접근한다. 이 방식은 TSC(Timestamp Counter) 값을 직접 읽어오는 것과 유사한 성능을 보이며, vDSO(Virtual Dynamic Shared Object) 호출에 따른 오버헤드(Overhead)를 줄여 성능을 향상시킨다. 하지만, vDSO(Virtual Dynamic Shared Object)의 레이아웃 변경에 취약하다는 단점이 존재한다.

캐싱(Caching)을 통한 테일 레이턴시(Tail Latency) 문제 해결

자체 타이머 구현 시 발생하는 테일 레이턴시(Tail Latency) 문제를 해결하기 위해 캐싱(Caching) 기법을 적용한다. vDSO(Virtual Dynamic Shared Object)에서 읽어온 값을 캐싱(Caching)하여, 매번 데이터 페이지(Data Page)에 접근하는 대신 캐시된 값을 사용한다. 또한, TSC(Timestamp Counter) 값을 캐싱(Caching)하여 L1/L2 캐시 미스(Cache Miss)를 줄이고, 성능을 더욱 향상시킨다. 이 방식을 통해 테일 레이턴시(Tail Latency)를 줄이고, 예측 가능한 성능을 확보할 수 있다.

The fastest Linux timestamps