在大语言模型推理系统中,KV Cache 的内存管理是决定系统吞吐量和延迟的关键因素。随着长上下文场景越来越普遍,KV Cache 的内存占用往往能够达到甚至超过模型权重本身的规模,这对 GPU 显存构成了巨大压力。Nano-vLLM 作为轻量级推理引擎,其 KV Cache 架构采用了连续物理存储与分页管理相结合的混合策略,本文将深入剖析其中的块驱逐与压缩机制,为工程实践提供可操作的参数配置参考。
物理内存结构与块组织方式
Nano-vLLM 的 KV Cache 采用统一的连续张量结构来存储所有层的键值对,这种设计简化了内存分配和释放的复杂度,同时为跨层共享和前缀缓存提供了便利。从物理层面来看,KV Cache 张量的形状定义为 [2, num_hidden_layers, num_kvcache_blocks, block_size, num_kv_heads, head_dim],其中维度 0 用于区分键(索引 0)和值(索引 1),维度 2 表示总块数,维度 3 的 block_size 默认配置为 256 个 token。这种固定块大小的设计使得内存管理更加可预测,同时也为后续的驱逐和压缩操作提供了规整的操作粒度。
每个注意力模块在初始化时会获得其对应层切片视图的引用,存储为 k_cache 和 v_cache 属性。这种设计使得不同层可以独立管理自己的缓存区域,同时又共享底层的物理存储空间。在实际推理过程中,当新的 token 生成时,系统会将其映射到对应的物理块位置,如果当前块已满,则会触发新的块分配或现有块的驱逐操作。这种逻辑块与物理块的分离映射机制,是 PagedAttention 能够有效减少内存碎片化的核心所在。
块驱逐策略的工程权衡
传统的 KV Cache 驱逐方法通常基于注意力分数来识别不重要 token,然后将其从缓存中移除。然而,这类方法在与 PagedAttention 结合时面临两个主要挑战:其一,FlashAttention 在推理过程中不返回注意力分数,导致基于注意力的方法需要额外的 CUDA kernel 修改来追踪这些值;其二,现有压缩方法在驱逐时可能跨越不同的 vLLM 块边界进行操作,这会引入新的内存碎片化问题,抵消 PagedAttention 带来的碎片化减少收益。
PagedEviction 提出了一种块对齐的 KV Cache 驱逐策略,专门针对 PagedAttention 的分页内存布局进行优化。该方法的核心思想是以完整的物理块作为驱逐单位,而非单个 token,这样可以在释放内存的同时避免产生碎片。具体实现上,PagedEviction 在预填充阶段根据 token 重要性进行预驱逐,在解码阶段则采用 "满一块驱逐一块" 的策略,仅当最新块被填满后才触发驱逐操作。这种设计显著降低了每步推理的驱逐开销,同时使内存使用量保持稳定。
从性能数据来看,PagedEviction 在 cache budget 为 1024 token 的条件下,能够在 LLaMA-1B 模型上实现约 3020 tokens / 秒的处理速度,相比完整缓存的 2200 tokens / 秒提升了约 37%。更重要的是,这种块级驱逐策略在不同规模的模型上都表现出约 10% 到 12% 的延迟降低,且在 LongBench 基准测试中始终优于其他无注意力基线方法。以 GovReport 数据集为例,PagedEviction 在 1024 token 预算下达到了 24.5 的 ROUGE 分数,分别比 StreamingLLM(21.0)和 KeyDiff(21.2)高出 15% 到 20%。
联合压缩与驱逐的统一优化
EvicPress 在驱逐策略的基础上进一步引入了有损压缩机制,并提出了一种联合优化框架。该方法认识到,单独的驱逐或压缩策略都未能充分利用存储层级优化的潜力 —— 通过将 KV Cache 卸载到低层级存储设备或应用有损压缩,可以显著扩展有效缓存容量。EvicPress 的核心创新在于其统一效用函数,该函数量化了压缩和驱逐决策对整体生成质量和延迟的综合影响。
具体而言,EvicPress 的分析模块会定期更新所有可能驱逐 - 压缩配置在各上下文上的效用函数分数,然后使用快速启发式算法在所有存储层级间重新排列 KV Cache,目标是最大化每个存储层级上的效用函数总分。这种联合优化方法相比单独使用驱逐或压缩,能够在快速设备上实现更高的 KV Cache 命中率,从而降低延迟,同时通过对压缩敏感上下文应用保守压缩来保持生成质量。实验评估显示,EvicPress 在 12 个数据集和 5 个模型上,最多可实现 2.19 倍的首 token 生成时间(TTFT)提升,同时保持等效的生成质量。
工程实践参数配置建议
在实际部署中,KV Cache 的内存管理需要根据具体场景进行参数调优。首先是块大小(block_size)的选择,默认的 256 token 适用于大多数场景,但如果主要处理极短序列(如对话轮次),可以适当减小块大小以减少内部碎片;如果主要处理超长文档,则可以增大块大小以降低块表维护开销。其次是缓存预算(cache budget)的设定,这直接决定了内存占用的上限,需要在内存节省和模型精度之间进行权衡。
对于驱逐策略的选择,如果系统主要服务于长上下文任务,PagedEviction 的块对齐驱逐是推荐方案,其能够有效控制内存增长同时保持较好的精度;如果系统需要处理大量共享前缀的请求,则应优先启用前缀缓存功能,让驱逐策略尽量保留共享前缀对应的块。对于压缩策略,需要根据业务对生成质量的容忍度来选择压缩比 ——EvicPress 的研究表明,对压缩不敏感的上下文可以使用更高的压缩比,而对质量敏感的任务则应保持较低的压缩开销。
最后是监控指标的设置,建议持续跟踪每请求平均 KV Cache 使用量、块驱逐率、缓存命中率以及前缀复用率等指标。当驱逐率持续高于阈值时,可能需要考虑增加 GPU 显存配额或调整 block_size;当缓存命中率下降时,则需要评估是否需要增大整体缓存预算。这些参数的协同调优,是实现高吞吐量和低延迟推理服务的关键。
资料来源:DeepWiki 的 nano-vllm 项目文档、EvicPress 论文(arXiv:2512.14946)、PagedEviction 论文(arXiv:2509.04377)。