[refactor] Retire the legacy config accessor and the remaining process singletons (#30493)

This commit is contained in:
Cheng Wan
2026-07-09 02:10:47 -07:00
committed by GitHub
parent 122b3266a2
commit 1f15308dca
158 changed files with 773 additions and 710 deletions
@@ -19,12 +19,9 @@ from sglang.srt.model_executor.forward_batch_info import ForwardBatch, ForwardMo
from sglang.srt.model_executor.forward_context import ForwardContext, forward_context
from sglang.srt.model_executor.graph_shared_output import GraphSharedOutput
from sglang.srt.model_executor.model_runner import ModelRunner
from sglang.srt.runtime_context import get_parallel
from sglang.srt.server_args import set_global_server_args_for_scheduler
from sglang.srt.runtime_context import get_context, get_parallel
from sglang.srt.speculative.spec_info import SpeculativeAlgorithm
from ..mock_server_args import make_mock_server_args
# Unit tests run without distributed initialization. Backends that size buffers by
# attention tensor-parallel degree should see the single-rank default.
_parallel_override = get_parallel().override(attn_tp_size=1)
@@ -338,7 +335,7 @@ class MockModelRunner(ModelRunner):
or case.forward_mode.is_draft_extend_v2()
else 0
)
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -363,7 +360,6 @@ class MockModelRunner(ModelRunner):
is_embedding=False,
kv_cache_dtype="auto",
max_running_requests=None,
model_path=None,
pp_size=1,
revision=None,
speculative_algorithm=None,
@@ -374,7 +370,7 @@ class MockModelRunner(ModelRunner):
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
)
set_global_server_args_for_scheduler(self.server_args)
self.server_args = self._server_args_override.install()
self.req_to_token_pool = ReqToTokenPool(
size=pool_batch_size,
max_context_len=max_context_len,
@@ -16,10 +16,8 @@ from sglang.srt.model_executor.cuda_graph_config import (
from sglang.srt.model_executor.forward_batch_info import ForwardBatch, ForwardMode
from sglang.srt.model_executor.forward_context import ForwardContext, forward_context
from sglang.srt.model_executor.model_runner import ModelRunner
from sglang.srt.runtime_context import get_parallel
from sglang.srt.server_args import set_global_server_args_for_scheduler
from sglang.srt.runtime_context import get_context, get_parallel
from ..mock_server_args import make_mock_server_args
from .dense_attention import (
DEFAULT_DEVICE,
DEFAULT_HEAD_DIM,
@@ -310,7 +308,7 @@ class DSAMockModelRunner(ModelRunner):
self._kernel_warmed_up = True
self.dp_size = 1
self.pp_size = 1
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -341,7 +339,6 @@ class DSAMockModelRunner(ModelRunner):
kv_cache_dtype="auto",
max_running_requests=None,
mem_fraction_static=0.8,
model_path=None,
pp_size=1,
revision=None,
speculative_algorithm=None,
@@ -352,7 +349,7 @@ class DSAMockModelRunner(ModelRunner):
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
)
set_global_server_args_for_scheduler(self.server_args)
self.server_args = self._server_args_override.install()
self.req_to_token_pool = ReqToTokenPool(
size=pool_batch_size,
max_context_len=max_context_len,
@@ -34,10 +34,7 @@ from sglang.srt.model_executor.cuda_graph_config import (
)
from sglang.srt.model_executor.forward_batch_info import ForwardBatch, ForwardMode
from sglang.srt.model_executor.forward_context import ForwardContext, forward_context
from sglang.srt.runtime_context import get_parallel
from sglang.srt.server_args import set_global_server_args_for_scheduler
from ..mock_server_args import make_mock_server_args
from sglang.srt.runtime_context import get_context, get_parallel
# DSV4 backend pre-resolves attention TP at construction; pin to single-rank.
_parallel_override = get_parallel().override(
@@ -334,7 +331,7 @@ class MockDSV4ModelRunner:
self.tp_size = 1
self.dp_size = 1
self.pp_size = 1
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -358,7 +355,6 @@ class MockDSV4ModelRunner:
is_embedding=False,
kv_cache_dtype="auto",
max_running_requests=None,
model_path=None,
pp_size=1,
revision=None,
speculative_algorithm=None,
@@ -369,7 +365,7 @@ class MockDSV4ModelRunner:
device=device,
mem_fraction_static=0.8,
)
set_global_server_args_for_scheduler(self.server_args)
self.server_args = self._server_args_override.install()
self.req_to_token_pool = ReqToTokenPool(
size=pool_batch_size,
max_context_len=max_context_len,
@@ -18,10 +18,8 @@ from sglang.srt.model_executor.cuda_graph_config import (
from sglang.srt.model_executor.forward_batch_info import ForwardBatch, ForwardMode
from sglang.srt.model_executor.forward_context import ForwardContext, forward_context
from sglang.srt.model_executor.model_runner import ModelRunner
from sglang.srt.runtime_context import get_parallel
from sglang.srt.server_args import set_global_server_args_for_scheduler
from sglang.srt.runtime_context import get_context, get_parallel
from ..mock_server_args import make_mock_server_args
from .dense_attention import (
DEFAULT_DEVICE,
DEFAULT_DTYPE,
@@ -325,7 +323,7 @@ class DualChunkMockModelRunner(ModelRunner):
self._kernel_warmed_up = True
self.dp_size = 1
self.pp_size = 1
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -352,7 +350,7 @@ class DualChunkMockModelRunner(ModelRunner):
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
)
set_global_server_args_for_scheduler(self.server_args)
self.server_args = self._server_args_override.install()
self.req_to_token_pool = ReqToTokenPool(
size=pool_batch_size,
max_context_len=max_context_len,
@@ -29,9 +29,7 @@ from sglang.srt.model_executor.cuda_graph_config import (
from sglang.srt.model_executor.forward_batch_info import ForwardBatch, ForwardMode
from sglang.srt.model_executor.forward_context import ForwardContext, forward_context
from sglang.srt.model_executor.model_runner import ModelRunner
from sglang.srt.runtime_context import get_parallel
from ..mock_server_args import make_mock_server_args
from sglang.srt.runtime_context import get_context, get_parallel
_parallel_override = get_parallel().override(attn_tp_size=1)
_parallel_override.__enter__()
@@ -221,7 +219,7 @@ class MockGDNModelRunner(ModelRunner):
or case.forward_mode.is_draft_extend_v2()
else 0
)
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -243,9 +241,7 @@ class MockGDNModelRunner(ModelRunner):
linear_attn_backend="triton",
linear_attn_decode_backend=None,
linear_attn_prefill_backend=None,
mamba_cache_chunk_size=64,
max_running_requests=None,
model_path=None,
revision=None,
speculative_algorithm=None,
speculative_eagle_topk=1 if case.forward_mode.is_target_verify() else 0,
@@ -253,7 +249,11 @@ class MockGDNModelRunner(ModelRunner):
speculative_num_steps=max(0, speculative_num_draft_tokens - 1),
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
# Pin the lazy mamba_cache_chunk_size property cache: production
# derives it from hf_config + page_size, which needs a real model.
_mamba_cache_chunk_size=64,
)
self.server_args = self._server_args_override.install()
cache_shape = Mamba2StateShape.create(
tp_world_size=1,
intermediate_size=case.num_v_heads * head_v_dim,
@@ -29,9 +29,7 @@ from sglang.srt.model_executor.cuda_graph_config import (
from sglang.srt.model_executor.forward_batch_info import ForwardBatch, ForwardMode
from sglang.srt.model_executor.forward_context import ForwardContext, forward_context
from sglang.srt.model_executor.model_runner import ModelRunner
from sglang.srt.runtime_context import get_parallel
from ..mock_server_args import make_mock_server_args
from sglang.srt.runtime_context import get_context, get_parallel
_parallel_override = get_parallel().override(attn_tp_size=1)
_parallel_override.__enter__()
@@ -227,7 +225,7 @@ class MockKDAModelRunner(ModelRunner):
or case.forward_mode.is_draft_extend_v2()
else 0
)
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -249,9 +247,7 @@ class MockKDAModelRunner(ModelRunner):
linear_attn_backend="triton",
linear_attn_decode_backend=None,
linear_attn_prefill_backend=None,
mamba_cache_chunk_size=64,
max_running_requests=None,
model_path=None,
revision=None,
speculative_algorithm=None,
speculative_eagle_topk=1 if case.forward_mode.is_target_verify() else 0,
@@ -259,7 +255,11 @@ class MockKDAModelRunner(ModelRunner):
speculative_num_steps=max(0, speculative_num_draft_tokens - 1),
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
# Pin the lazy mamba_cache_chunk_size property cache: production
# derives it from hf_config + page_size, which needs a real model.
_mamba_cache_chunk_size=64,
)
self.server_args = self._server_args_override.install()
# KDA uses the KimiLinear cache layout (conv_kernel-1, conv_dim) and a
# temporal state of (num_heads, head_dim, head_dim). The KDA backend's
# forward_extend splits conv by [q_dim, k_dim, v_dim] along the conv_dim
@@ -28,9 +28,7 @@ from sglang.srt.model_executor.cuda_graph_config import (
from sglang.srt.model_executor.forward_batch_info import ForwardBatch, ForwardMode
from sglang.srt.model_executor.forward_context import ForwardContext, forward_context
from sglang.srt.model_executor.model_runner import ModelRunner
from sglang.srt.runtime_context import get_parallel
from ..mock_server_args import make_mock_server_args
from sglang.srt.runtime_context import get_context, get_parallel
_parallel_override = get_parallel().override(attn_tp_size=1, attn_tp_rank=0)
_parallel_override.__enter__()
@@ -235,7 +233,7 @@ class MockLightningModelRunner(ModelRunner):
or case.forward_mode.is_draft_extend_v2()
else 0
)
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -258,9 +256,7 @@ class MockLightningModelRunner(ModelRunner):
linear_attn_backend="triton",
linear_attn_decode_backend=None,
linear_attn_prefill_backend=None,
mamba_cache_chunk_size=64,
max_running_requests=None,
model_path=None,
revision=None,
speculative_algorithm=None,
speculative_eagle_topk=1 if case.forward_mode.is_target_verify() else 0,
@@ -268,7 +264,11 @@ class MockLightningModelRunner(ModelRunner):
speculative_num_steps=max(0, speculative_num_draft_tokens - 1),
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
# Pin the lazy mamba_cache_chunk_size property cache: production
# derives it from hf_config + page_size, which needs a real model.
_mamba_cache_chunk_size=64,
)
self.server_args = self._server_args_override.install()
# Lightning seg_la temporal state is [num_heads, head_dim, head_dim]; Bailing's
# mamba2_cache_params sets intermediate_size=0, n_groups=0, conv_kernel=1
# because seg_la does not use a conv state (the conv shape collapses to (0, 0)).
@@ -7,7 +7,7 @@ from torch import nn
# Patch TP world size / rank before importing modules that read them at __init__.
import sglang.srt.layers.linear as _linear_mod
from sglang.srt.runtime_context import get_parallel
from sglang.srt.runtime_context import get_context, get_parallel
_parallel_override = get_parallel().override(
tp_size=1, tp_rank=0, attn_tp_size=1, attn_tp_rank=0
@@ -50,8 +50,6 @@ from sglang.srt.model_executor.forward_context import ( # noqa: E402
)
from sglang.srt.model_executor.model_runner import ModelRunner # noqa: E402
from ..mock_server_args import make_mock_server_args
# Tiny dims chosen to be the minimum that satisfies MambaMixer2's TP/chunk asserts:
# - num_heads % tp_size == 0 (tp_size=1)
# - intermediate_size = num_heads * head_dim
@@ -330,7 +328,7 @@ class MockMamba2ModelRunner(ModelRunner):
)
else:
speculative_num_draft_tokens = 0
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -351,7 +349,7 @@ class MockMamba2ModelRunner(ModelRunner):
enable_mis=False,
# `RowParallelLinear.forward` (called by the production
# `MambaMixer2.out_proj`) consults
# `get_global_server_args().enable_symm_mem` to decide whether
# `get_server_args().enable_symm_mem` to decide whether
# to wrap allocations in a symmetric-memory context. With
# `world_size=1` the wrapper short-circuits, but the
# attribute read still happens, so it must exist on the mock
@@ -367,9 +365,7 @@ class MockMamba2ModelRunner(ModelRunner):
# `MambaMixer2.forward_decode` calls into. Set it explicitly so
# the DECODE fixture path becomes reachable.
mamba_backend="triton",
mamba_cache_chunk_size=64,
max_running_requests=None,
model_path=None,
revision=None,
speculative_algorithm=None,
speculative_eagle_topk=0,
@@ -377,17 +373,14 @@ class MockMamba2ModelRunner(ModelRunner):
speculative_num_steps=0,
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
# Pin the lazy mamba_cache_chunk_size property cache: production
# derives it from hf_config + page_size, which needs a real model.
_mamba_cache_chunk_size=64,
)
# Install this fixture's `server_args` as the global so that
# `is_symmetric_memory_enabled()` (called from
# `RowParallelLinear.forward`) reads our `enable_symm_mem=False`
# value. Without this, a previous test in the discover sweep
# whose fixture *did* call `set_global_server_args_for_scheduler`
# would leave a SimpleNamespace without `enable_symm_mem` as the
# global, and the mamba2 forward would AttributeError.
from sglang.srt.server_args import set_global_server_args_for_scheduler
set_global_server_args_for_scheduler(self.server_args)
# install() publishes this fixture's config, so production reads
# like `is_symmetric_memory_enabled()` (RowParallelLinear.forward)
# see our `enable_symm_mem=False` for the fixture's lifetime.
self.server_args = self._server_args_override.install()
# Install the selective-state-update backend that
# `MambaMixer2.forward_decode` requires. In production the
@@ -23,10 +23,7 @@ from sglang.srt.model_executor.forward_context import (
)
from sglang.srt.model_executor.graph_shared_output import GraphSharedOutput
from sglang.srt.model_executor.model_runner import ModelRunner
from sglang.srt.runtime_context import get_parallel
from sglang.srt.server_args import set_global_server_args_for_scheduler
from ..mock_server_args import make_mock_server_args
from sglang.srt.runtime_context import get_context, get_parallel
_parallel_override = get_parallel().override(attn_tp_size=1)
_parallel_override.__enter__()
@@ -242,7 +239,7 @@ class MockMLAModelRunner(ModelRunner):
or case.forward_mode.is_draft_extend_v2()
else 0
)
self.server_args = make_mock_server_args(
self._server_args_override = get_context().override_server_args(
attention_backend=case.backend,
chunked_prefill_size=-1,
cuda_graph_config=CudaGraphConfig(
@@ -270,7 +267,6 @@ class MockMLAModelRunner(ModelRunner):
is_embedding=False,
kv_cache_dtype="fp8_e4m3" if fp8_kv_cache else "auto",
max_running_requests=None,
model_path=None,
pp_size=1,
revision=None,
speculative_algorithm=None,
@@ -281,7 +277,7 @@ class MockMLAModelRunner(ModelRunner):
triton_attention_num_kv_splits=8,
triton_attention_split_tile_size=None,
)
set_global_server_args_for_scheduler(self.server_args)
self.server_args = self._server_args_override.install()
self.req_to_token_pool = ReqToTokenPool(
size=pool_batch_size,
max_context_len=max_context_len,
@@ -1,62 +0,0 @@
"""Mock `ServerArgs` factory for attention-backend unit tests.
Production attention backends read many `ServerArgs` attributes and call
several `ServerArgs` methods at backend construction time. The set grows
monotonically: new attention features add new attributes/methods to
`ServerArgs`, and a fixture that mocks `server_args` as a manually-
populated `SimpleNamespace` will silently miss the new field and fail
with `AttributeError` the next time a backend looks it up.
`make_mock_server_args` sidesteps this by instantiating a real
`ServerArgs` (the dataclass) with all defaults from the dataclass
definition, then overlaying the caller's explicit overrides. New
`ServerArgs` attributes are picked up automatically with their default
values; methods like `enable_mamba_extra_buffer()` work because the
object is a real `ServerArgs` instance, so methods are bound correctly.
`__post_init__` is intentionally bypassed (via `object.__new__`) so
fixture callers don't have to supply a real `model_path`; the
validation it performs is irrelevant for module-level attention tests.
"""
import dataclasses
from sglang.srt.model_executor.cuda_graph_config import default_cuda_graph_config
from sglang.srt.server_args import ServerArgs
def make_mock_server_args(**overrides) -> ServerArgs:
"""Return a `ServerArgs` instance with all defaults pre-populated.
The instance is built by `object.__new__(ServerArgs)` so `__post_init__`
does not run — fixture callers do not need to supply a valid
`model_path` or other required-field values.
Any field with a `default` or `default_factory` in the dataclass
definition is set automatically. Caller-supplied `overrides` replace
those defaults; unknown keys are also stored (matching `SimpleNamespace`
semantics) so fixtures can attach test-only attributes when needed.
If an override name corresponds to a read-only `@property` on
`ServerArgs`, the value is stored under `_<name>` instead — many
`ServerArgs` properties cache through `_<name>` and return it when
set, so fixture callers can keep using the public name and let this
helper translate.
"""
sa = object.__new__(ServerArgs)
for f in dataclasses.fields(ServerArgs):
if f.default is not dataclasses.MISSING:
setattr(sa, f.name, f.default)
elif f.default_factory is not dataclasses.MISSING:
setattr(sa, f.name, f.default_factory())
for k, v in overrides.items():
cls_attr = getattr(type(sa), k, None)
if isinstance(cls_attr, property):
setattr(sa, f"_{k}", v)
else:
setattr(sa, k, v)
if sa.cuda_graph_config is None:
sa.cuda_graph_config = default_cuda_graph_config()
if not hasattr(sa, "_cuda_graph_config_locked"):
sa._cuda_graph_config_locked = set()
return sa
@@ -17,7 +17,6 @@ from sglang.srt.model_executor.forward_batch_info import (
from sglang.srt.model_executor.input_buffers import _forward_input_buffer_pool
from sglang.srt.model_executor.runner import set_global_graph_memory_pool
from sglang.srt.runtime_context import get_parallel
from sglang.srt.server_args import set_global_server_args_for_scheduler
from sglang.srt.speculative.draft_utils import DraftBackendFactory
from sglang.srt.speculative.eagle_draft_cuda_graph_runner import (
EAGLEDraftCudaGraphRunner,
@@ -327,8 +326,7 @@ def _configure_runner_for_eagle_draft(
"torch_compile_max_bs": 0,
"use_mla_backend": runner.use_mla_backend,
}
for key, value in updates.items():
setattr(server_args, key, value)
server_args.override(source="attention-unittest-eagle-draft", **updates)
runner.spec_algorithm = SpeculativeAlgorithm.EAGLE
runner.is_draft_worker = True
@@ -339,7 +337,6 @@ def _configure_runner_for_eagle_draft(
runner.model_config.dtype = runner.dtype
runner.model_config.vocab_size = settings.vocab_size
runner.model_config.hf_config.vocab_size = settings.vocab_size
set_global_server_args_for_scheduler(server_args)
def _build_eagle_draft_fixture(