[VLM] split multimodal scheduling from mm_utils (#32415)
This commit is contained in:
@@ -1,18 +1,18 @@
|
||||
"""Unit tests for per-item DataEmbeddingFunc results in the chunked mm path.
|
||||
|
||||
A DataEmbeddingFunc may return either one combined [tokens, hidden] tensor or
|
||||
one tensor per item (see mm_utils.DataEmbeddingFunc). These tests assert the
|
||||
one tensor per item (see mm_schedule.DataEmbeddingFunc). These tests assert the
|
||||
two forms produce bitwise-identical chunked-prefill embeddings, and that the
|
||||
per-item form yields cache entries that own their storage (a torch.split view
|
||||
of the combined tensor pins the whole concatenated buffer).
|
||||
|
||||
CPU-only: exercises mm_utils internals directly, no engine or GPU.
|
||||
CPU-only: exercises mm_schedule internals directly, no engine or GPU.
|
||||
"""
|
||||
|
||||
import pytest
|
||||
import torch
|
||||
|
||||
from sglang.srt.managers import mm_utils
|
||||
from sglang.srt.managers import mm_schedule
|
||||
from sglang.srt.managers.schedule_batch import Modality, MultimodalDataItem
|
||||
from sglang.srt.runtime_context import get_context, get_parallel
|
||||
from sglang.test.ci.ci_register import register_cpu_ci
|
||||
@@ -66,6 +66,14 @@ CHUNKS = [(0, 8), (8, 8), (16, 8), (24, 6)]
|
||||
_CPU = torch.device("cpu")
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def _skip_cuda_ipc_acknowledgement(monkeypatch):
|
||||
"""Keep CPU embedding tests independent of tensor-parallel runtime state."""
|
||||
monkeypatch.setattr(
|
||||
mm_schedule, "_acknowledge_deferred_cuda_ipc_cache_hits", lambda _items: None
|
||||
)
|
||||
|
||||
|
||||
def _num_tokens(item: MultimodalDataItem) -> int:
|
||||
start, end = item.offsets[0]
|
||||
return end - start + 1
|
||||
@@ -97,10 +105,10 @@ def _make_items():
|
||||
|
||||
|
||||
def _run_by_item_chunks(encoder):
|
||||
mm_utils.init_mm_embedding_cache(1 << 30)
|
||||
mm_schedule.init_mm_embedding_cache(1 << 30)
|
||||
items = _make_items()
|
||||
return [
|
||||
mm_utils._get_chunked_embedding_by_item(
|
||||
mm_schedule._get_chunked_embedding_by_item(
|
||||
encoder, items, ITEM_OFFSETS, prefix_len, extend_len, _CPU
|
||||
)
|
||||
for prefix_len, extend_len in CHUNKS
|
||||
@@ -108,12 +116,12 @@ def _run_by_item_chunks(encoder):
|
||||
|
||||
|
||||
def _run_full_chunks(encoder):
|
||||
mm_utils.init_mm_embedding_cache(1 << 30)
|
||||
mm_schedule.init_mm_embedding_cache(1 << 30)
|
||||
items = _make_items()
|
||||
input_ids = torch.zeros(TOTAL_LEN, dtype=torch.long)
|
||||
outs = []
|
||||
for prefix_len, extend_len in CHUNKS:
|
||||
chunk, _ = mm_utils._get_chunked_embedding_full(
|
||||
chunk, _ = mm_schedule._get_chunked_embedding_full(
|
||||
encoder, items, ITEM_OFFSETS, prefix_len, extend_len, input_ids, _CPU
|
||||
)
|
||||
outs.append(chunk)
|
||||
@@ -150,13 +158,13 @@ def test_full_matches_by_item():
|
||||
|
||||
|
||||
def test_list_cache_entries_own_storage():
|
||||
mm_utils.init_mm_embedding_cache(1 << 30)
|
||||
mm_schedule.init_mm_embedding_cache(1 << 30)
|
||||
items = _make_items()
|
||||
mm_utils._get_chunked_embedding_by_item(
|
||||
mm_schedule._get_chunked_embedding_by_item(
|
||||
_encoder_list, items, ITEM_OFFSETS, 0, TOTAL_LEN, _CPU
|
||||
)
|
||||
for item in items:
|
||||
emb = mm_utils.embedding_cache.get_single(item.hash).embedding
|
||||
emb = mm_schedule.embedding_cache.get_single(item.hash).embedding
|
||||
own_bytes = emb.numel() * emb.element_size()
|
||||
assert emb.untyped_storage().nbytes() == own_bytes
|
||||
|
||||
@@ -164,14 +172,14 @@ def test_list_cache_entries_own_storage():
|
||||
def test_tensor_cache_entries_share_storage():
|
||||
# Documents the motivation for the per-item form: split views of the
|
||||
# combined tensor keep the whole concatenated buffer alive.
|
||||
mm_utils.init_mm_embedding_cache(1 << 30)
|
||||
mm_schedule.init_mm_embedding_cache(1 << 30)
|
||||
items = _make_items()
|
||||
mm_utils._get_chunked_embedding_by_item(
|
||||
mm_schedule._get_chunked_embedding_by_item(
|
||||
_encoder_tensor, items, ITEM_OFFSETS, 0, TOTAL_LEN, _CPU
|
||||
)
|
||||
total_tokens = sum(_num_tokens(item) for item in items)
|
||||
for item in items:
|
||||
emb = mm_utils.embedding_cache.get_single(item.hash).embedding
|
||||
emb = mm_schedule.embedding_cache.get_single(item.hash).embedding
|
||||
assert (
|
||||
emb.untyped_storage().nbytes() == total_tokens * HIDDEN * emb.element_size()
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user