故障排除#

本文件概述了一些您可以考慮的故障排除策略。如果您認為您發現了錯誤,請先搜尋現有問題,看看是否已被報告。如果未被報告,請提交新問題,並提供儘可能多的相關資訊。

注意

一旦您除錯好問題,請記住關閉任何已定義的環境除錯變數,或者簡單地啟動一個新的 shell 以避免受到遺留除錯設定的影響。否則,系統可能會因除錯功能處於啟用狀態而變慢。

下載模型時掛起#

如果模型尚未下載到磁碟,vLLM 將從網際網路下載模型,這可能需要時間,具體取決於您的網際網路連線。建議首先使用 huggingface-cli 下載模型,並將模型的本地路徑傳遞給 vLLM。這樣,您可以隔離問題。

從磁碟載入模型時掛起#

如果模型很大,則從磁碟載入模型可能需要很長時間。請注意您儲存模型的位置。某些叢集在節點之間共享檔案系統,例如分散式檔案系統或網路檔案系統,這可能會很慢。最好將模型儲存在本地磁碟中。此外,請檢視 CPU 記憶體使用情況,當模型過大時,可能會佔用大量 CPU 記憶體,從而降低作業系統速度,因為它需要頻繁地在磁碟和記憶體之間進行交換。

注意

為了隔離模型下載和載入問題,您可以使用 --load-format dummy 引數來跳過載入模型權重。這樣,您可以檢查模型下載和載入是否是瓶頸。

記憶體不足#

如果模型太大而無法容納在單個 GPU 中,您將收到記憶體不足 (OOM) 錯誤。考慮使用張量並行將模型拆分到多個 GPU 上。在這種情況下,每個程序將讀取整個模型並將其拆分為塊,這會使磁碟讀取時間更長(與張量並行的大小成正比)。您可以使用 examples/offline_inference/save_sharded_state.py 將模型檢查點轉換為分片檢查點。轉換過程可能需要一些時間,但稍後您可以更快地載入分片檢查點。模型載入時間應保持不變,與張量並行的大小無關。

生成質量發生變化#

在 v0.8.0 中,預設取樣引數的來源在 Pull Request #12622 中進行了更改。在 v0.8.0 之前,預設取樣引數來自 vLLM 的中性預設值集。從 v0.8.0 開始,預設取樣引數來自模型建立者提供的 generation_config.json

在大多數情況下,這應該會帶來更高質量的響應,因為模型建立者可能知道哪些取樣引數最適合他們的模型。但是,在某些情況下,模型建立者提供的預設值可能會導致效能下降。

您可以透過使用 --generation-config vllm 進行線上嘗試和使用 generation_config="vllm" 進行離線嘗試來檢查是否發生了這種情況。如果在嘗試此操作後,您的生成質量有所提高,我們建議繼續使用 vLLM 預設值,並在 https://huggingface.tw 上請願模型建立者更新其預設 generation_config.json,以便生成更高質量的生成結果。

啟用更多日誌記錄#

如果其他策略無法解決問題,則可能是 vLLM 例項卡在某個地方。您可以使用以下環境變數來幫助除錯問題

  • export VLLM_LOGGING_LEVEL=DEBUG 以啟用更多日誌記錄。

  • export CUDA_LAUNCH_BLOCKING=1 以識別哪個 CUDA 核心導致了問題。

  • export NCCL_DEBUG=TRACE 以啟用更多 NCCL 日誌記錄。

  • export VLLM_TRACE_FUNCTION=1 以記錄日誌檔案中所有函式呼叫以進行檢查,從而判斷哪個函式崩潰或掛起。

不正確的網路設定#

如果您有複雜的網路配置,vLLM 例項可能無法獲取正確的 IP 地址。您可以找到類似 DEBUG 06-10 21:32:17 parallel_state.py:88] world_size=8 rank=0 local_rank=0 distributed_init_method=tcp://xxx.xxx.xxx.xxx:54641 backend=nccl 的日誌,並且 IP 地址應該是正確的。如果不是,請使用環境變數 export VLLM_HOST_IP=<your_ip_address> 覆蓋 IP 地址。

您可能還需要設定 export NCCL_SOCKET_IFNAME=<your_network_interface>export GLOO_SOCKET_IFNAME=<your_network_interface> 以指定 IP 地址的網路介面。

錯誤 near self.graph.replay()#

如果 vLLM 崩潰並且錯誤跟蹤捕獲到 vllm/worker/model_runner.pyself.graph.replay() 附近的某個位置,則表示 CUDAGraph 內部存在 CUDA 錯誤。要識別導致錯誤的特定 CUDA 操作,您可以將 --enforce-eager 新增到命令列,或者將 enforce_eager=True 新增到 LLM 類以停用 CUDAGraph 最佳化並隔離導致錯誤的確切 CUDA 操作。

不正確的硬體/驅動程式#

如果無法建立 GPU/CPU 通訊,您可以使用以下 Python 指令碼並按照以下說明確認 GPU/CPU 通訊是否正常工作。

# Test PyTorch NCCL
import torch
import torch.distributed as dist
dist.init_process_group(backend="nccl")
local_rank = dist.get_rank() % torch.cuda.device_count()
torch.cuda.set_device(local_rank)
data = torch.FloatTensor([1,] * 128).to("cuda")
dist.all_reduce(data, op=dist.ReduceOp.SUM)
torch.cuda.synchronize()
value = data.mean().item()
world_size = dist.get_world_size()
assert value == world_size, f"Expected {world_size}, got {value}"

print("PyTorch NCCL is successful!")

# Test PyTorch GLOO
gloo_group = dist.new_group(ranks=list(range(world_size)), backend="gloo")
cpu_data = torch.FloatTensor([1,] * 128)
dist.all_reduce(cpu_data, op=dist.ReduceOp.SUM, group=gloo_group)
value = cpu_data.mean().item()
assert value == world_size, f"Expected {world_size}, got {value}"

print("PyTorch GLOO is successful!")

if world_size <= 1:
    exit()

# Test vLLM NCCL, with cuda graph
from vllm.distributed.device_communicators.pynccl import PyNcclCommunicator

pynccl = PyNcclCommunicator(group=gloo_group, device=local_rank)
# pynccl is enabled by default for 0.6.5+,
# but for 0.6.4 and below, we need to enable it manually.
# keep the code for backward compatibility when because people
# prefer to read the latest documentation.
pynccl.disabled = False

s = torch.cuda.Stream()
with torch.cuda.stream(s):
    data.fill_(1)
    out = pynccl.all_reduce(data, stream=s)
    value = out.mean().item()
    assert value == world_size, f"Expected {world_size}, got {value}"

print("vLLM NCCL is successful!")

g = torch.cuda.CUDAGraph()
with torch.cuda.graph(cuda_graph=g, stream=s):
    out = pynccl.all_reduce(data, stream=torch.cuda.current_stream())

data.fill_(1)
g.replay()
torch.cuda.current_stream().synchronize()
value = out.mean().item()
assert value == world_size, f"Expected {world_size}, got {value}"

print("vLLM NCCL with cuda graph is successful!")

dist.destroy_process_group(gloo_group)
dist.destroy_process_group()

如果您正在使用單節點進行測試,請將 --nproc-per-node 調整為您要使用的 GPU 數量

NCCL_DEBUG=TRACE torchrun --nproc-per-node=<number-of-GPUs> test.py

如果您正在使用多節點進行測試,請根據您的設定調整 --nproc-per-node--nnodes,並將 MASTER_ADDR 設定為主節點的正確 IP 地址,該地址可從所有節點訪問。然後,執行

NCCL_DEBUG=TRACE torchrun --nnodes 2 --nproc-per-node=2 --rdzv_backend=c10d --rdzv_endpoint=$MASTER_ADDR test.py

如果指令碼成功執行,您應該看到訊息 sanity check is successful!

如果測試指令碼掛起或崩潰,通常意味著硬體/驅動程式在某種程度上已損壞。您應該嘗試聯絡您的系統管理員或硬體供應商以獲得進一步的幫助。作為一種常見的解決方法,您可以嘗試調整一些 NCCL 環境變數,例如 export NCCL_P2P_DISABLE=1 以檢視是否有幫助。請檢視 他們的文件 以獲取更多資訊。請僅將這些環境變數用作臨時解決方法,因為它們可能會影響系統的效能。最佳解決方案仍然是修復硬體/驅動程式,以便測試指令碼可以成功執行。

注意

多節點環境比單節點環境更復雜。如果您看到諸如 torch.distributed.DistNetworkError 之類的錯誤,則可能是網路/DNS 設定不正確。在這種情況下,您可以手動分配節點排名並透過命令列引數指定 IP

  • 在第一個節點中,執行 NCCL_DEBUG=TRACE torchrun --nnodes 2 --nproc-per-node=2 --node-rank 0 --master_addr $MASTER_ADDR test.py

  • 在第二個節點中,執行 NCCL_DEBUG=TRACE torchrun --nnodes 2 --nproc-per-node=2 --node-rank 1 --master_addr $MASTER_ADDR test.py

根據您的設定調整 --nproc-per-node--nnodes--node-rank,確保在不同的節點上執行不同的命令(具有不同的 --node-rank)。

Python 多程序處理#

RuntimeError 異常#

如果您在日誌中看到類似這樣的警告

WARNING 12-11 14:50:37 multiproc_worker_utils.py:281] CUDA was previously
    initialized. We must use the `spawn` multiprocessing start method. Setting
    VLLM_WORKER_MULTIPROC_METHOD to 'spawn'. See
    https://docs.vllm.tw/en/latest/getting_started/troubleshooting.html#python-multiprocessing
    for more information.

或者來自 Python 的類似這樣的錯誤

RuntimeError:
        An attempt has been made to start a new process before the
        current process has finished its bootstrapping phase.

        This probably means that you are not using fork to start your
        child processes and you have forgotten to use the proper idiom
        in the main module:

            if __name__ == '__main__':
                freeze_support()
                ...

        The "freeze_support()" line can be omitted if the program
        is not going to be frozen to produce an executable.

        To fix this issue, refer to the "Safe importing of main module"
        section in https://docs.python.club.tw/3/library/multiprocessing.html

那麼您必須更新您的 Python 程式碼,以在 if __name__ == '__main__': 塊後保護 vllm 的使用。例如,而不是這樣

import vllm

llm = vllm.LLM(...)

請嘗試改為這樣

if __name__ == '__main__':
    import vllm

    llm = vllm.LLM(...)

torch.compile 錯誤#

vLLM 嚴重依賴 torch.compile 來最佳化模型以獲得更好的效能,這引入了對 torch.compile 功能和 triton 庫的依賴。預設情況下,我們使用 torch.compile最佳化模型中的某些函式。在執行 vLLM 之前,您可以透過執行以下指令碼來檢查 torch.compile 是否按預期工作

import torch

@torch.compile
def f(x):
    # a simple function to test torch.compile
    x = x + 1
    x = x * 2
    x = x.sin()
    return x

x = torch.randn(4, 4).cuda()
print(f(x))

如果它從 torch/_inductor 目錄引發錯誤,通常意味著您有一個自定義的 triton 庫,該庫與您正在使用的 PyTorch 版本不相容。有關示例,請參見 此問題

模型檢查失敗#

如果您看到類似這樣的錯誤

  File "vllm/model_executor/models/registry.py", line xxx, in _raise_for_unsupported
    raise ValueError(
ValueError: Model architectures ['<arch>'] failed to be inspected. Please check the logs for more details.

這意味著 vLLM 無法匯入模型檔案。通常,這與 vLLM 構建中缺少依賴項或過時的二進位制檔案有關。請仔細閱讀日誌以確定錯誤的根本原因。

不支援的模型#

如果您看到類似這樣的錯誤

Traceback (most recent call last):
...
  File "vllm/model_executor/models/registry.py", line xxx, in inspect_model_cls
    for arch in architectures:
TypeError: 'NoneType' object is not iterable

  File "vllm/model_executor/models/registry.py", line xxx, in _raise_for_unsupported
    raise ValueError(
ValueError: Model architectures ['<arch>'] are not supported for now. Supported architectures: [...]

但您確定該模型在支援的模型列表中,則可能是 vLLM 的模型解析存在問題。在這種情況下,請按照這些步驟顯式指定模型的 vLLM 實現。

無法推斷裝置型別#

如果您看到類似 RuntimeError: Failed to infer device type 的錯誤,則表示 vLLM 無法推斷執行時環境的裝置型別。您可以檢視 程式碼,瞭解 vLLM 如何推斷裝置型別以及為何無法按預期工作。在 此 PR 之後,您還可以設定環境變數 VLLM_LOGGING_LEVEL=DEBUG 以檢視更詳細的日誌,從而幫助除錯問題。

已知問題#

  • v0.5.2v0.5.3v0.5.3.post1 中,存在由 zmq 引起的錯誤,該錯誤有時會導致 vLLM 掛起,具體取決於機器配置。解決方案是升級到最新版本的 vllm 以包含 修復

  • 為了規避 NCCL 錯誤,所有 vLLM 程序都將設定環境變數 NCCL_CUMEM_ENABLE=0 以停用 NCCL 的 cuMem 分配器。它不影響效能,但僅提供記憶體優勢。當外部程序想要與 vLLM 的程序建立 NCCL 連線時,它們也應設定此環境變數,否則,不一致的環境設定將導致 NCCL 掛起或崩潰,如 RLHF 整合討論 中所觀察到的那樣。