Prefill/Decode Disaggregation
A vllm_pd service splits inference into a prefill tier and a decode tier, each on nodes of its own, with a vllm-router in front. The tiers exchange KV cache over NIXL. From the benchmark’s point of view the router is the policy model: one OpenAI-compatible endpoint.
Example
Two pools, one node each, with one tier on each:
This single entry deploys three services:
The tiers inherit container, model, and served_model_name from the vllm_pd entry. Anything else, such as tensor_parallel_size, number_of_instances, extra_args, env, or mounts, is set per tier. The router address is what policy_base_url points at, so set driver.policy_model to the vllm_pd name (llm), not to a tier.
Rules
- Each tier needs a
node_pool. The two tiers run side by side, and the router addresses each by its pool’s first node. Pools must agree onpartition,ntasks_per_node, andgpus_per_node, as always. - Names are reserved.
llm-prefillandllm-decodemay not already exist inservices. - Tiers use different RPC ports.
data_parallel_rpc_portdefaults to 13345 for prefill and 13346 for decode. Overriding one so they match is an error. server_per_nodeandnixl_side_channel_portbelong on thevllm_pdentry, not on a tier, because they apply to both. Setting them on a tier is an error.- The router, if pinned, goes on the first pool. The driver reaches it over localhost from the allocation’s first node. Leaving
node_poolunset on the router is simplest. - Each tier is sized against its own pool, so a one-node pool is a single-node deployment with that pool’s GPUs.
Tuning
Each tier’s job step exports VLLM_NIXL_SIDE_CHANNEL_HOST (the node’s hostname) and VLLM_NIXL_SIDE_CHANNEL_PORT before vllm serve starts, in addition to any pre_command you set.