Articleaws.amazon.com·2026년 10월 28일·0

Distributed training with Ray Train DLCs and EFA on EKS

Quick Summary

AWS Ray Train DLC를 그대로 사용하고 KubeRay와 EFA를 구성해, Amazon EKS의 g6.12xlarge 2대에 있는 NVIDIA L4 GPU 8개에서 Qwen2.5 1.5B를 FSDP로 분산 학습하는 예제다.

Distributed training with Ray Train DLCs and EFA on EKS 관련 대표 이미지

🖼️ 인포그래픽

Distributed training with Ray Train DLCs and EFA on EKS 내용을 설명하는 본문 이미지

🖼️ 4컷 인포그래픽

Distributed training with Ray Train DLCs and EFA on EKS의 핵심 내용을 4단계로 요약한 인포그래픽
Distributed training with Ray Train DLCs and EFA on EKS 핵심 내용을 4단계로 압축한 4컷 인포그래픽

💡 한 줄 요약

AWS Ray Train DLC를 그대로 사용하고 KubeRay와 EFA를 구성해, Amazon EKS의 g6.12xlarge 2대에 있는 NVIDIA L4 GPU 8개에서 Qwen2.5-1.5B를 FSDP로 분산 학습하는 예제다.

📌 핵심 요약

  • Ray Train DLC는 CUDA·PyTorch·NCCL·EFA·AWS OFI NCCL plugin·Ray를 AWS가 함께 빌드하고 테스트하는 공개 이미지로, 예제는 별도 이미지 빌드 없이 public.ecr.aws/deep-learning-containers/ray:train-ml-cuda-v1.1을 사용한다.
  • KubeRay는 하나의 RayCluster 매니페스트로 Ray head와 worker pod를 생성하고 유지한다. 동일한 DLC 이미지를 사용하며 역할, GPU·EFA 자원, 네트워크 환경 변수, 작업별 추가 패키지는 이미지 밖에서 설정한다.
  • 클러스터는 m7i.xlarge 시스템 노드 1대와 같은 가용 영역의 g6.12xlarge 2대로 구성된다. 각 GPU 노드의 pod가 NVIDIA L4 GPU 4개와 EFA 인터페이스 1개를 요청하고, Ray Train이 GPU당 학습 프로세스 하나씩 총 8개를 배치한다.
  • Qwen2.5-1.5B의 bfloat16 학습에 필요한 가중치·기울기·옵티마이저 상태의 네 텐서는 약 12 GB이며, FSDP로 8개 GPU에 분할하면 GPU당 약 1.5 GB가 된다. 대신 매 단계 가중치 수집과 기울기 reduce-scatter가 발생하고, 인스턴스 사이 통신은 EFA가 담당한다.
  • 실행 전 AWS CLI v2, eksctl, kubectl, Helm, envsubst와 G 계열 온디맨드 용량 96 vCPU가 필요하다. 원문은 GPU 인스턴스 2대, EKS 제어 영역, NAT Gateway를 포함한 실행 비용을 시간당 약 9.50달러로 제시하며, 기존 용량 예약은 CAPACITY_RESERVATION_ID로 지정할 수 있다고 설명한다.

🧩 주요 포인트

  1. AWS가 분산 학습 의존성을 하나의 DLC로 검증 → 컨테이너 조합과 재빌드 부담이 줄고, NCCL이 TCP로 전환되는 호환성 문제를 줄이는 기반을 제공한다.
  2. KubeRay의 클러스터 관리와 Ray Train의 프로세스 실행을 분리 → 학습 함수는 모델 계산에 집중하고, 배치·자원·통신 조건은 외부 설정으로 조정한다.
  3. FSDP의 GPU당 메모리 절감에는 단계별 통신이 수반 → EFA 구성과 같은 가용 영역 배치가 다중 노드 학습 성능을 뒷받침하는 핵심 조건이 된다.

🧠 상세 정리

1. 확장의 출발점은 모델 코드보다 컨테이너 구성

원문은 PyTorch 학습을 여러 머신으로 확장할 때 흔히 발목을 잡는 요소가 모델 코드보다 컨테이너라고 설명한다. 모든 컨테이너에 동일한 CUDA 런타임, 그 버전에 맞춰 빌드된 PyTorch, NCCL, EFA 사용자 공간 라이브러리, NCCL과 EFA를 연결하는 AWS OFI NCCL plugin, 운영 환경과 합의된 Ray 버전이 필요하기 때문이다. 이 구성 요소가 바뀔 때마다 이미지를 다시 만들고 정합성을 유지하는 작업은 모델 학습과 별개의 부담이 된다. Ray Train DLC는 AWS가 이 스택을 조립하고 하나의 단위로 테스트한 뒤 Amazon ECR Public에 게시하고 패치하는 이미지다. 예제는 이 이미지를 수정 없이 사용해 g6.12xlarge 2대의 NVIDIA L4 GPU 8개에서 Qwen2.5-1.5B를 FSDP로 학습하며, 학습 함수와 RayCluster 매니페스트 및 변수 파일로 구성을 표현한다.

2. DLC에 포함된 학습·통신 스택과 검증 범위

예제가 사용하는 train-ml-cuda-v1.1 이미지에는 Train·Tune·Data를 포함한 Ray 2.58.0, PyTorch 2.13.0, torchvision 0.28.0이 들어 있다. GPU 런타임 구성은 CUDA 13.0.2, cuDNN, NCCL 2.29.7이며, 네트워크 계층에는 최신 EFA 구성, AWS OFI NCCL plugin, GDRCopy가 포함된다. 학습 라이브러리로는 DeepSpeed, flash-attn, Transformer Engine, PyTorch Lightning, Hugging Face 라이브러리가 제공되고, 진단용 all_reduce_perf도 실행 경로에 준비돼 있다. 원문은 특히 네트워크 라이브러리가 맞지 않으면 오류 없이 NCCL이 TCP 소켓으로 전환되어 작업은 끝나더라도 속도가 크게 떨어질 수 있다고 지적한다. AWS는 이 라이브러리들을 함께 빌드하고 테스트하며, 각 릴리스에 다중 노드 EFA 및 다중 노드 KubeRay 학습 테스트를 적용한다고 설명한다.

3. 공개 이미지와 공통 실행 방식이 줄이는 준비 작업

DLC는 공개 이미지이므로 노드가 인증 정보 없이 가져올 수 있고, 예제 실행 과정에서 별도의 레지스트리를 구성하거나 이미지를 빌드해 푸시할 필요가 없다. 컨테이너 진입점은 시작할 때 호스트의 NVIDIA 드라이버를 확인하고 이미지의 CUDA보다 오래된 드라이버라면 번들된 CUDA 전방 호환성 라이브러리를 자동으로 활성화한다. 이미지 자체에는 head나 worker 역할이 고정돼 있지 않으며, 컨테이너를 시작하는 쪽이 ray start 명령을 전달하므로 같은 태그로 두 역할을 모두 실행한다. 이 방식은 KubeRay가 Amazon EKS에서 pod를 생성할 때뿐 아니라 Amazon EC2에서 직접 실행할 때도 적용된다. Ray Train 이미지는 Ray Serve DLC 및 Ray LLM DLC와 동일한 ray ECR 저장소를 공유하며, 학습 이미지는 train-ml 태그 접두사로 구분된다.

4. 이미지 재빌드 대신 외부 설정으로 작업을 변경

예제는 head와 worker에 동일한 DLC_IMAGE를 지정하고, KubeRay의 rayStartParams로 역할을 정하며 head에는 num-gpus: "0"을 설정한다. worker pod의 자원 요청은 nvidia.com/gpu: 4와 vpc.amazonaws.com/efa: 1로 표현하고, 통신은 FI_PROVIDER, NCCL_NET_PLUGIN, NCCL_SOCKET_IFNAME, NCCL_DEBUG 환경 변수로 드러낸다. 이미지의 기본 FI_PROVIDER는 efa이지만 예제는 네 가지 변수를 매니페스트에 명시하며, EKS에서는 NCCL_SOCKET_IFNAME을 pod의 eth0로 지정한다. 기본 Hugging Face 학습 스택만으로 예제가 실행되며, 다른 패키지가 필요하면 Ray runtime_env를 통해 제출 시 설치하고 통신 변수도 작업별로 덮어쓸 수 있다. 인스턴스 유형·노드 수·리전·가용 영역은 scripts/env.sh에서, 모델·단계 수·시퀀스 길이·배치 크기는 train.py 인자로 설정한다. 버전 관리에서는 vX.Y 태그가 보안 재빌드에 따라 이동하고 vX.Y.Z 태그는 최초 릴리스 빌드로 고정되므로, 바이트 단위로 동일한 실행이 필요하면 digest 고정을 권한다.

5. EKS 클러스터 배치와 네트워크 경로

모든 노드는 하나의 VPC에 있는 프라이빗 서브넷에 배치되며, Amazon ECR Public에서 DLC를 가져오거나 Hugging Face에서 모델 가중치를 내려받을 때 NAT Gateway를 통해 인터넷에 접근한다. m7i.xlarge 시스템 노드 1대는 kube-system 부가 기능, KubeRay operator, GPU를 광고하지 않는 Ray head를 실행하므로 학습 작업이 head에 배치되지 않는다. head는 작업 서버에 8265 포트, 제어 저장소에 6379 포트를 사용하지만, 작업 제출은 EKS API를 거쳐 kubectl exec로 head pod 내부에서 수행해 8265 포트를 클러스터 밖에 노출하지 않는다. 학습용 g6.12xlarge는 각각 NVIDIA L4 GPU 4개, 48 vCPU, 메모리 192 GiB, 네트워크 40 Gbps, EFA 인터페이스 1개를 갖추고 단일 worker pod가 GPU와 EFA를 모두 요청한다. Ray Train은 한 인스턴스에 rank 0~3, 다른 인스턴스에 rank 4~7을 배치하며, EFA 트래픽은 가용 영역을 넘지 않으므로 스크립트는 해당 인스턴스를 제공하는 하나의 가용 영역에 두 노드를 배치한다.

6. Ray Train의 실행 관리와 FSDP의 통신 대가

Ray head는 클러스터 상태를 추적하는 전역 제어 저장소와 대시보드, 작업 서버를 운영하고, worker 노드는 head 주소에 연결해 GPU와 학습 프로세스를 제공한다. Kubernetes 자체에는 Ray 클러스터 개념이 없으므로 KubeRay가 RayCluster 리소스에 정의된 head·worker pod를 생성하고 역할별로 시작하며 실패한 pod를 교체한다. 학습 실행에서는 사용자가 함수를 TorchTrainer와 ScalingConfig에 전달하면 Ray Train이 GPU마다 worker 하나를 시작하고 rank, 전체 프로세스 수, torch.distributed 프로세스 그룹 구성을 맡는다. 예제의 FSDP는 가중치·기울기·옵티마이저 상태를 8개 GPU로 나누며, 원문은 Qwen2.5-1.5B의 bfloat16 학습에 필요한 네 텐서가 약 12 GB이고 분할 후 GPU당 약 1.5 GB라고 설명한다. 메모리 절감의 대가로 각 계층 사용 전 가중치를 모으고 이후 기울기를 reduce-scatter하므로 매 단계 모델 전체에 해당하는 통신이 rank 사이에서 발생하며, 두 인스턴스 사이 구간은 DLC의 EFA 스택이 처리한다.

7. 실행 전 도구·용량·비용 조건

실행 도구로는 대상 계정에 로그인된 AWS CLI v2, eksctl, kubectl, Helm과 GNU gettext의 envsubst가 필요하다. 용량 조건은 g6.12xlarge 2대를 위한 G 계열 온디맨드 용량 96 vCPU이며, 선택한 AWS 리전에는 해당 인스턴스를 제공하는 가용 영역이 적어도 하나 있어야 한다. 이미 인스턴스의 온디맨드 용량 예약을 보유했다면 CAPACITY_RESERVATION_ID를 설정할 수 있고, 이 경우 스크립트는 용량 검색을 건너뛰고 예약에 노드 그룹을 실행한다. 원문이 제시하는 예산은 GPU 인스턴스가 실행되는 동안 시간당 약 9.50달러로, 두 인스턴스와 EKS 제어 영역, NAT Gateway를 포함한다. 시작 전 aws sts get-caller-identity를 실행해 CLI가 예상한 계정을 가리키는지 확인하는 방법도 제시하며, 도구 준비와 별도로 계정·용량·비용 조건을 충족해야 함을 설명한다.

8. 학습 함수의 구성과 제공된 발췌의 범위

code/train.py의 train_func는 컨테이너나 클러스터, 네트워크에 특화된 내용 없이 GPU별 학습을 수행하며, Ray 문맥에서 전체 worker 수와 rank를 읽고 사용할 장치를 얻는다. 모델은 AutoModelForCausalLM.from_pretrained로 bfloat16 형식으로 불러오고, 매개변수가 1천만 개를 넘는 하위 모듈을 각각 FSDP 단위로 감싸도록 크기 기반 정책을 적용한다. 원문은 특정 모델의 계층 클래스 대신 크기를 기준으로 삼아 스크립트가 모델에 덜 종속되도록 했다고 설명하며, prepare_model에 parallel_strategy="fsdp"를 전달한 뒤 AdamW 옵티마이저를 구성한다. 각 단계에서는 무작위 토큰 ID를 생성해 입력과 정답으로 사용하고, 기울기를 초기화한 뒤 손실 계산, 역전파, 각 rank의 담당 조각 갱신을 수행하며 step과 loss를 Ray에 보고한다. 마지막 설명은 드라이버가 실행 중인 클러스터에 연결하고 GPU 수를 세어 trainer를 시작한다고 밝히지만, 제공된 source_body는 이어지는 문장 중간에서 끝나므로 이후 실행 절차나 결과는 확인할 수 없다.

🧾 핵심 주장 / 시사점

  • DLC의 가치는 라이브러리를 묶는 데 더해, 오류 없이 TCP로 전환될 수 있는 통신 경로를 다중 노드 테스트 대상으로 포함한다는 데 있다.
  • 동일한 이미지에 역할·자원·패키지·통신 설정을 외부에서 적용하는 구조는 학습 작업 변경과 컨테이너 유지보수를 분리하는 데 도움이 된다.
  • GPU당 약 1.5 GB라는 FSDP 메모리 수치만으로 확장 효과를 판단하기는 어렵다. 매 단계 발생하는 노드 간 통신을 함께 고려해야 하며, 제공된 발췌에는 실제 처리량이나 EFA 성능 비교 결과가 없다.

✅ 액션 아이템

  • train-ml-cuda-v1.1과 GPU·EFA 자원 요청, 네트워크 환경 변수를 기준으로 KubeRay 실행 구성 확인.
  • Qwen2.5-1.5B의 FSDP 적용 시 GPU당 약 1.5 GB의 상태 메모리와 단계별 EFA 통신 부담을 함께 검토.
  • G 계열 온디맨드 용량 96 vCPU 또는 CAPACITY_RESERVATION_ID 확보 여부와 시간당 약 9.50달러의 실행 비용 확인.

❓ 열린 질문

  • Qwen2.5-1.5B의 FSDP 학습에서 EFA 통신은 실제 처리량에 어느 정도 영향을 미치는가?
  • 같은 가용 영역에 필요한 g6.12xlarge 2대를 확보할 수 있으며, G 계열 온디맨드 용량 96 vCPU 조건도 충족하는가?
  • 시간당 약 9.50달러의 실행 비용은 예정된 학습 시간과 예산에 부합하는가?

관련 문서

공통 태그와 주제 흐름을 기준으로 같이 보면 좋은 문서를 이어서 제안합니다.