说句实话,很多玩大模型的朋友都有过类似经历:在 Linux 服务器上部署 vLLM,一条 pip install 接着一条 python 命令,跑得行云流水;但回到自己的 Windows 开发机上,想本地起一个 OpenAI 兼容的推理服务,就开始各种碰壁。vLLM 官方从没提供过 Windows 原生支持,很多人卡在 WSL2 环境初始化、CUDA 驱动识别、共享内存不足这一类问题上,反复折腾几个小时还没看到加载进度条。
这篇文章要解决的,就是“在 Windows 上从零跑通 vLLM,并把 Qwen3-8B-FP8 模型服务化”这件事。我会按实际操作的顺序,把环境搭建、模型下载、服务启动、API 调用和常见坑位全部过一遍。适合两类人:一类是刚接触大模型推理服务、想在本地做技术验证的开发者;另一类是已经在 Windows 上跑过 llama.cpp 或 LM Studio、现在想切换到吞吐量更高的 vLLM 的同学。全程以 WSL2 为主路径,因为这是目前在 Windows 上跑 vLLM 最稳的方案。
我尽量把每一步的“为什么这么做”讲清楚,而不只是给命令。很多教程只告诉你敲什么,不告诉你背后的机制,一旦报错就只能干瞪眼。希望你看完这篇,能具备自己排查问题的能力。
1. 为什么是 vLLM,为什么是 Qwen3-8B-FP8
1.1 vLLM 的价值,不只是“能跑模型”
先说 vLLM。你可能已经在 LM Studio、Ollama 里跑过本地模型,那些工具主打开箱即用,下载模型、点个按钮就能聊天,非常适合快速体验。但如果你想把本地模型接入自己的代码、做一个稳定的 API 服务,或者想要高吞吐、高并发的推理能力,vLLM 是更合适的选择。
vLLM 的核心竞争力主要有三点:
- PagedAttention 注意力机制:这是 vLLM 的招牌技术。它借鉴了操作系统中虚拟内存的分页思想,把 KV Cache 切成固定大小的块,减少显存碎片化,从而能同时服务更多并发请求。
- Continuous Batching(连续批处理):传统推理服务要等一个 batch 全部生成完后才能接收新请求,vLLM 可以在序列生成过程中动态插入新请求,显著提升 GPU 利用率。
- OpenAI 兼容 API:启动后直接提供
/v1/chat/completions、/v1/completions和/v1/embeddings接口,意味着你可以像调用 OpenAI 一样调用本地模型,代码层几乎零改动。
对于想在本地开发调试 Agent 应用、批量跑评测任务、或者给团队做小规模模型服务的场景,vLLM 的吞吐量优势非常明显。举个实际例子,同样的单卡 4090,llama.cpp 串行处理可能每秒只能生成几十个 token,而 vLLM 在并发 4-8 个请求时,总吞吐量能翻好几倍。
1.2 为什么选 Qwen3-8B,为什么挑 FP8 版本
选模型这件事,其实取决于你的显卡和用途。Qwen3-8B 是通义千问团队在 2025 年开源的新一代模型,8B 参数量属于“消费级显卡能扛住、能力又不至于太弱”的甜点区间。它特别适合中文场景,工具调用能力也不错,做本地 Agent 开发、知识库问答、代码辅助都很顺手。
至于 FP8 版本,关键在于显存开销。FP8(8-bit Floating Point,即 8 位浮点数)格式相比传统的 FP16/BF16,能把模型权重的大小直接砍半。Qwen3-8B-FP8 的权重文件大概在 8GB 左右,模型加载后加上 CUDA context 和 KV Cache,一张 12GB 显存的显卡就能比较从容地跑起来,16GB 或 24GB 会更宽裕。如果选 BF16 版本,权重就到 16GB 左右,12GB 显卡基本就得靠 offload 或者小 batch,体验差不少。
| 模型版本 | 权重大小 | 12GB 显存能否流畅运行 | 适用场景 |
|---|---|---|---|
| Qwen3-8B-BF16 | 约 16GB | 紧张,需开启 swap / 量化 | 显存充足(24GB+) |
| Qwen3-8B-FP8 | 约 8GB | 基本可行,推荐 | 12GB-24GB 显卡,兼顾速度与质量 |
FP8 量化是由官方(原厂)完成的,不是社区后训练的 4bit GGUF,所以精度损失很小,一般对话场景体感不出来。这也是我推荐直接上 FP8 版本的原因:不用自己量化,文件直接下载就能跑,质量有保障。
1.3 Windows 上跑 vLLM 的底层限制
vLLM 之所以在 Windows 上麻烦,核心原因是它依赖了很多 Linux 特有的内核特性。比如内存管理上对mmap和页面对齐有要求,分布式推理时依赖 NCCL 通信库,而 NCCL 官方只提供 Linux 版本。再加上 vLLM 的很多 CUDA kernel 是针对 Linux 生态编译的,在 Windows 原生环境里连编译都过不去。
这就意味着,在 Windows 上跑 vLLM 基本只有两条路:
- WSL2(Windows Subsystem for Linux 2):在 Windows 内嵌一个轻量 Linux 虚拟机,Windows 和 Linux 共享显卡驱动,本质上是“相当于有一台 Linux 机器”。
- Docker Desktop:Docker Desktop on Windows 底层也是靠 WSL2 跑 Linux 容器,再通过 GPU passthrough 把显卡映射进去。
所以你会发现,万事绕不开 WSL2。很多人被“Windows 上部署 vLLM”这句话吓住,其实拆穿了就是先搭一个 Linux 环境,然后在 Linux 环境里用你熟悉的那套流程跑 vLLM。只是搭建过程中有一些 Windows 特有的坑,比如显卡驱动版本、WSL 内存配置、文件系统性能等,这些我会在后面的章节里逐个拆开讲。
2. 环境准备:从 WSL2 到 CUDA,一步都不能省
2.1 开启 Windows 侧虚拟化与 WSL2
先把 WSL2 的基础打好。这一步如果以前没配过,建议按顺序来,别跳步。
首先是检查 Windows 版本。WSL2 需要 Windows 10 21H2 及以上,或者 Windows 11。Win10 的老版本也能装,但麻烦很多。建议把 Windows Update 跑一遍,把系统补丁打齐,再继续后续操作。
接着进 BIOS 开启虚拟化。重启电脑,进入 BIOS 设置,找到 Intel Virtualization Technology(VT-x)或 AMD SVM Mode,设为 Enabled。现在的新电脑基本默认开启,但如果是单位发的旧机器,很可能被关掉了。
然后以管理员身份打开 PowerShell 或 CMD,执行:
wsl --install这条命令会自动安装 WSL2 所需的组件,并默认安装 Ubuntu 发行版。装完后重启电脑。重启后 Ubuntu 第一次启动会让你设置 Linux 用户名和密码,记住这个密码,后面sudo需要用到。
如果你之前装过旧版 WSL,建议确认一下默认版本是不是 2:
wsl --set-default-version 2还可以用wsl -l -v查看当前发行版和版本号。看到 Ubuntu 对应的大版本是 2,就说明走对了。
这里有个小细节:WSL2 本质是一个轻量虚拟机,但它跟传统虚拟机最大的区别是,它和 Windows 共享文件系统、共享网络、共享 GPU。所以你不需要在 Ubuntu 里单独安装显卡驱动,只要 Windows 侧驱动没问题,Ubuntu 里直接就能调用 GPU。这一点很多人不知道,反而去下载 Linux 版驱动安装,结果装完 nvidia-smi 都识别不了,白折腾。
2.2 更新 Windows 显卡驱动,这是最容易被忽略的一步
这一步极其关键。WSL2 的 GPU 共享依赖 NVIDIA 官方驱动中附带的 WSL 组件,Windows 侧驱动版本过旧,Ubuntu 里就会出现 CUDA 版本对不上、nvidia-smi显示错误、vLLM 启动时报找不到设备之类的问题。
我的建议是直接去 NVIDIA 官网下载最新版驱动,或者用 GeForce Experience 更新到 Game Ready 或 Studio 驱动。Studio 驱动更适合做 AI 相关开发,但不是必须,Game Ready 驱动也能正常用。
更新完驱动后,进入 WSL2 的 Ubuntu 终端,执行:
nvidia-smi如果能显示 GPU 型号、驱动版本、CUDA 版本,比如:
+-----------------------------------------------------------------------------+ | NVIDIA-SMI 550.xx Driver Version: 550.xx CUDA Version: 12.4 | +-----------------------------------------------------------------------------+ | GPU Name Persistence-M | Bus-Id | Disp.A | Volatile Uncorr. | | 0 NVIDIA GeForce RTX 4070 ... On | 00000000:01:00.0 | On | N/A | +-----------------------------------------------------------------------------+说明 GPU 已经成功共享到 WSL2 里了。注意这里的 Driver Version 显示的是 Windows 驱动版本,CUDA Version 表示当前驱动最多支持的 CUDA 版本,不是说系统里已经装了 CUDA Toolkit。别把这两个概念搞混。
2.3 在 WSL2 中安装 CUDA Toolkit 与 Python 环境
vLLM 在pip install的时候会自动拉取它依赖的 CUDA 运行库(比如nvidia-cuda-runtime、nvidia-cudnn等)。那为什么还要手动装 CUDA Toolkit?因为部分算子编译、调试工具链、以及某些依赖库需要系统 CUDA 环境。为了避免后续踩坑,还是老老实实装一份。
打开 WSL2 Ubuntu 终端,按顺序执行:
wget https://developer.download.nvidia.com/compute/cuda/repos/wsl-ubuntu/x86_64/cuda-keyring_1.1-1_all.deb sudo dpkg -i cuda-keyring_1.1-1_all.deb sudo apt-get update sudo apt-get -y install cuda-toolkit-12-4安装版本建议和你的驱动支持的 CUDA 版本匹配。比如驱动显示 CUDA Version 12.4,就装 12.4 的 toolkit。版本不一定要完全一致,因为 vLLM 的依赖通常是动态链接的,但一致最省心。
装完后在~/.bashrc里追加环境变量:
echo 'export PATH=/usr/local/cuda/bin:$PATH' >> ~/.bashrc echo 'export LD_LIBRARY_PATH=/usr/local/cuda/lib64:$LD_LIBRARY_PATH' >> ~/.bashrc source ~/.bashrc nvcc --version看到 Cuda compilation tools 的版本信息,说明 CUDA Toolkit 安装成功。
接下来安装 Python 和虚拟环境管理工具。vLLM 目前对 Python 3.10 - 3.12 支持最好,建议用 Miniconda 来管理环境,避免系统 Python 被搞乱:
wget https://repo.anaconda.com/miniconda/Miniconda3-latest-Linux-x86_64.sh bash Miniconda3-latest-Linux-x86_64.sh安装过程中一路 yes,最后重新打开终端,conda命令就能用了。然后创建 vLLM 专用环境:
conda create -n vllm python=3.12 -y conda activate vllm到这里,环境准备基本结束。简单梳理一下:Windows 侧负责提供硬件驱动和 WSL2 运行底座,WSL2 里则是完整的 Linux 用户空间,CUDA Toolkit 和 Python 都装在这个用户空间里。
2.4 调整 WSL2 内存与磁盘配置(建议提前做)
vLLM 跑 8B 模型需要较大的可用内存。Qwen3-8B-FP8 权重加载后大约占用 8GB 显存,但 CPU 内存也要预留一部分给模型分片、tokenizer 和 Python 运行时。WSL2 的默认内存配置是物理内存的 50%,如果总内存只有 16GB,默认 WSL2 拿 8GB,很容易出现内存不足导致进程被杀。
想要微调,在 Windows 用户目录下创建或修改.wslconfig文件:
[wsl2] memory=12GB processors=8 swap=8GB localhostForwarding=true改完后在 PowerShell 中执行wsl --shutdown,再重新进入 WSL2 使配置生效。localhostForwarding=true是很关键的一项,它确保 Windows 侧通过localhost:8000就能访问到 WSL2 里 vLLM 启动的服务。
另一个容易忽略的点是磁盘空间。Qwen3-8B-FP8 模型权重 8GB 左右,加上 pip 安装的 CUDA 依赖、torch、conda 环境,总共需要预留至少 30GB 可用空间。而且下载大模型时还需要临时空间,建议预留 40GB 以上比较保险。
3. 安装 vLLM 与下载模型,最枯燥也最值得稳住的一段
3.1 pip 安装 vLLM 的完整流程
环境激活后,直接:
pip install vllm这一步会拉取大量依赖,包括 PyTorch、transformers、triton 等,体积好几个 GB,网络稍差一点就很容易中断。建议先换到国内镜像源,速度会快几个量级:
pip config set global.index-url https://mirrors.aliyun.com/pypi/simple/装完之后验证一下:
python -c "import vllm; print(vllm.__version__)"如果正常输出版本号,比如0.8.5,说明 vLLM 安装成功。我在实际部署中发现,即使版本较新,不同 vLLM 小版本之间的行为也可能有细微差异,比如某些启动参数改过名,所以遇到报错时先看看版本和官方文档是否对齐,是个好习惯。
这里顺带提一下,为什么很多人建议在 Windows 上用 Docker Desktop 装 vLLM 而不是直接 WSL2 里装?Docker 的好处是可复现性强,别人怎么装的你照着装就行,不容易被系统环境差异搞出问题。但缺点是调试不方便,想看日志、改代码、给 vLLM 打补丁都比较绕。我个人更推荐在 WSL2 里直接装,遇到问题可以直接改 Python 代码、看完整堆栈,对理解 vLLM 的运行机制帮助更大。
3.2 下载 Qwen3-8B-FP8 模型,注意别把文件放错位置
模型下载有两个来源可选:Hugging Face 和 ModelScope(魔搭)。Qwen3-8B-FP8 在两个平台都有托管。国内环境推荐用 ModelScope,速度更快更稳定。
ModelScope 下载命令:
pip install modelscope modelscope download --model Qwen/Qwen3-8B-FP8这里有两个细节要说明。第一,如果你网络条件不错,也可以直接用 Hugging Face 官方下载:
pip install huggingface_hub HF_ENDPOINT=https://hf-mirror.com huggingface-cli download Qwen/Qwen3-8B-FP8 --local-dir ./Qwen3-8B-FP8HF_ENDPOINT指向 hf-mirror,是社区提供的加速镜像,目的只是在国内环境提升下载速度,不用担心合规问题。
第二,模型下载的位置很重要。很多人习惯把模型放在 Windows 的某个盘符下,比如D:\models\Qwen3-8B-FP8,然后在 WSL2 里通过/mnt/d/models/Qwen3-8B-FP8访问。这样做在“能用”层面没问题,但性能会受到严重影响。WSL2 访问 Windows 文件系统(即/mnt/...)要经过 9P 协议转换,IO 开销很大,模型加载时读取大文件速度会明显变慢,极端情况下启动时间能差好几倍。
正确的做法是把模型放在 WSL2 自己的文件系统里,用了扩容后的 ext4 磁盘。下载完成后默认会在当前目录创建一个文件夹,这就是 WSL2 内部路径。如果习惯用 Hugging Face 的 cache 机制,模型会存在~/.cache/huggingface/下,vLLM 启动时也能自动找到。
3.3 验证模型文件完整性
下载完成后,先别急着启动,检查一下文件结构。Qwen3-8B-FP8 目录下应该有几十个文件,最关键的是:
config.json:模型配置,包括层数、注意力头数、词汇表大小等model-00001-of-00002.safetensors、model-00002-of-00002.safetensors等分片权重文件tokenizer.json、tokenizer_config.json:分词器generation_config.json:生成配置
如果是从 ModelScope 或 hf-mirror 下载的,通常默认会做完整性校验。但如果你是手动拷贝或者在中途中断过下载,建议用 sha256 校验一下文件是否完整。可以使用下面的命令:
cd Qwen3-8B-FP8 sha256sum model-*.safetensors然后和模型卡片上公布的 checksum 对照。如果对不上,删除对应文件重新下载。这一步在数据量大、网络不稳定的场景尤其值得做,因为 safetensors 这个格式在加载时一旦校验失败,报的错误可能非常难懂,定位起来很费时间。
3.4 用一个最小模型先验证环境(可选但推荐)
如果你是第一次在 WSL2 里跑 GPU 相关应用,建议先用一个小模型快速验证整个链路是否通了,再投入时间去跑 8B 大模型。这一步不会花很多时间,但能帮你把“环境问题”和“模型问题”切分清楚。
方法很简单,用 vLLM 直接跑一个几百 MB 的小模型,比如 Qwen2.5-0.5B-Instruct:
python -m vllm.entrypoints.openai.api_server \ --model Qwen/Qwen2.5-0.5B-Instruct \ --gpu-memory-utilization 0.5如果这条命令能正常加载模型并通过curl测试请求,说明 WSL2、CUDA、vLLM 三方协作正常,接下来换 Qwen3-8B-FP8 只是改个模型名的问题。如果这一步都过不去,那说明问题在环境层,不在这 8B 模型,排查范围会小很多。
4. 启动 Qwen3-8B-FP8 服务,手把手拆解参数
4.1 最简启动命令
一切就绪后,进入放置模型的目录,或者用绝对路径指定模型位置。我习惯用--model /path/to/Qwen3-8B-FP8这种方式,因为自己管理路径更可控,不依赖 cache 机制。
启动命令:
cd ~ python -m vllm.entrypoints.openai.api_server \ --model ./Qwen3-8B-FP8 \ --served-model-name qwen3-8b \ --max-model-len 8192 \ --gpu-memory-utilization 0.9 \ --port 8000解释一下每个参数:
--model:模型路径。写相对路径的前提是你已经cd到模型所在目录;建议直接用绝对路径避免歧义。--served-model-name:对外暴露的模型名称。如果你不设置,API 里返回的model字段会是路径里的名字,设置一个短名称方便下游调用。--max-model-len:最大上下文长度。Qwen3 支持很长上下文,但本地部署受显存限制。8192 对绝大多数开发调试场景足够,想更长可以慢慢往上加,直到显存吃紧。--gpu-memory-utilization:vLLM 最多允许用多少比例的显存来缓存模型和 KV Cache。0.9 表示最多用 90%,留一点余量给 CUDA context 和其他进程。显存只有 12GB 且运行中报 OOM 时,可以把这个降到 0.7-0.8,并同步缩短--max-model-len。--port:服务监听端口。默认就是 8000,写出来是为了方便改。
首次启动时,vLLM 会做很多初始化工作:加载权重、构建 CUDA graph、预热模型。日志会滚动输出:
INFO 06-xx xx:xx:xx Starting vLLM using 1 GPUs INFO 06-xx xx:xx:xx Graph capturing finished in 0.xx sec. INFO 06-xx xx:xx:xx init engine (profile, create kv cache, warmup) took ... INFO 06-xx xx:xx:xx Starting vLLM API server on http://0.0.0.0:8000看到最后一行,说明服务已经成功起来了。整个过程在 12GB 显存、PCIe 4.0 固态硬盘的环境下大约需要 1-2 分钟。
4.2 显存占用计算,心里要有笔账
很多人启动时报 OOM,根本原因是对显存需求没有概念。我来帮你算一笔账。
Qwen3-8B-FP8 权重文件大小约 8GB,加载进显存就是 8GB 左右。CUDA context 和 PyTorch 运行时大约占用 0.5-1GB。剩余部分会按--gpu-memory-utilization的比例分配给 KV Cache。假设你有 24GB 显存,设置 0.9,那么 KV Cache 可用内存约为 24 x 0.9 - 8 - 1 = 12.6GB,相当宽裕,可以支撑很长的上下文和较大的并发。如果只有 12GB,算下来 KV Cache 只剩 1.8GB 左右,那--max-model-len就得控制得短一点,比如 4096,并发数调低,不然请求一多就 OOM。
所以,显存不足的应对思路也清晰了:要么缩小模型(比如换 Qwen3-4B),要么缩短上下文长度,要么降低显存利用率(相当于限制 vLLM 对显存的使用,但这通常不能解决权重本身占用的显存不足问题)。我在 3060 12GB 上测试过,Qwen3-8B-FP8 + 4096 上下文是可以稳定运行的;如果强行把--max-model-len开到 32768,模型加载阶段就要报显存不够了。
4.3 通过 OpenAI 兼容接口做一次真实调用
服务启动后,最直接的验证方式是在终端里用 curl 发一个请求:
curl http://localhost:8000/v1/chat/completions \ -H "Content-Type: application/json" \ -d '{ "model": "qwen3-8b", "messages": [ {"role": "system", "content": "你是一个简洁的助手。"}, {"role": "user", "content": "用一句话介绍你自己。"} ], "max_tokens": 512, "temperature": 0.7 }'如果一切正常,返回的 JSON 里会包含一个choices数组,其中有模型的回复内容。这里注意一个细节:model字段的值必须和你启动时传的--served-model-name一致,否则会返回模型不存在的错误。
curl 测试通过后,可以进入 Python 用 OpenAI SDK 调用,体验更接近实际业务场景:
from openai import OpenAI client = OpenAI( base_url="http://localhost:8000/v1", api_key="EMPTY" ) response = client.chat.completions.create( model="qwen3-8b", messages=[ {"role": "user", "content": "解释一下什么是 PagedAttention,50 字以内。"} ], max_tokens=256, temperature=0.7, ) print(response.choices[0].message.content)只要输出内容是合理的模型回答,说明整条链路已经通了。接下来怎么做,完全取决于你的业务场景:接 LangChain、FastAPI 做个中转、或者用 Gradio 做个界面,都是后话了。
4.4 后台运行与开机自启动
开发调试时用前台启动没问题,但如果你想让它长期跑着,可以加nohup或使用tmux。我个人的习惯是用tmux,因为它既能后台运行,又能随时切回来看日志,比 nohup 灵活:
sudo apt-get install -y tmux tmux new -s vllm python -m vllm.entrypoints.openai.api_server ... # 按 Ctrl+b 再按 d 脱离会话,服务继续运行 # 重新接入会话:tmux attach -t vllm至于开机自启动,WSL2 的启动机制跟普通 Linux 服务不完全一样。如果你想每次开机自动起服务,可以在 Windows 下创建一个启动脚本,比如 PowerShell 脚本内容:
wsl -d Ubuntu -- tmux new-session -d -s vllm 'conda run -n vllm python -m vllm.entrypoints.openai.api_server --model ...'把这个脚本放到 shell:startup 目录或计划任务里。不过说实话,日常开发调试没必要搞这么重,需要的时候手动启动反而更可控。
5. 常见问题与排查技巧实录
5.1 CUDA 相关报错:版本不匹配与设备不可用
这是出现频率最高的一类问题,典型症状是启动日志出现:
RuntimeError: CUDA error: no kernel image is available for execution on the device或者是:
UserWarning: torch.cuda.is_available() returned False.这类报错 90% 的原因不是 CUDA Toolkit 装错了,而是 Windows 侧显卡驱动版本太旧,导致 WSL2 里的 CUDA 层识别不了 GPU。解决方法是先回到 Windows,用nvidia-smi确认驱动版本,再去 NVIDIA 官网把驱动升级到最新版。升级完别忘了wsl --shutdown再重开 WSL2。
还有一种情况是环境变量不对。如果你在~/.bashrc里手动指定过CUDA_HOME或CUDA_VISIBLE_DEVICES,检查一下路径是否存在。特别是有些人之前装过旧版 CUDA,环境变量指向了不存在的目录,vLLM 启动时会很困惑。
5.2 NCCL 与 pynccl 相关告警
你可能会在启动日志里看到类似:
(pynccl.py:113) vllm is using nccl==2.30.7这本身不是错误,是 vLLM 在打印它使用的 NCCL 版本。NCCL 是 NVIDIA 的集合通信库,主要用于多卡通信。单卡推理理论上不需要 NCCL,但 vLLM 初始化流程里会尝试加载它。WSL2 环境下偶尔会因为共享内存限制报 NCCL 相关错误:
CUDA error: invalid device pointer如果遇到这类问题,可以在启动命令前设置两个环境变量:
export NCCL_P2P_DISABLE=1 export NCCL_SHM_DISABLE=1这会关闭 NCCL 的点对点通信和共享内存通信,对单卡推理没有性能影响,但能避开很多 WSL2 下的通信兼容性坑。
5.3 “Out of memory” 与共享内存不足的应对方案
显存 OOM 的判断标准很直接:日志中出现CUDA out of memory。针对不同场景的处理方式:
| 场景 | 推荐方案 |
|---|---|
| 权重加载时就 OOM | 换更小的模型或量化版本,降低--max-model-len |
| 请求并发一高就 OOM | 降低--max-model-len,或加--max-num-seqs 4限制并发序列数 |
| 报 “No available memory for the cache blocks” | 降低--gpu-memory-utilization并缩短上下文长度 |
另外还要区分“显存 OOM”和“CPU 内存 OOM”。有时候 GPU 显存没爆,但系统内存不够,WSL2 进程会被 Linux 内核直接 kill,表现为终端里没有任何 Python 堆栈日志就退出了。处理办法就是调整.wslconfig里的memory配置,给 WSL2 分配更多内存。
共享内存shared memory不足是 WSL2 上很容易踩的坑。vLLM 的多进程 worker 之间依赖/dev/shm交换数据,而 WSL2 默认只给/dev/shm分配了物理内存的一半,如果不够用,会在启动时看到类似:
ERROR: The size of shared memory (/dev/shm) is smaller than ...解决办法是修改/etc/fstab:
sudo vi /etc/fstab在文件末尾追加:
tmpfs /dev/shm tmpfs defaults,size=8G 0 0保存后执行sudo mount -a,或用df -h /dev/shm确认生效。如果不想改 fstab,用sudo mount -o remount,size=8G /dev/shm临时解决也是可以的,只是重启后要重新执行。
5.4 端口占用与局域网访问问题
启动时报Address already in use,说明 8000 端口已经被占用。可能是之前启动过没关干净,或者 Windows 侧有其他程序占用了 8000。
排查方法:
sudo netstat -tlnp | grep 8000 # 或 sudo lsof -i:8000找到占用的 PID 后 kill 掉,或者改端口启动。记住,WSL2 中启动的服务,Windows 侧用localhost:8000就能访问,这是靠 WSL2 内置的 localhost forwarding 实现。但如果你想让局域网内其他机器访问这台 Windows 上的服务,事情就复杂一些。WSL2 默认是 NAT 网络模式,外部设备不能直接访问 WSL2 里的端口。简单临时方案是 Windows 防火墙放行后,用netsh interface portproxy做端口转发,但稳定性和性能不如直接把 WSL2 切换成镜像网络模式(Windows 11 22H2+ 支持)。这个需求如果不是很频繁,建议交给专门的部署文档,本地开发调试用 localhost 就足够了。
5.5 从 LM Studio / llama.cpp 迁移过来容易踩的坑
很多读者之前用过 LM Studio,换到 vLLM 会遇到几个观念上的差异:
- LM Studio 是 GUI 工具,模型文件管理、加载、聊天界面都打包好了;vLLM 是纯 Python 服务,一切靠命令行。别找图形界面,没有。
- LM Studio 可以通过 CPU offload 混合运行,vLLM 的设计前提是“GPU 显存要够用”。显存不够,vLLM 不会优雅降级,而是直接报错。
- LM Studio 默认用 llama.cpp 后端,模型格式是 GGUF;vLLM 读取的是 Safetensors 格式(或 AWQ/GPTQ/Marlin 等)。你之前下载的 GGUF 文件不能在 vLLM 里直接用,需要重新下载对应格式的模型。
想清楚这三点,切换过程中的困惑会少很多。
5.6 WSL2 文件 IO 慢导致模型加载卡住
最后提一个大家经常忽略的性能问题。前面说过,模型文件如果放在/mnt/下,加载时 IO 会很慢,启动可能从 1 分钟变成 5 分钟,甚至在读取大文件时表现得像卡死。
判断方法很简单,看模型加载日志是否长时间停留在同一行,比如一直在读某个 safetensors 分片文件。处理方式就是把模型移到 WSL2 的 ext4 路径下。如果模型已经下载到 Windows 盘,可以用这条命令复制:
cp -r /mnt/d/models/Qwen3-8B-FP8 ~/Qwen3-8B-FP8复制的过程可能也要花几分钟,但“复制时慢一次”远比“每次启动都慢五六分钟”划算。这也是我在本地部署多次之后摸索出的经验:模型路径这件事,值得在最初就规划好。
写在最后
这篇文章写的每一步,我基本都在自己机器上踩过一遍。最大的体会是:在 Windows 上跑 vLLM,真正的门槛不在 vLLM 本身,而在 WSL2 环境是否扎得稳。显卡驱动、内存配置、共享内存、文件系统位置,任何一个环节出了问题,都会在模型加载阶段以各种晦涩的方式爆发。
如果你第一次跑 Qwen3-8B-FP8 失败了,别急着怀疑模型或 vLLM,先回到基础环境逐项排查:nvidia-smi能不能看到 GPU,.wslconfig内存配得够不够,模型文件是不是完整。把这条链路走通之后,vLLM 的启动、调用、参数调优就都是水到渠成的事了。
最后再分享一个小技巧:遇到不懂的报错,先把日志最后一屏完整贴给 AI 或者搜索引擎,同时附上 vLLM 版本、CUDA 版本、显卡型号和完整的启动命令。很多问题你一描述清楚,答案其实已经自己浮出来了。祝你能顺利把这套服务跑起来,然后享受在 Windows 上自由调用本地大模型的体验。