diff --git a/python/sglang/srt/server_args.py b/python/sglang/srt/server_args.py index 95aade3ce..e429b8f64 100644 --- a/python/sglang/srt/server_args.py +++ b/python/sglang/srt/server_args.py @@ -1586,6 +1586,11 @@ class ServerArgs: "Phase 2 shared KV initially supports NSATokenToKVPool only; " "HiSparseNSATokenToKVPool is not wired yet." ) + assert self.hicache_storage_backend is None, ( + "enable_nsa_prefill_cp_shared_kv does not support " + "hicache_storage_backend in the host-only CP HiCache stage. " + "Disable hicache_storage_backend or disable CP shared KV." + ) if self.disaggregation_mode == "prefill": assert envs.SGLANG_DISAGGREGATION_ALL_CP_RANKS_TRANSFER.get(), ( "Phase 2 shared KV with PD disaggregation requires " diff --git a/test/registered/unit/server_args/test_server_args.py b/test/registered/unit/server_args/test_server_args.py index e167d83c8..af1f8b365 100644 --- a/test/registered/unit/server_args/test_server_args.py +++ b/test/registered/unit/server_args/test_server_args.py @@ -351,7 +351,7 @@ class TestSSLArgs(unittest.TestCase): self.assertTrue(server_args.enable_ssl_refresh) -class TestHiCacheArgs(unittest.TestCase): +class TestHiCacheArgs(CustomTestCase): def _make_args(self, **overrides) -> ServerArgs: args = ServerArgs(model_path="dummy") for key, value in overrides.items(): @@ -371,6 +371,35 @@ class TestHiCacheArgs(unittest.TestCase): if expected_decode_backend is not None: self.assertEqual(args.decode_attention_backend, expected_decode_backend) + def test_cp_shared_kv_rejects_hicache_storage_backend(self): + args = self._make_args( + enable_hierarchical_cache=True, + enable_nsa_prefill_context_parallel=True, + enable_nsa_prefill_cp_shared_kv=True, + nsa_prefill_cp_mode="in-seq-split", + disaggregation_mode=None, + page_size=64, + enable_hisparse=False, + hicache_storage_backend="mooncake", + tp_size=8, + ) + + with self.assertRaisesRegex( + AssertionError, + "enable_nsa_prefill_cp_shared_kv.*hicache_storage_backend", + ): + model_config = MagicMock() + model_config.hf_config.architectures = ["DeepseekV3ForCausalLM"] + with ( + patch.object(args, "get_model_config", return_value=model_config), + patch( + "sglang.srt.configs.model_config.is_deepseek_nsa", + return_value=True, + ), + patch("torch.cuda.get_device_capability", return_value=(9, 0)), + ): + args._handle_model_specific_adjustments() + def test_hicache_io_backend_and_mem_layout_compatibility(self): cases = [ {