Průvodce trénováním distribuovaného GPU (SDK v2)

PLATÍ PRO: Python SDK azure-ai-ml v2 (aktuální)

Přečtěte si další informace o použití distribuovaného trénovacího kódu GPU ve službě Azure Machine Učení. Tento článek vám pomůže spustit stávající distribuovaný trénovací kód a nabízí tipy a příklady, které můžete sledovat pro každou architekturu:

  • Rozhraní MPI (Message Passing Interface)
    • Horovod
    • Proměnné prostředí z Open MPI
  • PyTorch
  • TensorFlow
  • Zrychlení trénování GPU pomocí InfiniBandu

Požadavky

Projděte si základní koncepty distribuovaného trénování GPU, jako je datový paralelismus, distribuovaný datový paralelismus a paralelismus modelu.

Tip

Pokud nevíte, jaký typ paralelismu použít, měli byste použít distribuovaný datový paralelismus více než 90 % času.

MPI

Azure Machine Učení nabízí úlohu MPI pro spuštění daného počtu procesů v každém uzlu. Azure Machine Učení vytváří úplný příkaz MPI launch (mpirun) na pozadí. Nemůžete zadat vlastní úplné příkazy head-node-launcher jako mpirun nebo DeepSpeed launcher.

Tip

Základní image Dockeru používaná službou Azure Machine Učení úloha MPI musí mít nainstalovanou knihovnu MPI. Open MPI je součástí všech základních imagí GPU Učení Azure Machine. Při použití vlastní image Dockeru zodpovídáte za to, že image obsahuje knihovnu MPI. Doporučuje se otevřít MPI, ale můžete také použít jinou implementaci MPI, například Intel MPI. Azure Machine Učení také poskytuje kurátorovaná prostředí pro oblíbené architektury.

Pokud chcete spustit distribuované trénování pomocí MPI, postupujte takto:

  1. Použijte prostředí Azure Machine Učení s upřednostňovanou architekturou hlubokého učení a MPI. Azure Machine Učení poskytuje kurátorovaná prostředí pro oblíbené architektury. Nebo vytvořte vlastní prostředí s upřednostňovanou architekturou hlubokého učení a MPI.
  2. Definujte s .commandinstance_count instance_count pokud je uživatelský skript zodpovědný za spouštění procesů na jeden uzel, musí se rovnat počtu GPU na uzel nebo na hodnotu 1 (výchozí) pro spuštění jednotlivých uzlů.
  3. distribution Použijte parametr parametru command k určení nastavení pro MpiDistribution.
from azure.ai.ml import command, MpiDistribution

job = command(
    code="./src",  # local path where the code is stored
    command="python train.py --epochs ${{inputs.epochs}}",
    inputs={"epochs": 1},
    environment="AzureML-tensorflow-2.12-cuda11@latest",
    compute="gpu-cluster",
    instance_count=2,
    distribution=MpiDistribution(process_count_per_instance=2),
    display_name="tensorflow-mnist-distributed-horovod-example"
    # experiment_name: tensorflow-mnist-distributed-horovod-example
    # description: Train a basic neural network with TensorFlow on the MNIST dataset, distributed via Horovod.
)

Horovod

Konfiguraci úlohy MPI použijte při použití Horovodu pro distribuované trénování s architekturou hlubokého učení.

Ujistěte se, že váš kód používá tyto tipy:

  • Trénovací kód se správně instrumentuje pomocí Horovodu před přidáním částí Učení Azure Machine.
  • Vaše prostředí azure machine Učení obsahuje Horovod a MPI. Kurátorovaná prostředí GPU PyTorch a TensorFlow jsou předem nakonfigurovaná s Horovodem a jejími závislostmi.
  • Vytvořte požadovanou command distribuci.

Příklad Horovodu

Proměnné prostředí z Open MPI

Při spouštění úloh MPI s otevřenými imagemi MPI můžete pro každý spuštěný proces použít následující proměnné prostředí:

  1. OMPI_COMM_WORLD_RANK: Pořadí procesu
  2. OMPI_COMM_WORLD_SIZE: Velikost světa
  3. AZ_BATCH_MASTER_NODE: Primární adresa s portem, MASTER_ADDR:MASTER_PORT
  4. OMPI_COMM_WORLD_LOCAL_RANK: Místní pořadí procesu na uzlu
  5. OMPI_COMM_WORLD_LOCAL_SIZE: Počet procesů v uzlu

Tip

Navzdory názvu proměnná OMPI_COMM_WORLD_NODE_RANK prostředí neodpovídá sadě NODE_RANK. Chcete-li použít spouštěč pro jednotlivé uzly, nastavte process_count_per_node=1 a použijte OMPI_COMM_WORLD_RANK jako NODE_RANK.

PyTorch

Azure Machine Učení podporuje spouštění distribuovaných úloh pomocí nativních funkcí distribuovaného trénování PyTorch (torch.distributed).

Tip

V případě datového paralelismu je oficiální pokyny PyTorchu použít DistributedDataParallel (DDP) přes DataParallel pro distribuované trénování s jedním uzlem i více uzly. PyTorch také doporučuje používat DistributedDataParallel přes balíček multiprocessingu. Dokumentace ke službě Azure Machine Učení a příklady se proto zaměřují na trénování DistributedDataParallel.

Inicializace skupiny procesů

Páteř všech distribuovaných trénování je založená na skupině procesů, které navzájem znají a můžou mezi sebou komunikovat pomocí back-endu. Pro PyTorch se skupina procesů vytvoří voláním torch.distributed.init_process_group ve všech distribuovaných procesech , aby souhrnně vytvořily skupinu procesů.

torch.distributed.init_process_group(backend='nccl', init_method='env://', ...)

Nejběžnějšími používanými back-endy komunikace jsou mpi, nccla gloo. Pro trénování nccl na základě GPU se doporučuje nejlepší výkon a měl by se použít, kdykoli je to možné.

init_method informuje, jak se jednotlivé procesy můžou navzájem zjišťovat, jak inicializují a ověřují skupinu procesů pomocí back-endu komunikace. Pokud není zadáno, init_method PyTorch ve výchozím nastavení používá metodu inicializace proměnné prostředí (env://). init_methodje doporučená inicializační metoda, která se použije v trénovacím kódu ke spuštění distribuovaného PyTorchu na počítači Azure Učení. PyTorch hledá následující proměnné prostředí pro inicializaci:

  • MASTER_ADDR: IP adresa počítače, který hostuje proces s pořadím 0
  • MASTER_PORT: Bezplatný port na počítači, který je hostitelem procesu s pořadím 0
  • WORLD_SIZE: Celkový počet procesů. Měl by se rovnat celkovému počtu zařízení (GPU) používaných k distribuovanému trénování.
  • RANK: (globální) pořadí aktuálního procesu. Možné hodnoty jsou 0 až (velikost světa - 1)

Další informace o inicializaci skupin procesů najdete v dokumentaci k PyTorch.

Mnoho aplikací také potřebuje následující proměnné prostředí:

  • LOCAL_RANK: Místní (relativní) pořadí procesu v rámci uzlu. Možné hodnoty jsou 0 až (počet procesů na uzlu – 1). Tyto informace jsou užitečné, protože mnoho operací, jako je příprava dat, by se mělo provádět pouze jednou na uzel, obvykle na local_rank = 0.
  • NODE_RANK: Pořadí uzlu pro trénování s více uzly. Možné hodnoty jsou 0 až (celkový počet uzlů – 1).

Nemusíte používat spouštěcí nástroj, jako je torch.distributed.launch. Spuštění distribuované úlohy PyTorch:

  1. Zadejte trénovací skript a argumenty.
  2. Vytvořte command a zadejte typ jako PyTorch a process_count_per_instance v parametru distribution . Odpovídá process_count_per_instance celkovému počtu procesů, které chcete pro úlohu spustit. process_count_per_instance by měla být obvykle rovna # of GPUs per node. Pokud process_count_per_instance není zadaný, služba Azure Machine Učení ve výchozím nastavení spustí jeden proces na uzel.

Azure Machine Učení nastaví proměnné MASTER_ADDR, MASTER_PORT, WORLD_SIZEa NODE_RANK prostředí na každém uzlu a nastaví proměnné RANK procesu a LOCAL_RANK prostředí.

from azure.ai.ml import command
from azure.ai.ml.entities import Data
from azure.ai.ml import Input
from azure.ai.ml import Output
from azure.ai.ml.constants import AssetTypes

# === Note on path ===
# can be can be a local path or a cloud path. AzureML supports https://`, `abfss://`, `wasbs://` and `azureml://` URIs.
# Local paths are automatically uploaded to the default datastore in the cloud.
# More details on supported paths: https://docs.microsoft.com/azure/machine-learning/how-to-read-write-data-v2#supported-paths

inputs = {
    "cifar": Input(
        type=AssetTypes.URI_FOLDER, path=returned_job.outputs.cifar.path
    ),  # path="azureml:azureml_stoic_cartoon_wgb3lgvgky_output_data_cifar:1"), #path="azureml://datastores/workspaceblobstore/paths/azureml/stoic_cartoon_wgb3lgvgky/cifar/"),
    "epoch": 10,
    "batchsize": 64,
    "workers": 2,
    "lr": 0.01,
    "momen": 0.9,
    "prtfreq": 200,
    "output": "./outputs",
}

from azure.ai.ml.entities import ResourceConfiguration

job = command(
    code="./src",  # local path where the code is stored
    command="python train.py --data-dir ${{inputs.cifar}} --epochs ${{inputs.epoch}} --batch-size ${{inputs.batchsize}} --workers ${{inputs.workers}} --learning-rate ${{inputs.lr}} --momentum ${{inputs.momen}} --print-freq ${{inputs.prtfreq}} --model-dir ${{inputs.output}}",
    inputs=inputs,
    environment="azureml:AzureML-acpt-pytorch-2.2-cuda12.1@latest",
    instance_count=2,  # In this, only 2 node cluster was created.
    distribution={
        "type": "PyTorch",
        # set process count to the number of gpus per node
        # NC6s_v3 has only 1 GPU
        "process_count_per_instance": 1,
    },
)
job.resources = ResourceConfiguration(
    instance_type="Standard_NC6s_v3", instance_count=2
)  # Serverless compute resources

Příklad Pytorchu

DeepSpeed

Azure Machine Učení podporuje DeepSpeed jako prvotřídní občana ke spouštění distribuovaných úloh s téměř lineární škálovatelností z hlediska:

  • Zvětšení velikosti modelu
  • Zvýšení počtu grafických procesorů

DeepSpeed je možné povolit pomocí distribuce Pytorch nebo MPI pro spouštění distribuovaného trénování. Azure Machine Učení podporuje spouštěč DeepSpeed ke spuštění distribuovaného trénování a automatického ladění pro zajištění optimální ds konfigurace.

Kurátorované prostředí můžete použít pro zastaralé prostředí s nejnovějšími špičkovými technologiemi, včetně DeepSpeed, ORT, MSSCCL a Pytorch pro vaše trénovací úlohy DeepSpeed.

Příklad DeepSpeed

  • Příklady trénování a automatického ladění DeepSpeed najdete v těchto složkách.

TensorFlow

Pokud ve svém trénovacím kódu, jako je rozhraní API TensorFlow 2.x, použijete nativní distribuovanou úlohu TensorFlow, můžete ji spustit prostřednictvím služby Azure Machine Učení pomocí distribution parametrů nebo objektuTensorFlowDistribution.tf.distribute.Strategy

# create the command
job = command(
    code="./src",  # local path where the code is stored
    command="python main.py --epochs ${{inputs.epochs}} --model-dir ${{inputs.model_dir}}",
    inputs={"epochs": 1, "model_dir": "outputs/keras-model"},
    environment="AzureML-tensorflow-2.12-cuda11@latest",
    compute="cpu-cluster",
    instance_count=2,
    # distribution = {"type": "mpi", "process_count_per_instance": 1},
    # distribution={
    #     "type": "tensorflow",
    #     "parameter_server_count": 1,  # for legacy TensorFlow 1.x
    #     "worker_count": 2,
    #     "added_property": 7,
    # },
    # distribution = {
    #        "type": "pytorch",
    #        "process_count_per_instance": 4,
    #        "additional_prop": {"nested_prop": 3},
    #    },
    display_name="tensorflow-mnist-distributed-example"
    # experiment_name: tensorflow-mnist-distributed-example
    # description: Train a basic neural network with TensorFlow on the MNIST dataset, distributed via TensorFlow.
)

# can also set the distribution in a separate step and using the typed objects instead of a dict
job.distribution = TensorFlowDistribution(worker_count=2)

Pokud váš trénovací skript používá strategii serveru parametrů pro distribuované trénování, například pro starší verzi TensorFlow 1.x, musíte také zadat počet serverů parametrů, které se mají použít v úloze, uvnitř distribution parametru command. Ve výše uvedeném příkladu a "parameter_server_count" : 1"worker_count": 2.

TF_CONFIG

V TensorFlow TF_CONFIG se proměnná prostředí vyžaduje pro trénování na více počítačích. U úloh TensorFlow služba Azure Machine Učení nakonfiguruje a nastaví TF_CONFIG proměnnou odpovídajícím způsobem pro každý pracovní proces před spuštěním trénovacího skriptu.

Přístup z TF_CONFIG trénovacího skriptu získáte v případě, že potřebujete: os.environ['TF_CONFIG'].

Příklad TF_CONFIG nastavení na hlavním pracovním uzlu:

TF_CONFIG='{
    "cluster": {
        "worker": ["host0:2222", "host1:2222"]
    },
    "task": {"type": "worker", "index": 0},
    "environment": "cloud"
}'

Příklad TensorFlow

Zrychlení distribuovaného trénování GPU pomocí InfiniBandu

S rostoucím počtem virtuálních počítačů trénování modelu by se měl zkrátit čas potřebný k trénování tohoto modelu. V ideálním případě by mělo být snížení času lineární úměrné počtu trénovacích virtuálních počítačů. Pokud například trénování modelu na jednom virtuálním počítači trvá 100 sekund, trénování stejného modelu na dvou virtuálních počítačích by mělo v ideálním případě trvat 50 sekund. Trénování modelu na čtyřech virtuálních počítačích by mělo trvat 25 sekund atd.

InfiniBand může být důležitým faktorem při dosažení tohoto lineárního měřítka. InfiniBand umožňuje komunikaci s GPU na GPU mezi uzly v clusteru s nízkou latencí. InfiniBand vyžaduje specializovaný hardware pro provoz. Některé řady virtuálních počítačů Azure, konkrétně nc, ND a H-series, teď mají virtuální počítače podporující RDMA s podporou SR-IOV a InfiniBand. Tyto virtuální počítače komunikují přes nízkou latenci a síť InfiniBand s velkou šířkou pásma, což je mnohem výkonnější než připojení založené na ethernetu. SR-IOV pro InfiniBand umožňuje téměř holý výkon pro libovolnou knihovnu MPI (MPI používá mnoho distribuovaných trénovacích architektur a nástrojů, včetně softwaru NCCL NVIDIA.) Tyto skladové položky jsou určené ke splnění potřeb výpočetních úloh s akcelerovanými gpu. Další informace najdete v tématu Zrychlení distribuovaného trénování v Azure Machine Učení pomocí ROZHRANÍ SR-IOV.

Skladové položky virtuálních počítačů s "r" v názvu obvykle obsahují požadovaný hardware InfiniBand a ty bez r obvykle ne. ("r" je odkaz na RDMA, což je zkratka pro přímý přístup do paměti vzdáleného přístupu.) Skladová položka virtuálního počítače Standard_NC24rs_v3 je například povolená pro InfiniBand, ale skladová Standard_NC24s_v3 položka není. Kromě možností InfiniBand jsou specifikace mezi těmito dvěma skladovými jednotkami z velké části stejné. Oba mají 24 jader, 448 GB RAM, 4 GPU stejné skladové položky atd. Přečtěte si další informace o SKU počítačů s podporou RDMA a InfiniBand.

Upozorňující

Skladová položka Standard_NC24r počítače starší generace je povolená SDMA, ale neobsahuje hardware SR-IOV vyžadovaný pro InfiniBand.

Pokud vytvoříte AmlCompute cluster s jednou z těchto velikostí podporujících RDMA, dodává se image operačního systému s ovladačem Mellanox OFED vyžadovaným k povolení předinstalovaného a předkonfigurovaného infiniBandu.

Další kroky