前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >vLLM: 加速AI推理的利器

vLLM: 加速AI推理的利器

原创
作者头像
buzzfrog
发布2024-07-22 21:22:28
2310
发布2024-07-22 21:22:28
举报
文章被收录于专栏:云上修行

为什么LLM服务如此具有挑战性?

计算资源

由于LLM需要处理大量的参数来进行预测,这可能从70亿参数增加到3210亿,部署这样的模型可能需要大量的资源和优化,而不是使用传统的方法来部署机器学习模型。

延迟

当句子或令牌复杂时,处理结果需要几分钟时间,这可能在大规模或真实世界的业务中造成问题。例如,一家公司可能在产品Q&A聊天机器人中应用LLM,缓慢的响应可能会让用户感到沮丧。因此,应用一些方法来降低延迟是一个好的实践。

成本

在大规模系统中或系统中有多个LLM时,会消耗大量预算,因为LLMs使用大量资源进行处理,作为一个MLE,找到一种利用资源的方法将为系统带来财务效益。例如,降低每次请求的成本。

什么是vLLM?

这个项目来自于加州大学伯克利分校的学生们,他们热衷于优化服务LLMs的性能。许多系统在服务LLMs时花费了大量的资源,然而,使用简单的方法部署时响应时间却很差。因此,vLLM团队提出了一种新方法来解决这个问题,通过使用操作系统的虚拟内存设计,可提升LLM服务性能约24倍,同时相比传统方法使用的GPU内存减半。为了集成到您的系统中,vLLM提供了一个简单的接口,让机器学习工程师通过Python接口进行开发,您可以在不使用复杂包或依赖的情况下将其集成到您的系统中。

vLLM的秘密武器是什么?

为了理解vLLM如何实现降低延迟和优化系统总体性能的目标,我们应该了解vLLM的瓶颈以及如何解决这个问题。

内存使用问题

大型语言模型(LLM)本质上是一个注意力神经网络的分支,或者有些人将其称为变压器,具有基于模型的自定义解码。因此,我们需要理解一个关键概念:LLM是如何生成令牌的。

内存分片

本质上,请求的KV缓存是存储在连续的内存空间中的,因为许多深度学习框架计算都需要将张量值存储在连续的内存中。然而,根据模型架构的不同,KV缓存可能会随时间增长或缩小,这种存储格式可能会导致问题,并且对于计算来说并不实用。

如何克服这个问题

vLLM团队开发了一种新的注意力算法,称为PageAttention,其灵感来自于操作系统的虚拟内存概念。可以将块想象为页面,令牌想象为字节,请求想象为进程。

使用PageAttention的另一好处是,它允许系统共享KV缓存,因为它将令牌存储在非连续的内存中。这使得LLM在许多应用程序中得以利用。

vLLM的OpenAI兼容服务器

如果你希望快速的使用vLLM启动一个OpenAI兼容的服务器,可以如下执行:

命令行安装:

代码语言:bash
复制
pip3 install vllm==0.5.1 -i https://pypi.tuna.tsinghua.edu.cn/simple

正常启动(以Qwen2-7B为例):

代码语言:bash
复制
python -m vllm.entrypoints.openai.api_server --model Qwen/Qwen2-7B-Instruct

其他启动参数详解:

代码语言:bash
复制
python3 -m vllm.entrypoints.openai.api_server -h
用法: api_server.py [-h] [--host HOST] [--port PORT] [--uvicorn-log-level {debug,info,warning,error,critical,trace}] [--allow-credentials] [--allowed-origins ALLOWED_ORIGINS] [--allowed-methods ALLOWED_METHODS] [--allowed-headers ALLOWED_HEADERS]
[--api-key API_KEY] [--lora-modules LORA_MODULES [LORA_MODULES ...]] [--chat-template CHAT_TEMPLATE] [--response-role RESPONSE_ROLE] [--ssl-keyfile SSL_KEYFILE] [--ssl-certfile SSL_CERTFILE] [--ssl-ca-certs SSL_CA_CERTS]
[--ssl-cert-reqs SSL_CERT_REQS] [--root-path ROOT_PATH] [--middleware MIDDLEWARE] [--model MODEL] [--tokenizer TOKENIZER] [--skip-tokenizer-init] [--revision REVISION] [--code-revision CODE_REVISION]
[--tokenizer-revision TOKENIZER_REVISION] [--tokenizer-mode {auto,slow}] [--trust-remote-code] [--download-dir DOWNLOAD_DIR] [--load-format {auto,pt,safetensors,npcache,dummy,tensorizer,bitsandbytes}]
[--dtype {auto,half,float16,bfloat16,float,float32}] [--kv-cache-dtype {auto,fp8,fp8_e5m2,fp8_e4m3}] [--quantization-param-path QUANTIZATION_PARAM_PATH] [--max-model-len MAX_MODEL_LEN]
[--guided-decoding-backend {outlines,lm-format-enforcer}] [--distributed-executor-backend {ray,mp}] [--worker-use-ray] [--pipeline-parallel-size PIPELINE_PARALLEL_SIZE] [--tensor-parallel-size TENSOR_PARALLEL_SIZE]
[--max-parallel-loading-workers MAX_PARALLEL_LOADING_WORKERS] [--ray-workers-use-nsight] [--block-size {8,16,32}] [--enable-prefix-caching] [--disable-sliding-window] [--use-v2-block-manager]
[--num-lookahead-slots NUM_LOOKAHEAD_SLOTS] [--seed SEED] [--swap-space SWAP_SPACE] [--gpu-memory-utilization GPU_MEMORY_UTILIZATION] [--num-gpu-blocks-override NUM_GPU_BLOCKS_OVERRIDE]
[--max-num-batched-tokens MAX_NUM_BATCHED_TOKENS] [--max-num-seqs MAX_NUM_SEQS] [--max-logprobs MAX_LOGPROBS] [--disable-log-stats]
[--quantization {aqlm,awq,deepspeedfp,fp8,marlin,gptq_marlin_24,gptq_marlin,gptq,squeezellm,compressed-tensors,bitsandbytes,None}] [--rope-scaling ROPE_SCALING] [--rope-theta ROPE_THETA] [--enforce-eager]
[--max-context-len-to-capture MAX_CONTEXT_LEN_TO_CAPTURE] [--max-seq-len-to-capture MAX_SEQ_LEN_TO_CAPTURE] [--disable-custom-all-reduce] [--tokenizer-pool-size TOKENIZER_POOL_SIZE] [--tokenizer-pool-type TOKENIZER_POOL_TYPE]
[--tokenizer-pool-extra-config TOKENIZER_POOL_EXTRA_CONFIG] [--enable-lora] [--max-loras MAX_LORAS] [--max-lora-rank MAX_LORA_RANK] [--lora-extra-vocab-size LORA_EXTRA_VOCAB_SIZE] [--lora-dtype {auto,float16,bfloat16,float32}]
[--long-lora-scaling-factors LONG_LORA_SCALING_FACTORS] [--max-cpu-loras MAX_CPU_LORAS] [--fully-sharded-loras] [--device {auto,cuda,neuron,cpu,openvino,tpu,xpu}] [--image-input-type {pixel_values,image_features}]
[--image-token-id IMAGE_TOKEN_ID] [--image-input-shape IMAGE_INPUT_SHAPE] [--image-feature-size IMAGE_FEATURE_SIZE] [--image-processor IMAGE_PROCESSOR] [--image-processor-revision IMAGE_PROCESSOR_REVISION]
[--disable-image-processor] [--scheduler-delay-factor SCHEDULER_DELAY_FACTOR] [--enable-chunked-prefill] [--speculative-model SPECULATIVE_MODEL] [--num-speculative-tokens NUM_SPECULATIVE_TOKENS]
[--speculative-draft-tensor-parallel-size SPECULATIVE_DRAFT_TENSOR_PARALLEL_SIZE] [--speculative-max-model-len SPECULATIVE_MAX_MODEL_LEN] [--speculative-disable-by-batch-size SPECULATIVE_DISABLE_BY_BATCH_SIZE]
[--ngram-prompt-lookup-max NGRAM_PROMPT_LOOKUP_MAX] [--ngram-prompt-lookup-min NGRAM_PROMPT_LOOKUP_MIN] [--model-loader-extra-config MODEL_LOADER_EXTRA_CONFIG] [--preemption-mode PREEMPTION_MODE]
[--served-model-name SERVED_MODEL_NAME [SERVED_MODEL_NAME ...]] [--qlora-adapter-name-or-path QLORA_ADAPTER_NAME_OR_PATH] [--otlp-traces-endpoint OTLP_TRACES_ENDPOINT] [--engine-use-ray] [--disable-log-requests]
[--max-log-len MAX_LOG_LEN]

vLLM与OpenAI兼容的RESTful API服务器。

可选参数:
  -h, --help            显示此帮助信息并退出
  --host HOST           主机名
  --port PORT           端口号
  --uvicorn-log-level {debug,info,warning,error,critical,trace}
                        uvicorn的日志等级
  --allow-credentials   允许凭证
  --allowed-origins ALLOWED_ORIGINS
                        允许的来源
  --allowed-methods ALLOWED_METHODS
                        允许的方法
  --allowed-headers ALLOWED_HEADERS
                        允许的头信息
  --api-key API_KEY     如果提供,服务器将要求在头信息中提供此密钥。
  --lora-modules LORA_MODULES [LORA_MODULES ...]
                        LoRA模块配置,格式为name=path。可以指定多个模块。
  --chat-template CHAT_TEMPLATE
                        聊天模板的文件路径,或为指定模型的单行形式的模板
  --response-role RESPONSE_ROLE
                        如果`request.add_generation_prompt=true`,则返回的角色名称。
  --ssl-keyfile SSL_KEYFILE
                        SSL密钥文件的文件路径
  --ssl-certfile SSL_CERTFILE
                        SSL证书文件的文件路径
  --ssl-ca-certs SSL_CA_CERTS
                        CA证书文件
  --ssl-cert-reqs SSL_CERT_REQS
                        是否需要客户端证书(参考标准库ssl模块)
  --root-path ROOT_PATH
                        当应用程序位于基于路径的路由代理之后时的FastAPI root_path
  --middleware MIDDLEWARE
                        应用于应用的附加ASGI中间件。我们接受多个--middleware参数。其值应为一个导入路径。如果提供了函数,vLLM会将其添加到服务器使用@app.middleware('http')。如果提供了类,则vLLM会使用app.add_middleware()添加它。
  --model MODEL         使用的huggingface模型名称或路径。
  --tokenizer TOKENIZER
                        使用的huggingface分词器名称或路径。如果未指定,则使用模型名称或路径。
  --skip-tokenizer-init
                        跳过分词器和反分词器的初始化
  --revision REVISION   要使用的特定模型版本。它可以是一个分支名称、一个标签名称或一个提交id。如果未指定,将使用默认版本。
  --code-revision CODE_REVISION
                        用于模型代码在Hugging Face Hub的特定修订版本。它可以是一个分支名称、一个标签名称或一个提交id。如果未指定,将使用默认版本。
  --tokenizer-revision TOKENIZER_REVISION
                        要使用的huggingface分词器的修订版本。它可以是一个分支名称、一个标签名称或一个提交id。如果未指定,将使用默认版本。
  --tokenizer-mode {auto,slow}
                        分词器模式。* "auto"将使用快速分词器(如果可用)。* "slow"将总是使用慢分词器。
  --trust-remote-code   信任来自huggingface的远程代码。
  --download-dir DOWNLOAD_DIR
                        下载并加载权重的目录,默认为huggingface的默认缓存目录。
  --load-format {auto,pt,safetensors,npcache,dummy,tensorizer,bitsandbytes}
                        用于加载模型权重的格式。* "auto"将尝试以safetensors格式加载权重,并在safetensors格式不可用时回退到pytorch bin格式。* "pt"将以pytorch bin格式加载权重。* "safetensors"将以safetensors格式加载权重。* "npcache"将以pytorch格式加载权重并存储numpy缓存以加速加载。* "dummy"将以随机值初始化权重,主要用于性能分析。* "tensorizer"将使用来自CoreWeave的tensorizer加载权重。有关更多信息,请参见示例部分中的Tensorize vLLM模型脚本。* "bitsandbytes"将使用bitsandbytes量化加载权重。
  --dtype {auto,half,float16,bfloat16,float,float32}
                        模型权重和激活的数据类型。* "auto"将对FP32和FP16模型使用FP16精度,对BF16模型使用BF16精度。* "half"用于FP16。推荐用于AWQ量化。* "float16"与"half"相同。* "bfloat16"用于平衡精度和范围。* "float"是FP32精度的简写。* "float32"用于FP32精度。
  --kv-cache-dtype {auto,fp8,fp8_e5m2,fp8_e4m3}
                        kv缓存存储的数据类型。如果为"auto",将使用模型数据类型。CUDA 11.8+支持fp8(=fp8_e4m3)和fp8_e5m2。ROCm(AMD GPU)支持fp8(=fp8_e4m3)
  --quantization-param-path QUANTIZATION_PARAM_PATH
                        包含KV缓存比例因子的JSON文件路径。当KV缓存数据类型为FP8时,通常应当提供此文件。否则,KV缓存比例因子默认为1.0,可能导致准确性问题。FP8_E5M2(未缩放)仅在CUDA版本大于11.8时支持。在ROCm(AMD GPU)上,相反,支持FP8_E4M3以满足常见的推理标准。
  --max-model-len MAX_MODEL_LEN
                        模型上下文长度。如果未指定,将从模型配置自动派生。
  --guided-decoding-backend {outlines,lm-format-enforcer}
                        哪个引擎将默认用于指导解码(JSON架构/正则表达式等)。当前支持https://github.com/outlines-dev/outlines 和 https://github.com/noamgat/lm-format-enforcer。可通过请求中的guided_decoding_backend参数覆盖。
  --distributed-executor-backend {ray,mp}
                        用于分布式服务的后端。当使用多于1个GPU时,如果安装了"ray"将自动设置为"ray",否则设置为"mp"(多进程)。
  --worker-use-ray    已弃用,请使用--distributed-executor-backend=ray。
  --pipeline-parallel-size PIPELINE_PARALLEL_SIZE, -pp PIPELINE_PARALLEL_SIZE
                        管道阶段的数量。
  --tensor-parallel-size TENSOR_PARALLEL_SIZE, -tp TENSOR_PARALLEL_SIZE
                        张量并行副本的数量。
  --max-parallel-loading-workers MAX_PARALLEL_LOADING_WORKERS
                        分多批次顺序加载模型,以避免在使用张量并行和大型模型时发生RAM OOM。
  --ray-workers-use-nsight
                        如果指定,使用nsight对Ray工作节点进行分析。
  --block-size {8,16,32}
                        连续token块的token块大小。
  --enable-prefix-caching
                        启用自动前缀缓存。
  --disable-sliding-window
                        禁用滑动窗口,设置为滑动窗口大小
  --use-v2-block-manager
                        使用BlockSpaceMangerV2。
  --num-lookahead-slots NUM_LOOKAHEAD_SLOTS
                        实验性调度配置,必要用于对初始解码的推测。这将被推测配置在未来替代;它目前的存在是为了直到那时启用正确性测试。
  --seed SEED           操作的随机种子。
  --swap-space SWAP_SPACE
                        每GPU的CPU交换空间大小(GiB)。
  --gpu-memory-utilization GPU_MEMORY_UTILIZATION
                        用于模型执行器的GPU内存的使用比例,可以从0到1的范围。例如,0.5的值将意味着50%的GPU内存利用率。如果未指定,将使用0.9的默认值。
  --num-gpu-blocks-override NUM_GPU_BLOCKS_OVERRIDE
                        如果指定,忽略GPU性能测试结果并使用这个数字的GPU块。用于测试抢占。
  --max-num-batched-tokens MAX_NUM_BATCHED_TOKENS
                        每次迭代的最大批处理token数。
  --max-num-seqs MAX_NUM_SEQS
                        每次迭代的最大序列数。
  --max-logprobs MAX_LOGPROBS
                        返回logprobs的最大数量,如果在SamplingParams中指定了logprobs。
  --disable-log-stats   禁用日志统计。
  --quantization {aqlm,awq,deepspeedfp,fp8,marlin,gptq_marlin_24,gptq_marlin,gptq,squeezellm,compressed-tensors,bitsandbytes,None}, -q {aqlm,awq,deepspeedfp,fp8,marlin,gptq_marlin_24,gptq_marlin,gptq,squeezellm,compressed-tensors,bitsandbytes,None}
                        用于量化权重的方法。如果None,我们首先检查模型配置文件中的`quantization_config`属性。如果那是None,我们假设模型权重未量化,并使用`dtype`确定权重的数据类型。
  --rope-scaling ROPE_SCALING
                        RoPE缩放配置的JSON格式。例如,{"type":"dynamic","factor":2.0}
  --rope-theta ROPE_THETA
                        使用`rope_scaling`的RoPE theta。在某些情况下,改变RoPE theta可以提高缩放模型的性能。
  --enforce-eager       总是使用PyTorch的急切模式。如果为False,将使用急切模式和CUDA图的混合以获得最大的性能和灵活性。
  --max-context-len-to-capture MAX_CONTEXT_LEN_TO_CAPTURE
                        由CUDA图覆盍的最大上下文长度。当序列的上下文长度大于此长度时,我们将回退到急切模式。(已弃用。请改用--max-seq-len-to-capture)
  --max-seq-len-to-capture MAX_SEQ_LEN_TO_CAPTURE
                        由CUDA图覆盖的最大序列长度。当序列的上下文长度大于此长度时,我们将回退到急切模式。
  --disable-custom-all-reduce
                        参见ParallelConfig。
  --tokenizer-pool-size TOKENIZER_POOL_SIZE
                        用于异步分词的分词器池的大小。如果为0,将使用同步分词。
  --tokenizer-pool-type TOKENIZER_POOL_TYPE
                        用于异步分词的分词器池的类型。如果tokenizer_pool_size为0,则忽略。
  --tokenizer-pool-extra-config TOKENIZER_POOL_EXTRA_CONFIG
                        分词器池额外配置。这应当是一个将被解析成字典的JSON字符串。如果tokenizer_pool_size为0,则忽略。
  --enable-lora         如果为True,启用LoRA适配器的处理。
  --max-loras MAX_LORAS
                        单个批次中LoRAs的最大数量。
  --max-lora-rank MAX_LORA_RANK
                        LoRA秩的最大值。
  --lora-extra-vocab-size LORA_EXTRA_VOCAB_SIZE
                        LoRA适配器中可以存在的额外词汇表的最大大小(添加到基础模型词汇表中)。
  --lora-dtype {auto,float16,bfloat16,float32}
                        LoRA的数据类型。如果为auto,将默认为基础模型的dtype。
  --long-lora-scaling-factors LONG_LORA_SCALING_FACTORS
                        指定多个缩放因子(可以与基础模型的缩放因子不同-参见例如Long LoRA),以允许同时使用训练有这些缩放因子的多个LoRA适配器。如果未指定,仅允许使用基础模型缩放因子训练的适配器。
  --max-cpu-loras MAX_CPU_LORAS
                        在CPU内存中存储的LoRAs的最大数量。必须大于等于max_num_seqs。默认为max_num_seqs。
  --fully-sharded-loras
                        默认情况下,仅使用张量并行对LoRA计算的一半进行分片。启用此选项将使用完全分片的层。在高序列长度、最大秩或张量并行大小下,这可能更快。
  --device {auto,cuda,neuron,cpu,openvino,tpu,xpu}
                        vLLM执行的设备类型。
  --image-input-type {pixel_values,image_features}
                        传入vLLM的图像输入类型。
  --image-token-id IMAGE_TOKEN_ID
                        图像令牌的输入id。
  --image-input-shape IMAGE_INPUT_SHAPE
                        给定输入类型的最大图像输入形状(对内存占用最不利)。仅用于vLLM的profile_run。
  --image-feature-size IMAGE_FEATURE_SIZE
                        图像特征沿上下文维度的大小。
  --image-processor IMAGE_PROCESSOR
                        要使用的huggingface图像处理器的名称或路径。如果未指定,将使用模型名称或路径。
  --image-processor-revision IMAGE_PROCESSOR_REVISION
                        要使用的huggingface图像处理器的修订版本。它可以是一个分支名称、一个标签名称或一个提交id。如果未指定,将使用默认版本。
  --disable-image-processor
                        即使为模型在huggingface上定义了图像处理器,也禁用图像处理器的使用。
  --scheduler-delay-factor SCHEDULER_DELAY_FACTOR
                        在调度下一个提示之前应用延迟(以先前提示的延迟乘以延迟因子)。
  --enable-chunked-prefill
                        如果设置,prefill请求可以根据max_num_batched_tokens进行分块。
  --speculative-model SPECULATIVE_MODEL
                        在推测解码中使用的草案模型的名称。
  --num-speculative-tokens NUM_SPECULATIVE_TOKENS
                        从草案模型在推测解码中采样的推测token数。
  --speculative-draft-tensor-parallel-size SPECULATIVE_DRAFT_TENSOR_PARALLEL_SIZE, -spec-draft-tp SPECULATIVE_DRAFT_TENSOR_PARALLEL_SIZE
                        在推测解码中草案模型的张量并行副本数。
  --speculative-max-model-len SPECULATIVE_MAX_MODEL_LEN
                        草案模型支持的最大序列长度。序列超过此长度将跳过推测。
  --speculative-disable-by-batch-size SPECULATIVE_DISABLE_BY_BATCH_SIZE
                        如果入队请求的数量大于此值,则禁用新进入请求的推测解码。
  --ngram-prompt-lookup-max NGRAM_PROMPT_LOOKUP_MAX
                        在推测解码中ngram提示查找的最大窗口大小。
  --ngram-prompt-lookup-min NGRAM_PROMPT_LOOKUP_MIN
                        在推测解码中ngram提示查找的最小窗口大小。
  --model-loader-extra-config MODEL_LOADER_EXTRA_CONFIG
                        模型加载器的额外配置。这将传递给对应于所选load_format的模型加载器。这应当是一个将被解析成字典的JSON字符串。
  --preemption-mode PREEMPTION_MODE
                        如果为‘recompute’,引擎通过块交换执行抢占;如果为‘swap’,引擎通过块交换执行抢占。
  --served-model-name SERVED_MODEL_NAME [SERVED_MODEL_NAME ...]
                        API中使用的模型名称。如果提供了多个名称,服务器将响应任何提供的名称。响应中的模型字段中的模型名称将是此列表中的第一个名称。如果未指定,模型名称将与`--model`参数相同。注意,此名称也将用于prometheus度量中的`model_name`标签内容,如果提供了多个名称,度量标签将采用第一个。
  --qlora-adapter-name-or-path QLORA_ADAPTER_NAME

总结

vLLM展示了使用我们已经应用了十年的简单概念,就能做出令人惊叹的东西。这个框架在GPU内存使用和利用PageAttention技术的各种优势方面取得了巨大的改进。通过减少KV缓存的使用,系统能够处理更大的负载并更快地进行推理。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 为什么LLM服务如此具有挑战性?
    • 计算资源
      • 延迟
        • 成本
        • 什么是vLLM?
        • vLLM的秘密武器是什么?
          • 内存使用问题
            • 内存分片
            • 如何克服这个问题
            • vLLM的OpenAI兼容服务器
            • 总结
            相关产品与服务
            SSL 证书
            腾讯云 SSL 证书(SSL Certificates)为您提供 SSL 证书的申请、管理、部署等服务,为您提供一站式 HTTPS 解决方案。
            领券
            问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档