본문으로 건너뛰기

[triton] Triton NVIDIA GPU 백엔드: WarpGroupDotWaitOp 최적화 및 동기화 개선

PR 링크: triton-lang/triton#9281 상태: Merged | 변경: +126 / -56

들어가며

Triton의 NVIDIA GPU 백엔드에서 WarpGroupDotWaitOp의 동작을 개선하여 GB200 및 H100 아키텍처에서의 성능을 향상시킨 PR을 분석합니다. 기존 구현에서는 비동기 행렬 곱셈(async dot) 작업 후 공유 메모리 의존성을 보수적으로 처리하기 위해 과도한 배리어를 삽입하는 문제가 있었습니다. 특히 num_warps > 4인 경우, 불필요한 동기화가 발생하여 파이프라인 효율을 저해했습니다. 본 PR은 warpGroupLocal 속성을 도입하여 동기화 범위를 정밀하게 제어함으로써 이 문제를 해결했습니다.

코드 분석

1. IR 정의 변경 (TritonNvidiaGPUOps.td)

WarpGroupDotWaitOpUnitAttr 타입의 warpGroupLocal 속성을 추가했습니다. 이를 통해 컴파일러는 해당 작업이 로컬 워프 그룹 내에서만 동기화가 필요한지 판단할 수 있습니다.

-  let arguments = (ins Variadic<TTG_TensorOrMemDesc>:$inputs, I32Attr:$pendings);
+  let arguments = (ins Variadic<TTG_TensorOrMemDesc>:$inputs, I32Attr:$pendings, UnitAttr:$warpGroupLocal);

2. Membar 분석 로직 개선 (Membar.cpp)

MembarAnalysis에서 로컬 배리어 포함 여부를 판단하는 containsLocalBarrier 함수를 수정했습니다. 이제 WarpGroupDotWaitOpwarpGroupLocal 속성을 가지고 있지 않고 num_warps > 4인 경우에만 배리어를 삽입하도록 조건을 강화했습니다.

+  if (auto wgWait = dyn_cast<ttng::WarpGroupDotWaitOp>(op))
+    return !wgWait.getWarpGroupLocal() && ttg::lookupNumWarps(op) > 4;

3. 파이프라이너 및 유틸리티 업데이트

WGMMAPipeline.cppUtility.cpp에서 WarpGroupDotWaitOp을 생성하는 모든 지점에 새로운 속성을 반영하도록 수정하여, 컴파일러 패스 전반에서 일관된 동작을 보장했습니다.

왜 이게 좋은가

이번 최적화의 핵심은 **'불필요한 동기화의 제거'**입니다. 기존에는 모든 WarpGroupDotWaitOp에 대해 보수적인 배리어가 적용되어, 실제로는 공유 메모리 의존성이 없는 상황에서도 워프들이 대기 상태에 빠지는 병목이 있었습니다.

  • 성능 향상: 내부 벤치마크 결과, GB200 환경에서 여러 커널에 대해 약 2.5%의 성능 향상을 확인했습니다.
  • 교훈: 비동기 연산이 많은 GPU 커널에서는 동기화 범위를 최소화하는 것이 중요합니다. 특히 num_warps가 큰 경우, 전역적인 배리어보다는 로컬 그룹 단위의 동기화가 하드웨어 리소스 활용도를 극대화합니다.
  • 안정성: num_acc_buffers = 1인 경우 발생하던 데드락 문제를 해결하기 위해 배리어 더블 버퍼링을 도입하여, 비동기 파이프라인의 정합성을 확보했습니다.

리뷰어 피드백 반영

리뷰 과정에서 ArriveBarrierOp의 결함이 발견되어 함께 수정되었습니다. 특히 masahi는 TMEM 로드 후 arrive 호출 전 bar.sync가 누락될 경우 발생할 수 있는 정합성 문제를 지적했으며, 이는 멀티 워프 환경에서의 올바른 동기화 시퀀스를 확립하는 계기가 되었습니다.

참고 자료

⚠️ 알림: 이 분석은 AI가 실제 코드 diff를 기반으로 작성했습니다.

댓글

관련 포스트

PR Analysis 의 다른글