ステータス: ドラフト (2026-10-13)、一部実測値あり。 論文、公式ドキュメント、NVIDIAブログは2026-10-13に直接アクセスして確認しました。ドキュメントはDynamo v1.5.1(2026-10-07)を基準としています。NVIDIAが発表したパフォーマンス数値は「メーカー発表値」として記載しています。実測値は同サイトの「トス ML/AI Infra 準備」の第14편(8GBクラスGPU、vLLM)および第24편(Dynamo 1.6.0開発ビルド、8GBクラス・24GBクラスGPU、0.6Bモデル)から再引用しました。NVLinkやRDMAで接続された環境における分散サービングのメリットは未実測です。 作成ルール: 実測データを基本とし、測定できなかったものは「未実測」、確認できなかったものは「未確認」と表示します。
NVIDIA Dynamo: プリフィルドecodeの分離
目次
- 1. プリフィルとデコードは同じGPU上で互いに干渉し合う
- 2. 分散サービング: 分離とKVの移行
- 3. NVIDIA Dynamoの構成
- 4. なぜスループットが向上するのか
- 5. 実際に測定したDynamo
- 6. DynamoとLMCacheの関係
- 7. いつメリットがなくなるのか
- 8. シリーズのまとめ
- 参考文献
1. プリフィルとデコードは同じGPU上で互いに干渉し合う
第1回で説明したように、プリフィルは計算に、デコードはメモリ帯域幅に制約されます。両者が1つのGPUを共有すると問題が発生します。連続バッチング(Continuous Batching)は新しいリクエストのプリフィルをデコードのステップの間に挿入しますが、プリフィルの長いステップは時間がかかり、その間バッチ内の他のリクエストは次のトークンを受け取れなくなります。
我々の実測値。 8GBクラスのGPUにおいてvLLMのデフォルト設定(1ステップあたりの入力上限2,048トークン)でデコード中のリクエストの傍らに3,500トークンの入力を割り込ませたところ、その区間における最大トークン間隔は227msでした(3回測定して227ms・226ms・226ms)。通常時の間隔は約15msです。第2回のチャンクプリフィル(Chunked Prefill)によってこの値を69msまで短縮できましたが、その代償として長い入力の最初のトークンがわずかに遅れました。 チャンクは干渉を分割するだけで、完全に解消することはできません。
分散サービングを初めて体系的に扱った2つの論文は、この問題を次のように指摘しています。
- DistServe(Zhongら、OSDI 2024): 1つのGPUに混在させると、(1)両方のフェーズがお互いの処理を遅くし、プロンプトが長いほどそれが顕著になり、(2)両方のフェーズが 同じリソースと同一の並列化設定を使わなければならないため、TTFTとトークン間隔の目標値のうち厳しい方に合わせてGPUが過剰に割り当てられてしまうと指摘しています。チャンクプリフィルはTTFTとトークン間隔をトレードオフしているに過ぎないと評価しています。
- Splitwise(Patelら、ISCA 2024): 実際のクラウドの履歴を分析し、プロンプトフェーズは計算中心であり、トークンフェーズはメモリ帯域幅および容量中心であることを示しました。BLOOM-176Bにおいて1,500トークンのプロンプト処理時間は6つの出力トークンを生成する時間と同等であり、トークンフェーズはGPUの電力を700Wから350Wに下げてもレイテンシーがほとんど増加しませんでした。このように特性が大きく異なる場合、 異なるハードウェアまたは異なる設定を使用する方が望ましいという結論です。
2. 分散サービング: 分離とKVの移行
アプローチはシンプルです。 プリフィル専用GPUとデコード専用GPUを個別に用意します。 プリフィルGPUがプロンプトのKVを生成したら、そのKVをデコードGPUに送信し、デコードGPUは受け取ったKVの続きからトークンを生成します。
- デコードGPUには長いプリフィルが割り込まないため、トークン間隔が均一になります。間隔の目標値を守りつつ、 デコードのバッチサイズをより大きく 設定できます。
- 両方のフェーズに 異なる並列化手法と異なるGPU数を割り当てることができます。プリフィルは計算を分散させる方向へ、デコードは大きなバッチを収容する方向へ最適化します。
- その代償となるのが KV転送です。第1回の数式通り、KVのサイズは大きく、それを最初のトークンを生成する前に移行する必要があります。
DistServeの測定結果。 A100 80GB(ノード内NVLink、ノード間25Gbps)、OPT-13B・66B・175Bを使用し、レイテンシー目標を90%以上満たす最大リクエストレート(Goodput)を測定しました。
| ワークロード | モデル | vLLM比較の処理能力(リクエストレート) | vLLM比較のレイテンシー目標 |
|---|---|---|---|
| チャットボット(ShareGPT) | OPT-13B・66B・175B | 2.0〜4.6倍 | 1.8〜3.2倍 厳格 |
| コード補完(HumanEval) | OPT-66B | 5.7倍 | 1.4倍 厳格 |
| 要約(LongBench) | OPT-66B | 4.3倍 | 12.6倍 厳格 |
他のベースライン(DeepSpeed-MII)と比較した場合は最大7.4倍であり、アブストラクトの「リクエストレート最大7.4倍またはレイテンシー目標12.6倍厳格」という記述はこれら2つの表を合わせた値です。同期的検証の例も直感的です。13BモデルをA100 1枚に配置した場合は約1.6リクエスト/秒でしたが、プリフィルのみの場合は5.6、デコードのみの場合は10リクエスト/秒を記録し、プリフィル2枚+デコード1枚に分割した場合はGPUあたり3.3リクエスト/秒となり2.1倍に向上しました。
KV転送はどうだったでしょうか。論文では、OPT-66Bの512トークンのリクエスト1つあたりのKVは約1.13GBであり、秒間10リクエストであれば11.3GB/sが必要であると計算しています。そのため、プリフィルとデコードを 同一ノード内(NVLink) に配置するように設計されており、その結果OPT-175Bにおいて転送が全体レイテンシーに占める割合は0.1%未満でした。
Splitwiseの測定結果。 KVを レイヤーごとに非同期で 送信し、次のレイヤーの計算とオーバーラップさせました(InfiniBand)。オーバーラップさせられなかった転送は、A100で約8ms、H100で約5msであり、プロンプト計算時間の7%未満にとどまり、全体のレイテンシーには0.8%を加算するにとどまりました。消費電力が同一の条件下において、A100のみで分割した構成は基準(A100単体)の2.15倍のスループットを記録しました(本文図18a)。アブストラクトの代表的な数値(「コスト20%削減しつつ1.4倍」、「同一コスト・電力で2.35倍」)は本文の実験と完全に対応するペアが見つからなかったため、ここでは本文の数値のみを記載します。
3. NVIDIA Dynamoの構成
DynamoはvLLM・SGLang・TensorRT-LLMといったエンジン の上で 複数のGPUや複数のノードを統合するサービングフレームワークです。エンジンそのものを置き換えるのではなく、複数のエンジンをどのように分割し、どこへルーティングすべきかを担当します。ドキュメント(v1.5.1)で確認した構成は以下の通りです。
- フロントエンド: OpenAI互換API、トークナイゼーション。
- KVアウェア・ルーター: リクエストをどのワーカーに送信するかを決定します。ワーカーごとにコストを計算し、最もコストの低い場所を選択します。v1.5.1におけるコストは「そのワーカーで新たま計算しなければならないプリフィルブロック数(すでに保持しているブロックは差し引く)× 重み + デコードブロック負荷 + 実行中リクエスト数 × 重み」です。 すでに同じプレフィックスのKVを持っているワーカーは、プリフィルの分量が減るためコストが安くなります。 ただし、特定の部分に負荷が偏りすぎないように負荷状況も同時に考慮します。プレフィックスの一致に対する加算ウェイトを大きくするとTTFTが短縮され、小さくすると負荷が均等に分散されてトークン間隔が短縮されるとドキュメントでは説明されています。
- ワーカーが何を保持しているかを把握する方法: ワーカーがブロックを保存・削除するたびにイベントを送信し、ルーターがインデックスを構築する方式がデフォルトですが、イベントなしで「最近送信したリクエスト」を記憶して推定する近似モード(デフォルトTTL 120秒)もあります。
- 分散サービング: プリフィルワーカーを選択するルーターが別途存在し、プリフィルワーカーがKVを生成した後、デコードワーカーが NIXL を介してそのKVを直接取得します。
- NIXL: GPUメモリ、CPUメモリ、ファイル、オブジェクトストレージ間の転送を単一のインターフェースでラップしたライブラリです。実際の転送はプラグインが担当します(UCXがデフォルト、GPUDirect Storage、POSIX、Mooncake、libfabric、オブジェクトストレージなど)。NVLink、InfiniBandやRoCEなどのRDMA、PCIe、TCPを目的に応じて使い分けます。
- プランナー: 負荷を監視し、プリフィルおよびデコードのワーカー数を動的に変更します。スループット目標(キューの深さやKV使用率など)やレイテンシー目標(TTFTやトークン間隔のSLA)などのモードが存在し、到着するリクエスト数、入出力長、キャッシュヒット率を予測して決定する方式や、エンジンのステップごとのメトリクスに対して回帰分析を適用する方式があります。Kubernetes環境ではオペレーターがその数を調整します。
- KVブロックマネージャー(KVBM): GPU(G1)→ 固定ホストメモリ(G2)→ ローカルディスク(G3)→ オブジェクトストレージ(G4)へとKVを階層的にオフロードする仕組みでした。 v1.5.0のリリースノートで非推奨(deprecated)となり、v1.7.0で削除される予定です。ホスト・ディスク層はエンジン自身のオフロード機能(またはLMCacheのような連携機能)へ移行することが推奨されています。
4. なぜスループットが向上するのか
| 要因 | 何が変化するか | 根拠 |
|---|---|---|
| 干渉の排除 | デコードGPUに長いプリフィルが割り込まないため、トークン間隔の目標値を守りながらデコードバッチを拡大できる | 実測値(干渉227ms)、DistServe・Splitwise |
| フェーズごとの最適化 | プリフィルとデコードに異なる並列化手法・GPU数・ハードウェアを割り当てる。プランナーが比率を負荷に合わせる | DistServe(2.1倍の例)、Splitwise |
| キャッシュヒット | 同一のプレフィックスを持つワーカーに送信することで、プリフィル自体をバイパスする | 実測値(第5節)、メーカー発表値 |
| ワーキングセットの分割 | プレフィックスがワーカーごとに分散され、各ワーカーのGPUキャッシュに自身の担当分が完全に収まる | 実測値(第5節) |
NVIDIAの発表数値は以下の通りです。すべて メーカー発表値であり、直接再現したものではありません。
- 紹介ブログ(2025-03-18): GB200 NVL72上でDeepSeek-R1 671B(FP4、入力32K・出力8K)を分散サービングで稼働させ、スループットが最大30倍に向上。Hopper上でLlama 70B(FP8、入力3K・出力50)の場合は2倍以上。図の注記には「予想パフォーマンス、変更される可能性あり」と記載されています。
- ドキュメント v0.9.0 の設計ドキュメント:分散サービングは Llama 70B 係列(FP8、H100、入力 3K・出力 150)で単一ノード GPU 当たりのスループット +30%、2ノードで 2 倍以上。KV 認識ルーティングは H100 の 2 ノードに実際のリクエスト 10 万件(平均入力 4K・出力 800)を送信し、ランダムルーティング比で TTFT 3 倍、平均遅延 2 倍減。KVBM の CPU オフロードは Qwen3-8B(H100、マルチターン会話、平均入力 20K)で GPU プレフィックスキャッシュのみを使用する場合に比べ TTFT 2.2〜12 倍改善。
5. 実際に測定してみた Dynamo
別のシリーズにて、Dynamo(1.6.0 開発ビルド、vLLM 0.30.0、NIXL 1.3.2)を Qwen3-0.6B(トークンあたりの KV 114,688 バイト)で再測定しました。
KV 認識ルーティング。 ワーカーを 2 つ起動し、約 1,500 単語のプレフィックス 12 種を 6 回ずつ混ぜて送信しました(再リクエスト 60 回)。再リクエストが同じプレフィックスの KV を持つワーカーに向かった場合、初トークンは約 15ms、そうでない場合は約 80ms でした。
| ルーティング | 60 回中のヒット(3回) | 初トークン平均 |
|---|---|---|
| ラウンドロビン | 35, 40, 43 | 34〜42ms |
| ランダム | 44, 31, 45 | 32〜46ms |
| KV 認識、近似モード | 60, 53, 60 | 15〜26ms |
| KV 認識、イベントモードだがイベントなし | 39, 44, 41 | 32〜38ms |
| KV 認識、イベントモード | 60, 60, 60 | 15ms |
- ルーターを有効にすると、ヒット率はほぼ 100% でした。
- サイレント障害に注意する必要があります。 イベントモードを有効にしたにもかかわらずワーカーがイベントを送信しない場合、ルーターのインデックスが空になり、ヒット率がランダムレベルまで低下し、エラーなしでログの警告が 1 行残るだけでした。ルーティングを有効にした後は、「同じプレフィックスを再送すると初トークンが短縮されるか」を実際に測定する必要があります。
- ラウンドロビンがランダムより優れているわけでもありませんでした。1 つのワーカーの KV 容量(14,816 トークン)に 12 種のプレフィックス(約 18,000 トークン)がすべて入りきらない一方、KV 認識ルーティングはプレフィックスをワーカーごとに 6 種ずつに分けてそれぞれに収めました。ルーティングのメリットには、「同じ宛先に送信する」ことに加え、「各ワーカーのワーキングセットが小さくなる」ことが相乗効果として加わります。
- フロントエンドを経由するコストはアイドル時に約 13ms であり、同時実行数 8 および 32 では区別がつきませんでした。
分散サービング。 結果は逆でした。すべて単独サービングより遅くなりました。
| 構成(同時実行 1) | 1,500 単語 | 3,000 単語 |
|---|---|---|
| 8GB 級 GPU 単独 | 78ms | 172ms |
| 同一 GPU 1 枚をプリフィル・デコードプロセスに分割 | 406ms | 812ms |
| 異なる 2 つのサーバーに分割(1GbE 級リンク) | 1,721〜1,752ms | 3,407〜3,533ms |
- 1 枚のカードを分割しても計算リソースは増加せず、KV 転送が追加されるだけです。分割が解決しようとする問題を解決するための GPU が存在しない構成です。
- 2 つのサーバーに分割した場合の増加した時間は、 KV バイト ÷ リンクスループットと一致していました。3,000 単語のリクエスト 1 件あたりの転送は 351.75MB、3,374ms、104MB/s であり、プリフィル 83ms に転送約 3.4 秒を加算した値が測定値と一致していました。どの GPU がプリフィルを担当してもほぼ同じでした。時間は計算ではなくリンクに制限されていたためです。
これは「分散サービングが遅い」のではなく、**「遅いリンクで分割すると遅い」**ということです。論文が NVLink や InfiniBand を前提としている理由がこの表にあります。
6. Dynamo と LMCache の関係
両者は競合関係ではなく、レイヤーが異なります。LMCache は 単一エンジンの側で KV を保存・ロードするキャッシュ層であり、Dynamo は 複数のエンジンを束ねて分割・送信するフレームワークです。ドキュメントで確認した統合ポイントは以下の通りです。
- 集約構成(1 つのワーカーがプリフィルとデコードを兼務):Dynamo の vLLM ワーカーが
LMCacheMPConnector(ロールkv_both)としてノードのlmcache serverに KV を書き込み、ロードします。ワーカーと LMCache サーバーが CUDA IPC で結合するため、Kubernetes ではhostIPC: trueが必要です。v1.5.1 の Kubernetes ガイドはこの集約構成のみを扱い、検証済みのバージョンコンビネーションを個別に記載しており、サーバーとワーカーの LMCache のバージョンが異なると通信プロトコルが一致しないと警告しています。 - 分散構成:v1.3.0 のドキュメントでは、プリフィル側で LMCache コネクタと NIXL コネクタを組み合わせてラップする例が挙げられています。プリフィルからデコードへの転送は NIXL が担当し、LMCache はリクエスト間の再利用を担当するという役割分担です。LMCache ドキュメントの分散構成も同様の形状です(パート 3 セクション 7)。v1.5.1 において、LMCache を分散サービングと併用する公式手順は見つかりませんでした(未確認)。
- KVBM との関係:Dynamo のオフロード概要ドキュメントでは、LMCache、SGLang の HiCache、FlexKV を代替手段として紹介し、 重複して使用しないよう求めています。KVBM は v1.5.0 より非推奨(deprecated)となっています。
- ルーターの視野:v1.5.1 のルーターサポート表には、vLLM 自体のオフロード、SGLang HiCache、TensorRT-LLM のホストおよびディスクヒット率がスコアに反映されると記載されており(ホストヒット 0.75、ディスク 0.25)、 LMCache の行はありません。 そのため、LMCache にオフロードされた KV をルーターがスコアに考慮しているかどうかは、ドキュメントからは確認できませんでした(未確認)。
7. メリットがないケース
分散サービングの損益は、パート 3 と同様の形式の式で見積もることができます。 初トークンに追加される時間 ≈ トークンあたりの KV × 入力トークン ÷ リンクスループット(レイヤーごとの転送により、一部は計算と重複させて隠すことができます)。入力 4,096 トークンの KV を転送する時間を計算すると、次のようになります(転送時間のみ、計算を除く)。
リンク速度は、1GbE 級が当社の実測実効値で 104MB/s、100Gb/s が理論値で 12.5GB/s、NVLink 級が DistServe の論文に記載されている A100 間での 600GB/s です。
| モデル | KV サイズ | 1GbE 級 | 100Gb/s | NVLink 級 |
|---|---|---|---|---|
| Qwen3-0.6B | 470MB | 4.5 秒 | 38ms | 0.8ms |
| Llama 3.1 8B | 537MB | 5.2 秒 | 43ms | 0.9ms |
| Llama 3.1 70B | 1.34GB | 12.9 秒 | 107ms | 2.2ms |
この値が削減できるもの(干渉により遅延していたデコード、過剰に確保されていた GPU)よりも大きい場合、損失となります。したがって、分散がメリットを持たない、または損失になるケースは以下の通りです。
- リンクが遅い。 上記テーブルの最初の列がそのケースであり、実測で 20 倍以上遅くなりました。
- プロンプトが短い。 プリフィルが短ければデコードに割り込む時間も短いため、排除すべき干渉が少なくなります。一方、転送やルーティングの固定費は残ります。
- 負荷が低い。 同時にデコードするリクエストが少ない場合、干渉を受ける対象がありません。分散は GPU を 2 つに分割するため、アイドル時には遊休状態の GPU が増えるだけになります。
- GPU が 1 枚である。 分割しても計算リソースは増えません(実測で 4.7〜7.2 倍遅くなります)。
- 小規模モデル。 プリフィルがすでに安価であるため(0.6B のプリフィルは 83ms)、KV 転送の相対的な割合が大きくなります。
Dynamo のドキュメントにも、普遍的な閾値はないと記載されています。モデル、GPU、入力長の分布によって境界が変化するため、初期バージョン(v0.1.0)では「プレフィックスヒットを差し引いたプリフィル長が閾値を超え、かつリモートプリフィールのキューが短い場合のみ」リモートプリフィルを使用しており、v1.5.1 ではルーターコストに応じて条件付きで分割する機能が実験的ステージとして導入されています。 分散させるかどうかは、自分のリンクにおける KV 転送のスループットを最初に測定し、その値を使って上記の式を計算した上で 決定するのが安全です。
KV 認識ルーティングは事情が異なります。KV を転送するのではなく リクエストを KV の側へ移動させるため 、リンクコストが発生しません。同じプレフィックスが再送されるような負荷であれば、比較的損失が発生しにくくなります。ただし、特定のワーカーに負荷が偏らないように負荷ウェイトを調整し、イベントが実際に届いていることを確認する必要があります。
8. シリーズのまとめ
| 回 | 何を削減するか | いつ効果が大きいか | いつ効果がないか |
|---|---|---|---|
| 1. KV キャッシュ | 過去のトークンの K・V の再計算 | 常に(出力が同じ場合) | — 代わりにメモリを消費する |
| 2. PagedAttention・連続バッチング・プレフィックスキャッシュ | メモリの無駄遣い、空きスロット、同一プレフィックスの計算 | 同時リクエストが多い時、共通プロンプト | ワーキングセットが GPU より大きい場合にキャッシュがクリアされる |
| 3. LMCache | GPU 外に配置した KV によるプリフィルの代替 | 長文脈、再利用が多い、高速なストレージパス | 短い入力、低いヒット率、遅いリンク、小さな容量 |
| 4. Dynamo | 干渉の排除、段階的なカスタマイズ、KV 側へのルーティング | 高負荷、長いプロンプト、GPU 間の高速なリンク | 遅いリンク、1 枚のカード、低負荷、小規模モデル |
4 つの回を貫く質問は 1 つでした。 「この KV を再計算することと、どこかから持ってくることのどちらが安価か。」 答えは、モデルのトークンあたり KV サイズ、GPU の計算速度、KV が通過するパスの速度、そして同じプレフィックスがどれくらいの頻度で再送されるかによって決まります。これらはいずれも測定可能な値です。
T-i の一言。 サーブの練習をしている人とラリーの練習をしている人を同じテーブルに置くと、お互いにボールを待たなければならず、両者にとってマイナスになります。テーブルを分ければ改善されます。しかし、ボールカゴを隣の建物から運ばなければならないとしたらどうでしょうか?その場合は一緒にプレイした方がマシです。分割する前に、カゴがどれくらいの速さで届くのかをまず測定してみてください。
参考
- Zhong ら, DistServe: Disaggregating Prefill and Decoding for Goodput-optimized LLM Serving (OSDI 2024): https://arxiv.org/abs/2401.09670 (v3, セクション 1・2.3・3.3・6、表 1、図 8・9・10)
- Patel ら, Splitwise: Efficient Generative LLM Inference Using Phase Splitting (ISCA 2024): https://arxiv.org/abs/2311.18677 (v2, セクション 3・4.C・6、図 18)、Microsoft Research ページ: https://www.microsoft.com/en-us/research/publication/splitwise-efficient-generative-llm-inference-using-phase-splitting/
- NVIDIA Dynamo リポジトリ・リリース: https://github.com/ai-dynamo/dynamo (v1.5.1, 2026-10-07)、ドキュメント: https://docs.nvidia.com/dynamo/ (アーキテクチャ、ルーターの概念・設定、分散サービング、プランナー、KVBM 設定、KV オフロード・LMCache MP デプロイ、ルーターオフロードサポート表、2026-10-13 閲覧)、初期版の分散サービングドキュメント: https://github.com/ai-dynamo/dynamo/blob/v0.1.0/docs/disagg_serving.md
- NIXL: https://github.com/ai-dynamo/nixl (README,
docs/nixl.md) - NVIDIA 紹介ブログ(ベンダー発表): https://developer.nvidia.com/blog/introducing-nvidia-dynamo-a-low-latency-distributed-inference-framework-for-scaling-reasoning-ai-models/ (2025-03-18)、設計ドキュメント v0.9.0(ベンダー発表): https://docs.nvidia.com/dynamo/v-0-9-0/design-docs/overall-architecture
- LMCache の Dynamo 連携ドキュメント: https://docs.lmcache.ai/production/dynamo_coordination.html
- 実測の引用:同一サイト「トス ML/AI Infra 準備」第 14 回(チャンクと干渉)、第 24 回(Dynamo 実測)