{"record":{"id":"dcc84438d3aa9d40","repo":"sgl-project/sglang","slug":"has-entries-but-rank-index","errorCode":null,"errorMessage":"{} has {} entries, but rank_index={}","messagePattern":"(.+?) has (.+?) entries, but rank_index=(.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"python/sglang/srt/mem_cache/storage/umbp/umbp_store.py","lineNumber":121,"sourceCode":"def _select_rank_config_value(\n    value: Any,\n    rank_index: int,\n    field_name: str,\n    cast_type,\n    auto_increment_scalar: bool = False,\n):\n    if value is None:\n        raise ValueError(f\"{field_name} must not be None\")\n\n    candidates = value\n    if isinstance(value, str) and \",\" in value:\n        candidates = [item.strip() for item in value.split(\",\") if item.strip()]\n\n    if isinstance(candidates, (list, tuple)):\n        if not candidates:\n            raise ValueError(f\"{field_name} must not be empty\")\n        if rank_index >= len(candidates):\n            raise ValueError(\n                f\"{field_name} has {len(candidates)} entries, but rank_index={rank_index}\"\n            )\n        return cast_type(candidates[rank_index])\n\n    selected = cast_type(candidates)\n    if auto_increment_scalar:\n        selected = cast_type(selected + rank_index)\n    return selected\n\n\n# extra_config is an explicit allow-list grouped by the scope in which each key\n# takes effect (distributed mode is enabled by master_address). Advanced SPDK\n# knobs outside this list go through the \"spdk_passthrough\" escape hatch.\n_COMMON_EXTRA_KEYS = frozenset(\n    {\n        \"dram_capacity_bytes\",\n        \"ssd_enabled\",\n        \"ssd_storage_dir\",","sourceCodeStart":103,"sourceCodeEnd":139,"githubUrl":"https://github.com/sgl-project/sglang/blob/0132848349585cfe6aae51c4941cbae872505f8a/python/sglang/srt/mem_cache/storage/umbp/umbp_store.py#L103-L139","documentation":"A per-rank list config has fewer entries than the current rank_index, so no value can be selected for this rank.","triggerScenarios":"Passing e.g. numa list with 2 entries while running TP=4 (rank_index 2 or 3), or a comma string '0,1' with rank_index >= 2.","commonSituations":"Scaling tensor parallelism up without extending per-rank storage config lists (NUMA nodes, SSD paths).","solutions":["Extend the list to at least rank_index+1 entries (ideally one per rank)","Or use a single scalar, which with auto_increment_scalar is broadcast/incremented per rank"],"exampleFix":"# before\nextra['ssd_paths'] = '/mnt/nvme0,/mnt/nvme1'  # tp=4\n# after\nextra['ssd_paths'] = '/mnt/nvme0,/mnt/nvme1,/mnt/nvme2,/mnt/nvme3'","handlingStrategy":"validation","validationCode":"vals = rank_list(extra['ssd_paths'])  # as in 4947\nassert tp_rank < len(vals) or len(vals) == 1, f'need >= {tp_rank+1} entries for tp={tp_size}'","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Keep per-rank list length == tensor-parallel size","Use a scalar with auto_increment where the pattern allows"],"tags":["umbp","config-validation","rank-mismatch"],"backgroundTag":"config-validation-failed","analyzedSha":"0132848349585cfe6aae51c4941cbae872505f8a","analyzedAt":"2026-08-28T05:10:05.995Z","schemaVersion":2},"datasetVersion":"2026-08-28T06:17:29.519Z"}