Linux

19 개의 포스트

datadog원문

.NET 연속 프로파일러: CPU 및 월 타임 프로파일링 (새 탭에서 열림)

Datadog의 .NET 컨티뉴어스 프로파일러는 CPU 사용량과 Wall Time(실행 시간)을 효과적으로 수집하기 위해 저수준 스레드 샘플링 방식을 채택하고 있습니다. 운영 환경의 부하를 최소화하면서도 정확한 데이터를 확보하기 위해 관리되는 스레드(Managed Threads)를 정밀하게 추적하며, 가비지 컬렉션(GC)과 같은 네이티브 스레드의 영향까지 함께 분석합니다. 이를 통해 개발자는 연산 집약적인 코드뿐만 아니라 I/O 대기 등으로 인한 지연 원인까지 심층적으로 파악할 수 있습니다. ### CPU와 Wall Time 프로파일링의 개념적 차이 * **CPU 프로파일링**: 스레드가 CPU 코어에서 실제로 실행되는 동안 소모한 사이클을 측정하여 연산량이 많은 코드 블록을 찾는 데 집중합니다. * **Wall Time 프로파일링**: I/O 대기나 락(Lock) 경합 등 스레드가 중단된 시간까지 포함하여 메서드 실행에 걸린 전체 시간을 측정하며, 요청 지연의 근본 원인을 파악하는 데 유용합니다. * **샘플링 방식 채택**: ETW(Windows)나 perf(Linux) 같은 도구는 높은 권한과 시스템 부하 문제로 운영 환경에 부적합하므로, 특정 주기로 스레드 스택을 관찰하는 샘플링 방식을 사용하여 성능 영향을 최소화합니다. ### 효율적인 스레드 모니터링 구조 * **관리되는 스레드 추적**: `ICorProfilerCallback`의 메서드들을 활용해 .NET 런타임이 관리하는 스레드의 생성 및 파괴를 실시간으로 모니터링하고 `ManagedThreadList`에 보관합니다. * **네이티브 스레드 오탐 방지**: 초기 구현에서는 C#을 사용했으나, 네이티브 스레드가 관리되는 메서드를 호출할 때 발생하는 예외적인 상황을 방지하기 위해 전체 구조를 C++로 작성하여 프로파일러 자체 스레드가 샘플링되는 문제를 해결했습니다. * **공용 익스포터 활용**: 수집된 샘플 데이터는 Rust로 작성된 고성능 익스포터를 통해 Datadog 백엔드로 전송되며, 이 모듈은 PHP, Ruby 등 다른 언어 프로파일러와 공유되어 안정성을 확보했습니다. ### OS 수준의 CPU 프로파일링 최적화 * **상태 확인 메커니즘**: 10ms마다 실행 가능한 스레드를 검사하며, Windows는 `NtQueryInformationThread`를, Linux는 `/proc/self/task/<tid>/stat` 파일을 파싱하여 CPU 소비량을 확인합니다. * **저수준 C 구현을 통한 성능 개선**: Linux 환경에서 `std::ifstream` 등 고수준 C++ 클래스를 사용할 때 발생하는 메모리 할당 오버헤드를 줄이기 위해, 할당이 없는 저수준 C API로 교체하여 전체 메모리 할당량의 8%와 CPU 사용량의 2%를 절감했습니다. * **GC 스레드 가시화**: .NET 5 이상의 환경에서는 프로파일링 API가 감지하지 못하는 서버 GC 및 배경 GC 스레드의 CPU 소비량을 별도로 계산하여 플레임 그래프에 표시함으로써 성능 간섭 현상을 명확히 보여줍니다. ### 분산 추적과 연동된 Wall Time 분석 * **Code Hotspots 기능**: 분산 트레이서와 연동하여 특정 요청(Span)을 처리 중인 스레드를 우선적으로 샘플링하며, 이를 통해 느린 요청의 원인이 되는 코드 경로를 정확히 짚어냅니다. * **P/Invoke 비용 최소화**: 트레이서가 프로파일러를 호출할 때 발생하는 오버헤드를 줄이기 위해, 스팬 ID가 기록되는 메모리 위치를 직접 공유하여 추가적인 API 호출 없이 데이터를 실시간으로 읽어옵니다. * **동적 샘플링**: 실행 중인 스레드가 많아질수록 샘플링 간격을 조절하여 데이터의 정확도와 시스템 부하 사이의 균형을 유지합니다. 이 프로파일러는 고성능 환경에서 안정적으로 동작하기 위해 C++와 Rust를 기반으로 저수준 OS API를 직접 제어하도록 설계되었습니다. 특히 Linux 환경에서의 파일 파싱 최적화나 트레이서와의 메모리 공유 방식은 대규모 트래픽을 처리하는 서비스에서 프로파일러 자체의 오버헤드를 극단적으로 줄여야 하는 개발자들에게 유용한 참고 사례가 됩니다.

datadog원문

Dirty Pipe 취약점을 이용한 컨 (새 탭에서 열림)

리눅스 커널에서 발견된 Dirty Pipe 취약점은 권한이 없는 프로세스가 읽기 권한만 가진 파일에 데이터를 쓸 수 있게 허용하며, 이를 통해 컨테이너 환경에서 호스트 시스템의 루트 권한을 탈취할 수 있는 심각한 위협을 초래합니다. 특히 Kubernetes 환경에서 널리 쓰이는 컨테이너 런타임인 runC의 실행 바이너리를 페이지 캐시 수준에서 변조함으로써, 격리된 컨테이너를 탈출하여 호스트 시스템을 완전히 장악하는 시나리오가 가능합니다. 본 글에서는 이 취약점의 기술적 배경과 함께 실제 컨테이너 탈출이 이루어지는 공격 메커니즘을 상세히 설명합니다. **컨테이너 런타임과 runC의 구조적 취약성** - Kubernetes는 containerd나 CRI-O 같은 런타임을 통해 컨테이너를 관리하며, 실제 프로세스 생성은 OCI 규격을 준수하는 하위 레벨 런타임인 runC가 담당합니다. - runC는 컨테이너 내부 프로세스를 실행할 때 자신을 포크(fork)한 뒤 `execve` 시스템 콜을 호출하는데, 이때 `/proc/self/exe` 경로를 통해 호스트에 있는 runC 이진 파일에 대한 파일 서술자(File Descriptor)를 열어두게 됩니다. - 과거 CVE-2019-5736 취약점에 대한 대응으로 runC를 읽기 전용으로 마운트하는 방어책이 도입되었으나, Dirty Pipe는 커널의 페이지 캐시를 직접 수정하므로 이러한 파일 시스템 수준의 권한 제한을 무력화합니다. **Dirty Pipe를 이용한 컨테이너 탈출 과정** - 공격자는 먼저 취약한 웹 애플리케이션 등을 통해 권한이 제한된 일반 컨테이너에 침투한 뒤, 호스트의 runC 바이너리가 실행되기를 대기합니다. - 관리자가 `kubectl exec`와 같은 명령을 수행하여 컨테이너 내부에서 runC가 구동되는 순간, 공격 프로세스는 `/proc/<runC-pid>/exe`를 통해 호스트의 runC 실행 파일에 접근합니다. - Dirty Pipe 공격 프리미티브를 활용하여 페이지 캐시에 로드된 runC 바이너리 내용을 공격자의 악성 ELF 코드로 덮어씁니다. - 이렇게 변조된 runC는 호스트의 루트 권한으로 실행되므로, 공격자는 호스트 시스템에서 임의의 명령(예: 호스트 이름 확인, 루트 권한 쉘 실행 등)을 수행하며 컨테이너 격리를 완전히 무너뜨립니다. **메모리 기반 공격의 비영구적 특성** - Dirty Pipe를 통한 바이너리 변조는 디스크의 실제 파일을 직접 수정하는 것이 아니라 커널의 페이지 캐시 내에서 발생합니다. - 따라서 공격으로 인한 변조는 시스템이 재부팅되거나 커널 캐시가 드롭(drop)되기 전까지만 유지되는 비영구적 특성을 가집니다. - 하지만 단 한 번의 실행만으로도 호스트에 백도어를 설치하거나 권한을 상승시키기에 충분하므로 그 위험성은 매우 높습니다. Dirty Pipe 취약점은 리눅스 커널 수준의 결함이므로 이를 근본적으로 해결하기 위해서는 최신 보안 패치가 적용된 커널로 신속히 업데이트해야 합니다. 또한 컨테이너 환경에서는 최소 권한 원칙을 철저히 준수하고, 런타임 보안 모니터링 도구를 도입하여 `/proc` 파일 시스템에 대한 의심스러운 접근이나 시스템 이진 파일의 비정상적인 동작을 실시간으로 감지하고 차단하는 방어 전략이 필요합니다.

datadog원문

Go 1.18의 프로파일링 개선 사항 (새 탭에서 열림)

Go 1.18은 제네릭과 퍼징(Fuzzing) 외에도 프로파일링 측면에서 비약적인 발전을 이루었으며, 특히 리눅스 환경에서의 CPU 프로파일링 정확도를 획기적으로 개선했습니다. 기존 버전에서 멀티코어 시스템의 CPU 사용량을 실제보다 낮게 측정하던 고질적인 버그를 해결하고, 프로파일러 레이블(pprof labels)의 신뢰성을 높인 것이 핵심입니다. 이러한 변화 덕분에 개발자들은 고부하 분산 시스템에서도 더욱 정밀하게 성능 병목 지점을 파악할 수 있게 되었습니다. ### 리눅스 CPU 프로파일링의 정확도 향상 * **기존 방식의 한계**: Go 1.17까지는 `setitimer(2)` 시스템 콜을 사용하여 10ms마다 `SIGPROF` 신호를 발생시켰으나, POSIX 신호의 특성상 큐에 쌓이지 않아 신호가 처리되기 전 다른 신호가 오면 유실되는 문제가 있었습니다. * **멀티코어에서의 과소측정**: 커널의 시간 측정 단위인 '지피(jiffy)' 해상도 한계로 인해 여러 코어에서 발생한 신호가 특정 시점에 몰리게 되며, 이 과정에서 대량의 신호가 누락되어 실제 CPU 사용량(예: 20코어)보다 훨씬 적은 수치(예: 2.4코어)만 기록되는 현상이 발생했습니다. * **timer_create(2) 도입**: Go 1.18은 스레드별로 신호를 관리할 수 있는 `timer_create(2)`를 도입하여 신호 유실을 방지했습니다. 이를 통해 멀티코어 시스템에서도 모든 CPU 버스트를 정확하게 포착할 수 있습니다. * **cgo 스레드 대응**: Go 런타임이 생성한 스레드뿐만 아니라 cgo 코드에서 생성된 스레드까지 아우르기 위해 `timer_create(2)`와 `setitimer(2)`를 정교하게 조합하여 구현했습니다. ### 프로파일러 레이블(pprof labels) 버그 수정 * **레이블 누락 문제**: 고루틴에 특정 키/값 쌍을 할당하여 프로파일을 분류할 수 있게 해주는 pprof 레이블이 간혹 스택 트레이스에서 누락되는 현상이 발견되었습니다. * **근본 원인 해결**: CPU 프로파일러가 레이블 정보를 수집할 때 엉뚱한 고루틴 객체를 참조하던 로직을 발견했습니다. 이를 현재 스레드에서 실제로 실행 중인 고루틴(`gp.m.curg`)을 정확히 가리키도록 수정하여 데이터의 일관성을 확보했습니다. * **트레이싱 연동 강화**: 이번 수정을 통해 프로파일링 데이터를 분산 트레이싱(Tracing)과 연결하여 분석하는 작업의 신뢰도가 크게 향상되었습니다. Go 1.18은 고성능 멀티코어 서비스를 운영하는 환경에서 필수적인 업데이트입니다. 특히 리눅스 서버에서 Go 애플리케이션의 성능을 분석할 때 이전 버전보다 훨씬 신뢰할 수 있는 데이터를 제공하므로, CPU 프로파일링 기반의 최적화를 진행 중이라면 즉시 업데이트할 것을 권장합니다.

datadog원문

데이터독에서 솔루션 엔지니어로 일한다는 것 (새 탭에서 열림)

Datadog의 솔루션 엔지니어는 기술적 전문성과 고객 커뮤니케이션 능력을 결합하여 제품의 기술적 문제를 해결하고 발전을 이끄는 핵심적인 가교 역할을 수행합니다. 이들은 고객의 복잡한 기술 요구사항을 해결하는 동시에 내부 개발 팀과의 긴밀한 협업 및 임베딩 프로그램을 통해 지속적으로 기술 역량을 확장해 나갑니다. 결과적으로 솔루션 엔지니어링 직무는 개인의 적성에 따라 순수 엔지니어링, 제품 관리(PM), 또는 세일즈 엔지니어링 등 다양한 커리어 경로로 성장할 수 있는 유연한 토대를 제공합니다. **솔루션 엔지니어의 기술적 업무 범위** * 고객이 제품 사용 중 겪는 다양한 기술적 문제(에이전트 설정, 통합 구성, 대시보드 시각화, 얼럿 버그 등)를 티켓 시스템을 통해 해결합니다. * 단순한 상담을 넘어 직접 소스 코드를 분석하고, 필요에 따라 버그를 수정하거나 기술적 조사를 수행하는 심도 있는 엔지니어링 역량이 요구됩니다. * 고객의 요구를 정확히 이해하기 위해 멀티태스킹 능력을 발휘하며, 리눅스(Linux), 루비(Ruby), SQL 쿼리 등 폭넓은 기술 스택을 활용합니다. **고객 경험과 제품 개선의 연결** * 실시간 채팅과 기술 콜을 통해 고객과 직접 소통하며, 사용자가 필요로 하는 새로운 기능에 대한 피드백을 가장 먼저 수집하여 제품 개선에 기여합니다. * 문제가 즉각 해결되기 어려운 경우 창의적인 단기 우회 방법(Workaround)을 제시하며, 이 과정을 통해 제품의 내부 구조에 대한 깊은 지식을 습득합니다. * 문서화 작업을 통해 내부 지식을 공유하고, 고객이 스스로 문제를 해결할 수 있는 환경을 구축하는 데 동참합니다. **역량 강화를 위한 임베딩 프로그램과 프로젝트** * '임베딩(Embedding)' 제도를 통해 솔루션 엔지니어가 다른 엔지니어링 팀에 2주간 완전히 합류하여 실제 스프린트 업무를 수행하며 내부 설계 방식과 기술적 도전 과제를 경험합니다. * 업무 숙련도가 높아지면 데모 환경 개선이나 내부 프로세스 자동화와 같은 사이드 프로젝트를 주도적으로 수행할 수 있는 권한이 주어집니다. * 개별 엔지니어의 성향에 맞춰 코딩 중심의 프로젝트나 제품 기능 구현 등 커리어 경로를 맞춤형으로 설계할 수 있도록 지원합니다. Datadog의 솔루션 엔지니어 직무는 빠르게 변화하는 기술 환경에서 고객과 직접 소통하며 실질적인 문제를 해결하고 싶은 개발자에게 적합합니다. 기술적 깊이를 더하는 동시에 제품의 비즈니스적 가치를 함께 고민하고 싶은 분들에게 강력히 추천되는 커리어 경로입니다.