BladeLLM进阶操作

BladeLLM支持多种进阶操作,本文为您介绍这些操作的配置方法。

多卡推理的部署方式

BladeLLM支持使用多卡进行模型推理和文本生成,以提升推理速度和支持更广的使用场景。 具体部署方式分为两步:

  • 对于非量化模型,直接使用blade_llm_server拉起服务即可。

  • 对于量化模型,如果是多卡部署,需要先使用blade_llm_split对量化模型进行模型拆分,再使用blade_llm_server拉起服务。

本章节将以部署2Llama模型为例,演示多卡推理的使用方式。

模型拆分

通过命令行语句blade_llm_split进行模型拆分,目前支持HuggingFace的多种模型结构,包括Bloom、Llama、ChatGLM、OPT等。

创建模型拆分任务的方法与量化任务基本相同,只需将运行命令配置为如下模型拆分命令即可,具体操作,请参见创建量化任务。任务运行成功后,拆分好的模型将按rank保存在您指定的输出路径中。

blade_llm_split \
  --tensor_parallel_size 2 \
  --model ./local/llama_model_dir \
  --output_dir ./llama_split_2_2

主要参数说明如下,可以通过-h参数查看完整帮助信息:

参数

类型

描述

tensor_parallel_size

int

模型张量并行拆分后的每组并行对应卡数。

model

str

原始浮点模型所在的目录,需要和模型配置中挂载的OSS路径相匹配。

output_dir

str

拆分后模型保存路径,需要和模型配置中挂载的OSS路径相匹配。

模型部署

使用blade_llm_server直接加载拆分后的模型路径进行推理,详情请参见BladeLLM快速入门

blade_llm_server \  
  --port 8081 \  
  --tensor_parallel_size 2 \  
  --model ./llama_split_2_2

推测解码

推测解码(即投机采样),支持使用小模型作为原模型的提词器,在保证模型精度的同时,提升整体吞吐和生成速度。

使用推测解码

使用BladeLLM引擎部署服务时,在高级配置区域配置以下关键参数,更多参数配置说明,请参见场景化部署

参数

描述

推测解码

打开推测解码开关。

草稿模型

选择公共模型或自定义模型。目前仅支持使用与原模型词表相同的小模型。

推测步长

草稿模型在每次推测中生成的Token序列长度,默认值为4。这些序列会被目标模型验证和筛选。每次预测的Token数不宜过多,推荐使用小于等于5的数值。

最大显存占有率

因投机采样功能会顺序地调用草稿模型和原模型,所以通过该参数指定的kv_cache使用的显存比例需适当降低。

运行命令预览

支持通过单击切换为自由编辑模式,来修改运行命令。具体配置示例如下:

blade_llm_server --model Qwen2-72B --attn_cls ragged_flash --draft.model Qwen2-1.5B --draft.attn_cls ragged_flash --decode_algo sps  --gamma 2

其中:

  • --decode_algo sps:表示打开投机采样功能。

  • --draft.model:通过该参数指定草稿模型。

  • --gamma:设置的推测步长。

  • --max_gpu_memory_utilization:表示最大显存占有率。

注意事项

  • 因推测解码(即投机采样)功能会顺序地调用草稿模型和原模型,所以–max_gpu_memory_utilization(最大显存占有率)指定的kv_cache使用的显存比例需适当降低。

  • 每次预测的Token数不宜过多,推荐–gamma(推测步长)使用小于等于5的数值。

LoRA服务的部署和调用

LoRA(Low-Rank Adaptation)是一种LLM微调技术,通过引入低秩矩阵实现高效快速的模型适配。LoRA的原理是在预训练模型的基础上,增加一个旁路,包含降维矩阵A和升维矩阵B,其中:

r可视为秩的大小。训练的时候固定预训练的参数,只训练AB,推理时将两路的参数叠加。

image

BladeLLM使用LoRA模型的方式如下:

在部署时,通过--model指定主模型;在请求时,通过--model指定LoRA模型。服务会按照优先级加载LoRA模型:首先尝试在GPU中查找LoRA模型,若GPU中不存在,则从CPU中查找,若CPU中也不存在,则从磁盘加载。当GPU中的LoRA模块数量达到max_loras,或CPU中的LoRA模块数量达到max_cpu_loras,系统会先卸载最久未用的LoRA模型,再加载新的LoRA模型。

目前,部署LoRA服务支持的ModuleModel列表如下:

  • Module:包括ColParaLinearWithLoRA、RowParaLinearWithLoRA、QKVProjectionWithLoRAColParaLinearWithSliceLoRA。

  • Model:包括Qwen、Qwen1.5、Qwen2Qwen2.5。

部署带有LoRA Adapter的服务

使用BladeLLM引擎部署服务时,在高级配置区域的运行命令中,配置LoRA的相关参数。更多参数配置说明,请参见场景化部署。例如通过如下示例命令启用并加载LoRA参数:

# 通过--model加载LoRA路径;通过-enable_lora启用LoRA功能。
blade_llm_server --model ~/workspace/test_models/Qwen--Qwen2-7B/ --enable_lora

其余可选配置的LoRA参数说明如下:

  • max_lora_rank:表示LoRA低秩分解矩阵的最大秩(rank),默认值为16。

  • max_loras:GPU支持存储的LoRA模块数量。

  • max_cpu_loras:CPU支持存储的LoRA模块数量,一般大于max_loras。

  • lora_dtype:LoRA中的数据类型,支持float16、bfloat16float32。

调用LoRA Adapter的服务

客户端调用服务时,通过Model指定LoRA Path,示例代码如下:

# Call local service; 其中<EAS_Service_URL>替换为服务访问地址。 
curl -X POST \
    -H "Content-Type: application/json" \ 
    -d '{
        "messages": [
        {
            "role": "system",
            "content": "You are a helpful assistant."
        },
        {
            "role": "user",
            "content": "Hello!"
        }
        ],
        "model": "~/workspace/test_models/Ko-QWEN-7B-Chat-LoRA/"
    }' \
    <EAS_Service_URL>/v1/chat/completions

结构化输出(JSON Mode)

JSON是一种广泛使用的数据交换格式。如果您希望模型严格生成JSON格式的输出,同时避免设计过于复杂的Prompt,可以使用BladeLLM提供的JSON Mode功能。

JSON Mode是一种引导解码(Guided Decoding)或称受限解码(Constrained Decoding)的结构化输出(Structured Output)方式。它会根据您提供的JSON Schema修正解码输出,从而严格生成JSON格式的输出。除JSON外,目前还支持通过正则表达式(Regex)来规范输出。

BladeLLM会根据您输入的JSON Schema或正则表达式,使用 outlines工具构造有限状态机(Finite State Machine,FSM)。该有限状态机是一张 Map<token,List<token>>形式的映射表,表示跟在任一Token之后符合约束的 List<token> 候选集。根据这个候选集,BladeLLMlogits prob过滤不符合要求的Token,就可以规范下一个词的生成。

目前,引导编码支持的格式如下:

  • JSON Schema

  • Regex Expression

支持使用HuggingFace默认分词器(tokenizer)的模型(如LLaMA Herd、Qwen1.5、Qwen2等),不支持将分词器(tokenizer)重写为bytes类型的模型(如Qwen1、GLM等)。

使用JSON Mode的方法

服务端模型部署无需改动。客户端在调用服务时,可根据需求指定guided_json 或 guided_regex

单击此处,查看示例代码

#!/usr/bin/env python

import json
import requests

TEST_REGEX = r"((25[0-5]|(2[0-4]|1\d|[1-9]|)\d)\.){3}" + r"(25[0-5]|(2[0-4]|1\d|[1-9]|)\d)"

TEST_SCHEMA = {
    "type": "object",
    "properties": {
        "name": {"type": "string"},
        "age": {"type": "integer"},
        "skills": {"type": "array", "items": {"type": "string", "maxLength": 10}, "minItems": 3},
        "work history": {
            "type": "array",
            "items": {
                "type": "object",
                "properties": {
                    "company": {"type": "string"},
                    "duration": {"type": "string"},
                    "position": {"type": "string"},
                },
                "required": ["company", "position"],
            },
        },
    },
    "required": ["name", "age", "skills", "work history"],
}

url = "http://localhost:8081/v1/completions"
# prompt = f"Give an example IPv4 address with this regex: {TEST_REGEX}\n"
prompt = f"Give an example JSON for an employee profile that fits this schema: {TEST_SCHEMA}\n"

req = {
    "prompt": prompt,
    "stream": True,
    "temperature": 0.0,
    "top_p": 0.5,
    "top_k": 10,
    "max_tokens": 200,
    # "guided_regex": TEST_REGEX,
    "guided_json": json.dumps(TEST_SCHEMA),
}
response = requests.post(
    url,
    json=req,
    headers={"Content-Type": "application/json"},
    stream=True,
)
for chunk in response.iter_lines(chunk_size=8192, decode_unicode=False):
    msg = chunk.decode("utf-8")
    if msg.startswith('data'):
        info = msg[6:]
        if info == '[DONE]':
            break
        else:
            resp = json.loads(info)
            print(resp['choices'][0]['text'], end='', flush=True)

注意事项

  • 在一个请求中只允许使用一个guided_jsonguided_regex,在并发的多个请求中,允许分别使用不同的guided_jsonguided_regex

  • 首次向服务端发起JSON Mode请求时,会有一段较长的耗时用于构造FSM,具体时长据guided_jsonguided_regex的复杂程度而定。随后,FSM将会被缓存,后续在第二次及以后发起同样的guided_jsonguided_regex请求时,无需重复构造FSM,显著减少耗时。

使用CUDA Graph

CUDA Graph特性能够通过预先createcapture一个graph,将graph里大量的kernel launch转化成一次graph launch,以降低launchdevicehost上的开销。 BladeLLM通过CUDA Graph运行模型的解码阶段,可以提高解码速度。

配置CUDA Graph

使用BladeLLM引擎部署服务时,在高级配置区域的运行命令中,添加以下关键配置。更多参数配置说明,请参见场景化部署

参数

类型

描述

disable_cuda_graph

bool

用来关闭CUDA Graph功能,默认是False。运行时,首次capture会有日志信息caching graph of graph_batch_size=xx,说明CUDA Graph功能已经打开。

cuda_graph_max_batch_size

int

表示可以capture的最大batch size。例如--cuda_graph_max_batch_size,只有batch size小于64时使用CUDA Graph。

说明

cuda_graph_max_batch_sizecuda_graph_batch_sizes的范围冲突时,系统会忽略cuda_graph_max_batch_size。

cuda_graph_batch_sizes

List[int]

通过传入一个INT数组,指定范围和padding方法。例如--cuda_graph_batch_sizes 8 16 64,则表示当batch size不大于64时,padding到列表里不小于batch size的最接近的长度,当batch size超过列表中最大的数时,则不使用CUDA Graph。

注意事项

保存CUDA Graph会消耗显存,所以通过--max_gpu_memory_utilization指定的kv_cache使用的显存比例,需适当降低。

部署环境检查

BladeLLM提供blade_llm_check 工具来检查您的环境是否符合部署要求,以便提前排除潜在问题。

  1. 执行检查。

    使用BladeLLM引擎部署服务时,在高级配置区域配置如下运行命令。更多参数配置说明,请参见场景化部署

    blade_llm_check
  2. 查看输出结果。

    单击目标服务名称,切换到日志页签,查看输出结果。输出结果示例如下:

           check_shm       PASS  -  shared Memory is 198269968384 bytes
        check_pb_env       PASS  -  Env var PROTOCOL_BUFFERS_PYTHON_IMPLEMENTATION=None is OK
    check_flops_diff       PASS  -  max flops diff amoung 2 devices is 1.00
    
    PASS 3, WARNING 0, FAILED 0
    

    其中:

    • 每行的输出表示一个检查项,包括检查项名称、检查结果(PASS、WARNING、FAILED)和详细信息。

    • 输出的最后一行会汇总所有检查项的结果。

    您也可以通过程序的退出码来确认是否所有检查都通过。当所有检查都通过时,blade_llm_check 会返回0,否则返回1。示例如下:

    time="2025-05-22T09:58:02Z" level=info msg="program stopped with status:exit status 0" program=/bin/sh

检查通过后,您可以停止检测服务,并重新使用BladeLLM引擎部署服务,详情请参见BladeLLM快速入门