Edge0-145B 属于百亿级参数中的“大块头”:参数规模 145B,意味着仅权重本身在全精度下就是几百 GB 的量级。这个体量不可能像 7B、8B 模型那样“双击就跑”,但只要算清楚内存账、选对量化档位、把 CPU 与 GPU 的分工配置好,在 64GB 以上内存的个人工作站上跑起来是可行的。这篇教程把整个流程拆成可照抄的步骤。
适用场景
适合手头有一台大内存工作站(64GB 内存起步,带一张 24GB 级显卡更佳)或高配统一内存笔记本,希望把 145B 级模型放在本地跑、用于长文写作、代码审查、私有数据问答等不方便调用云端 API 的场景。这套方案解决的核心问题是:显存装不下完整模型时,如何用“GPU 跑热层 + CPU 跑冷层”的混合方式把模型跑起来,并用合适的量化档位在质量与速度之间取得平衡。
环境与前置条件
硬件门槛(先算账,再动手)
145B 权重在不同精度下的粗略占用(按每参数字节数估算,实际以生成文件的大小为准):
| 精度档位 | 每参数约占比特 | 权重大致占用 | 说明 |
|---|---|---|---|
| BF16 / F16 | 16 | 约 290 GB | 原始权重与转换中间产物 |
| FP8 | 8 | 约 145 GB | 需较新显卡支持 |
| Q8_0 | 8.5 | 约 154 GB | 近乎无损,体积大 |
| Q6_K | 6.6 | 约 119 GB | 质量与体积的折中 |
| Q5_K_M | 5.7 | 约 103 GB | 推荐的下限之一 |
| Q4_K_M | 4.9 | 约 88 GB | 个人环境的主力档位 |
| Q3_K_M | 3.9 | 约 71 GB | 内存吃紧时使用 |
| Q2_K | 2.6 | 约 48 GB | 质量下降明显,不推荐长期使用 |
由此得出几条硬性前提:
- 磁盘:如果要做完整的“下载原始权重 → 转 GGUF → 量化”流程,需要预留 290GB(原始)+ 290GB(F16 中间产物)+ 目标量化文件的空间,总计 700GB 以上比较稳妥。直接下载他人做好的 GGUF 文件则只需目标文件大小的 1.2 倍左右。
- 内存:运行 Q4_K_M 时,内存 + 显存的总和要能装下约 88GB 权重,再加上 AI 词典:KV Cache">KV Cache 和运行时开销,建议 128GB 内存;64GB 内存只能跑 Q3 或 Q2 档。
- 显存:24GB 显卡可以把一部分层放进显存加速,剩下的留给 CPU。若要全部放显存,4bit 量化也需要 2 张 48GB 或 4 张 24GB 显卡。
- CPU 与内存带宽:混合推理时 CPU 侧是瓶颈,内存带宽越高越好,双通道以上、频率较高的大容量内存收益明显。
软件前置
- Linux(推荐)或 macOS;Windows 建议走 WSL2
- Python 3.10 及以上
- Git、CMake 3.20 及以上、C++ 编译器(gcc 或 clang)
- NVIDIA 显卡需安装较新的驱动与 CUDA Toolkit(版本以官方文档当前版本为准)
- 磁盘剩余空间按上面的表预留
分步骤部署
第 1 步:确认硬件与可用资源
在动手前先把机器状态记录清楚,后面排查问题都靠它。
```bash
内存与交换分区
free -h
显卡与显存
nvidia-smi
磁盘余量(选一个空间最大的挂载点)
df -h
```
成功标志:free -h 里的 available 一栏大于你打算跑的量化档位所需内存;nvidia-smi 能正常输出显卡型号与显存总量。如果 nvidia-smi 报 command not found,先解决驱动问题再继续。
第 2 步:准备 Python 环境与下载工具
单独建一个虚拟环境,避免和系统 Python 冲突。
```bash
python3 -m venv ~/edge0-env
source ~/edge0-env/bin/activate
pip install -U pip
pip install -U "huggingface_hub[cli]" hf_transfer modelscope
```
hf_transfer 是 Hugging Face 的加速下载组件,对大文件效果明显。装完后 hf --help 或 huggingface-cli --help 能打印帮助信息即为成功(不同版本命令名不同,两者试一个即可)。
第 3 步:获取权重
权重仓库地址、文件名与分片数量请以模型的官方仓库页面为准,下面用占位符表示。
方式一,从 Hugging Face 拉取:
```bash
export HF_ENABLE_HF_TRANSFER=1
export HF_HOME=~/hf-cache
新版本 CLI
hf download <组织名>/<模型仓库名> --local-dir ./edge0-145b
老版本 CLI 用这个
huggingface-cli download <组织名>/<模型仓库名> --local-dir ./edge0-145b
```
方式二,国内网络或 Hugging Face 不通时走 ModelScope:
```bash
modelscope download --model <组织名>/<模型仓库名> --local_dir ./edge0-145b
```
方式三,如果只想跑推理、不想自己量化,直接下载社区做好的 GGUF 单文件(搜索模型名 + GGUF 即可找到对应仓库),只下载 Q4_K_M 那一个文件,能省下几百 GB 磁盘。
成功标志:ls -lh ./edge0-145b 能看到 config.json、分词器文件以及若干个 .safetensors 分片,总大小与模型卡上标注的一致。
第 4 步:编译推理引擎(以 llama.cpp 为例)
llama.cpp 对混合 CPU/GPU 推理支持成熟,是这类“显存装不下”场景的主力工具。
```bash
git clone https://github.com/ggml-org/llama.cpp
cd llama.cpp
NVIDIA 显卡
cmake -B build -DGGML_CUDA=ON -DCMAKE_BUILD_TYPE=Release
Apple Silicon 用这个
cmake -B build -DGGML_METAL=ON -DCMAKE_BUILD_TYPE=Release
纯 CPU
cmake -B build -DCMAKE_BUILD_TYPE=Release
cmake --build build --config Release -j $(nproc)
```
成功标志:build/bin/ 目录下出现 llama-cli、llama-server、llama-quantize、llama-bench 这几个可执行文件。跑一下 ./build/bin/llama-cli --version 能打印版本信息即可。
需要注意:模型架构日新月异,如果后面加载时报“不认识的架构”,回到这一步 git pull 后重新编译通常就能解决。
第 5 步:转换成 GGUF 并量化
如果第 3 步已经下载了现成 GGUF,跳过本步。
```bash
cd llama.cpp
转成 F16 GGUF(中间产物,体积接近原始权重)
python convert_hf_to_gguf.py ../edge0-145b \
--outfile ../edge0-145b-f16.gguf \
--outtype f16
量化为 Q4_K_M
./build/bin/llama-quantize \
../edge0-145b-f16.gguf \
../edge0-145b-Q4_K_M.gguf \
Q4_K_M
```
转换这一步会占用大量内存,建议在内存充裕的机器上做,或者先小批量验证脚本能跑通。量化过程可能持续几十分钟到数小时,取决于磁盘与 CPU。
成功标志:ls -lh ../edge0-145b-Q4_K_M.gguf 显示文件大小落在上表 Q4_K_M 那一档的预期区间内(约 80–95GB 之间都属正常)。量化完成后,F16 中间文件可以删掉腾空间。
量化档位怎么选:先用 Q4_K_M 打通全流程,这是质量损失与体积的常见平衡点。如果内存富裕且对质量敏感,升到 Q5_K_M 或 Q6_K;如果只有 64GB 内存,退到 Q3_K_M。Q2_K 只建议用来验证流程是否跑通,不建议作为长期使用档位。
第 6 步:确定 GPU 卸载层数
这是整个部署里最关键的一步。-ngl(卸载到 GPU 的层数)设得太高会 OOM,设得太低则慢。先用 0 测出 CPU 基线,再逐级往上加。
```bash
基线:全部放 CPU
./build/bin/llama-bench \
-m ../edge0-145b-Q4_K_M.gguf \
-ngl 0 -p 256 -n 64
逐步增加卸载层数,每次观察显存占用
./build/bin/llama-bench \
-m ../edge0-145b-Q4_K_M.gguf \
-ngl 20 -p 256 -n 64
用 nvidia-smi 另开一个窗口盯着显存
watch -n 1 nvidia-smi
```
经验做法是:把 -ngl 往上加,直到 nvidia-smi 显示显存占用接近但不超过总容量的 90%,再回退几层留出 KV Cache 余量。把最终确定的数字记下来,后面启动服务时固定使用。
如果这个模型是 MoE 架构(以模型卡说明为准),llama.cpp 还提供 --n-cpu-moe 一类参数,可以把专家层留在内存、只把注意力层放显存,通常比单纯调 -ngl 更划算。
第 7 步:启动推理服务
命令行交互试跑:
```bash
./build/bin/llama-cli \
-m ../edge0-145b-Q4_K_M.gguf \
-ngl 30 \
-c 8192 \
-fa \
--no-warmup \
-p "用三句话解释什么是量化" \
-n 256
```
参数含义:-c 是上下文长度,越大 KV Cache 占用越高;-fa 开启 Flash Attention,能显著降低长上下文的内存开销;-ngl 是上一步确定的值。
启动 OpenAI 兼容的 HTTP 服务:
```bash
./build/bin/llama-server \
-m ../edge0-145b-Q4_K_M.gguf \
-ngl 30 \
-c 8192 \
-fa \
--host 0.0.0.0 \
--port 8080 \
--metrics
```
成功标志:终端打印出 server is listening on http://0.0.0.0:8080 之类的信息,并且模型加载完成的日志里能看到分配了多少层到 GPU、多少层在 CPU。
如果用 Ollama 管理更方便,可以写一个 Modelfile:
```
FROM ./edge0-145b-Q4_K_M.gguf
PARAMETER num_gpu 30
PARAMETER num_ctx 8192
```
```bash
ollama create edge0-145b:q4km -f Modelfile
ollama run edge0-145b:q4km
```
注意:上下文长度、KV Cache 字节数会随 -c 线性增长,-c 从 8192 调到 32768,内存占用可能多出好几 GB,调参时务必同步观察 free -h 和 nvidia-smi。
验证部署是否成功
验证一:进程正常响应
```bash
curl -s http://127.0.0.1:8080/health
```
预期返回表示健康的 JSON(llama.cpp 的 server 会返回类似 {"status":"ok"} 的内容)。
验证二:发一个真实的推理请求
```bash
curl -s http://127.0.0.1:8080/v1/chat/completions \
-H "Content-Type: application/json" \
-d '{
"messages": [{"role": "user", "content": "用一句话说明你是什么模型"}],
"max_tokens": 128,
"temperature": 0.7
}'
```
预期返回标准 OpenAI 格式的 JSON,choices[0].message.content 里有连贯的中文回答。能返回完整句子而不只是标点碎片,说明分词器、权重、采样都正常。
验证三:测实际速度
```bash
./build/bin/llama-bench \
-m ../edge0-145b-Q4_K_M.gguf \
-ngl 30 -p 512 -n 128
```
输出里会给出 prompt 处理速度(tokens/s)和生成速度(tokens/s)。记录这两个数字作为基线,日后改配置或升级硬件时用作对比。具体数值取决于内存带宽、量化档位、卸载层数,不同机器差异很大,以本机实测为准。
验证四:长上下文不崩
把 -c 调到 16384,重新发一个几千字的输入,观察是否 OOM。这一步能提前暴露 KV Cache 估算不足的问题。
常见报错与解决
报错一:CUDA error: out of memory 或 ggml_cuda_host_malloc: allocation failure
→ 原因:-ngl 设置过高,或者上下文长度过大导致 KV Cache 挤占显存。
→ 解决:降低卸载层数并缩短上下文,先跑通再加。
```bash
./build/bin/llama-server -m ../edge0-145b-Q4_K_M.gguf -ngl 24 -c 4096 -fa
```
报错二:error loading model: unknown model architecture
→ 原因:llama.cpp 版本早于模型发布,不认识新的架构字段。
→ 解决:更新源码后重新编译。
```bash
cd llama.cpp
git pull
cmake --build build --config Release -j $(nproc)
```
报错三:进程被系统杀掉,日志里只有 Killed
→ 原因:触发系统 OOM Killer。常见于开了 --mlock 锁定内存,或机器上还跑着其他吃内存的程序。
→ 解决:去掉 --mlock,关闭不必要的进程,必要时临时增加交换分区。
```bash
查看是不是被 OOM Killer 干掉的
dmesg | tail -n 50 | grep -i "killed process"
临时加 64G swap(按需调整)
sudo fallocate -l 64G /swapfile
sudo chmod 600 /swapfile
sudo mkswap /swapfile
sudo swapon /swapfile
```
注意交换分区只能保命,跑在这个上面速度会明显变慢。
报错四:401 Client Error: Unauthorized 或下载中断
→ 原因:仓库需要授权(gated model),或未登录、网络不稳。
→ 解决:先登录再下载,并开启断点续传。
```bash
hf auth login
或
huggingface-cli login
下载中断后重复执行同一条 download 命令即可续传
```
报错五:ValueError: Tokenizer class ... does not exist 或转换脚本报字段缺失
→ 原因:转换脚本与模型仓库不匹配,通常是模型用了较新的分词器实现。
→ 解决:升级转换依赖后重试。
```bash
source ~/edge0-env/bin/activate
pip install -U transformers sentencepiece protobuf
cd llama.cpp && git pull
python convert_hf_to_gguf.py ../edge0-145b --outfile ../edge0-145b-f16.gguf --outtype f16
```
报错六:No CUDA GPUs are available
→ 原因:编译时没开 CUDA 后端,或驱动与 Toolkit 版本不匹配。
→ 解决:确认驱动正常后,带 CUDA 选项重新编译。
```bash
nvidia-smi
cmake -B build -DGGML_CUDA=ON -DCMAKE_BUILD_TYPE=Release
cmake --build build --config Release -j $(nproc)
```
后续维护
备份
原始权重和量化产物都要留。量化文件重新生成一次要花不少时间,建议用硬链接或快照保留一份,并记录生成时的参数(量化类型、llama.cpp 提交号),方便复现。
```bash
sha256sum ../edge0-145b-Q4_K_M.gguf > edge0-q4km.sha256
```
升级
llama.cpp 更新频繁,升级前先备份当前可用的 build/ 目录。升级后如果新版本反而不认模型,回退到上一个可用提交即可,不必死磕。
```bash
cd llama.cpp
git log --oneline -5 # 记下当前提交
git pull
cmake --build build --config Release -j $(nproc)
```
量化格式本身也在演进,如果新版本支持了更高效的量化类型,可以在硬件不变的前提下重新量化一次,通常能换来体积或速度上的改善。
日志与监控
启动服务时加 --metrics 参数,即可用 Prometheus 抓取请求数、延迟、token 吞吐等指标:
```bash
curl -s http://127.0.0.1:8080/metrics | head -n 40
```
日常巡检看三样东西:显存占用(nvidia-smi)、系统内存与 swap 使用(free -h)、服务日志里的报错行。把 llama-server 的输出重定向到文件并配合日志轮转,避免日志把磁盘撑满。
长期运行建议
用 systemd 或进程管理器托管服务,配置自动重启;把 -ngl、-c、-fa 这些调好的参数写进启动脚本而不是手敲;对上下文长度设置上限,防止单个超长请求把内存打满影响其他服务。
最后提醒一句:模型仓库的文件名、分片数量、推荐的推理参数都会随版本变化,动手前先去官方仓库页面核对一遍当前的文件清单与参数说明,比照抄任何二手教程都可靠。
