Encoder-only 实例
生产者实例只跑 multimodal encoder,不初始化语言模型 KV cache。代码中 get_kv_cache_spec() 在非 consumer EC transfer 下返回空。
vLLM 的 EPD 路径把视觉/音频 encoder 输出变成可跨进程复用的 Encoder Cache(EC)。
Encoder 实例只负责生产 EC,PD 或 P/D 实例按 mm_hash 命中并加载 EC,然后继续语言模型 prefill/decode。
当前代码主干来自 vllm#25233;
vllm#44049 是后续共享内存和资源回收增强,尚未出现在本次源码快照里。
生产者实例只跑 multimodal encoder,不初始化语言模型 KV cache。代码中 get_kv_cache_spec() 在非 consumer EC transfer 下返回空。
connector 把 scheduler 的“命中/计划”与 worker 的“加载/保存”分开。当前本地实现是 ECExampleConnector,用共享目录保存 safetensors。
PD scheduler 先查本地 encoder cache,再查外部 EC。外部命中时只安排加载,不把该 MM input 放进 scheduled_encoder_inputs。
#44049 增加共享内存 connector、ACK 和独立容量管理,目标是降低磁盘 I/O,并让外部缓存释放成为 scheduler 闭环。
EPD 不是单个 vLLM server 自动拆分,而是由示例 proxy 组织多个 OpenAI-compatible vLLM 实例。 proxy 负责先触发 encoder primer 请求,再把原始请求转发给 PD 或 P/D。
ec_role=ec_producerencoder_cache[mm_hash]mm_hashec_role=ec_consumermax_tokens=1 的请求,发给 encoder cluster。scheduled_encoder_inputs,worker 执行 multimodal encoder。encoder_cache[mm_hash],随后 maybe_save_ec_to_connector 调用 connector 的 save_caches。ec_connector.has_cache_item(mm_hash) 为真,加入 external_load_encoder_input。ec_connector_metadata,挂到 SchedulerOutput。start_load_caches,随后 _gather_mm_embeddings 使用本地 encoder cache。| 层次 | 职责 | 关键源码 | 阅读要点 |
|---|---|---|---|
| 配置层 | 声明 EC connector、角色、connector 额外参数。 | ECTransferConfig | ec_producer 只生产;ec_consumer 只消费;ec_both 同时具备生产/消费语义。 |
| 抽象层 | 把 scheduler 侧计划和 worker 侧数据搬运分离。 | ECConnectorBase | 看 has_cache_item、update_state_after_alloc、build_connector_meta、start_load_caches、save_caches。 |
| connector 实现 | 当前本地代码用共享目录保存/加载 safetensors。 | ECExampleConnector | 保存路径是 shared_storage_path/mm_hash/encoder_cache.safetensors。 |
| 调度层 | 决定 MM encoder output 是本地计算、复用本地 cache,还是从外部 EC 加载。 | _try_schedule_encoder_inputs | 外部命中会分配本地 encoder cache slot,但不会加入 scheduled_encoder_inputs。 |
| 输出协议 | 把 EC metadata 从 scheduler 带到 worker。 | SchedulerOutput.ec_connector_metadata | metadata 是 connector 自定义结构,当前为 ECExampleConnectorMetadata.mm_datas。 |
| 执行层 | 执行前 load EC,执行后 save EC,并把结果回传。 | ECConnectorModelRunnerMixin | context manager 是 EC 生命周期的中心。 |
| 模型 runner | 在 MM embedding 构造前后嵌入 EC 逻辑;producer 可跳过 KV cache。 | GPUModelRunner._preprocess | consumer 路径 load + gather;producer 路径执行 encoder 后返回空输出。 |
| 部署入口 | 组织 E、PD、P、D 多个服务实例。 | Proxy /v1/chat/completions | vLLM 本体提供 EC 能力,服务拆分由 proxy 和启动脚本完成。 |
当前代码已经包含 EPD 主体框架,但 connector 注册项只有 ECExampleConnector。
未发现 ECSharedMemoryConnector 或 ECConnectorCacheManager 文件。
ECConnectorFactory.register_connector(
"ECExampleConnector",
"vllm.distributed.ec_transfer.ec_connector.example_connector",
"ECExampleConnector",
)
producer 将 EC tensor detach 到 CPU 后保存为 safetensors; consumer 根据 metadata 找到文件并 load 到当前平台设备。这个路径足够验证架构,但磁盘 I/O 会影响高并发 TTFT。
#25233 增加了 EC transfer 配置、EC connector 抽象、scheduler 外部 cache 命中逻辑、worker load/save 生命周期、proxy 示例和测试。
if ec_connector.has_cache_item(mm_hash):
external_load_encoder_input.append(i)
continue
encoder_inputs_to_schedule.append(i)
这段分支就是 EPD 的调度本质:同一个 multimodal item,要么外部加载,要么本地计算。
#44049
的目标是引入 ECSharedMemoryConnector 和 scheduler 侧 ECConnectorCacheManager。
这会把当前磁盘传输换成本机共享内存,并通过 ACK / unlink 管理物理缓存生命周期。
/dev/shm,按 mm_hash 命名。free_physical_cache。
当前本地 scheduler 没有消费 ECConnectorOutput.finished_sending/finished_recving 来驱动外部物理缓存回收。
#44049 正是在补“connector 外部存储容量管理”和“物理资源释放”这条闭环。
vLLM 内部提供 EC transfer 能力,但 E、PD、P、D 的服务编排由示例脚本和 proxy 完成。
VLLM_USE_V2_MODEL_RUNNER 配置校验会把 EC transfer 加入 unsupported 列表。
本地实现是 safetensors 落盘。SHM/RDMA 等方向属于后续 connector 演进。
ec_producer,它负责生成并保存 EC;如果实例是 ec_consumer,scheduler 会尽量从 EC connector 加载已有 embeddings,再继续语言模型路径。
ec_connector_metadata 的传递点。
| 问题 | 能回答时说明你读懂了 |
|---|---|
| 为什么 producer 不需要语言模型 KV cache? | 因为它只执行 multimodal encoder,get_kv_cache_spec() 在非 consumer EC transfer 下返回空。 |
| 外部 EC 命中后,scheduler 还会分配本地 encoder cache 吗? | 会。PD worker 最终仍要从本地 encoder_cache 取 embeddings,只是这些 embeddings 是 load 进来的,不是本地算出来的。 |
ec_connector_metadata 何时生成、何时消费? |
scheduler 每步 build;worker 的 EC context 在模型执行前 bind 并消费。 |
| #44049 和 #25233 是替代关系吗? | 不是。#25233 是主体架构;#44049 是 connector 后端和资源回收增强。 |