{"record":{"id":"12160b86d51c21fb","repo":"huggingface/transformers","slug":"list-index-out-of-range","errorCode":null,"errorMessage":"list index out of range","messagePattern":"list index out of range","errorType":"validation","errorClass":"IndexError","httpStatus":null,"severity":"error","filePath":"src/transformers/integrations/heterogeneity/configuration_utils.py","lineNumber":253,"sourceCode":"            layer_overrides = self._config._heterogeneity_spec.per_layer_overrides\n            reference_overrides = layer_overrides.get(layer_types.index(layer_idx), {})\n            for idx, layer_type in enumerate(layer_types):\n                if layer_type == layer_idx and layer_overrides.get(idx, {}) != reference_overrides:\n                    raise ValueError(\n                        f\"Layer type '{layer_idx}' is not homogeneous across layers (layer {idx} differs). \"\n                        f\"Use an integer index to access a specific layer's config.\"\n                    )\n\n            return _get_layer_config(self._config, reference_overrides)\n\n        # Return a list of configs for a slice of layers\n        if isinstance(layer_idx, slice):\n            return [self[i] for i in range(*layer_idx.indices(len(self)))]\n\n        if layer_idx < 0:\n            layer_idx += len(self)\n        if layer_idx < 0 or layer_idx >= len(self):\n            raise IndexError(\"list index out of range\")\n\n        # Config is actually homogeneous so just return the global config\n        if not self._config.is_heterogeneous:\n            return self._config\n\n        heterogeneity_spec = self._config._heterogeneity_spec\n        return _get_layer_config(\n            self._config,\n            heterogeneity_spec.per_layer_overrides.get(layer_idx, {}),\n        )\n\n\ndef _get_explicit_per_layer_overrides(config: PreTrainedConfig) -> dict[int, dict[str, Any]]:\n    heterogeneity_spec = config._heterogeneity_spec\n    explicit_per_layer_overrides = {}\n\n    for layer_idx in range(config.num_hidden_layers):\n        layer_overrides = copy.deepcopy(heterogeneity_spec.per_layer_overrides.get(layer_idx, {}))","sourceCodeStart":235,"sourceCodeEnd":271,"githubUrl":"https://github.com/huggingface/transformers/blob/a597f974857b3d92939971296bc0deb93d33d780/src/transformers/integrations/heterogeneity/configuration_utils.py#L235-L271","documentation":"`per_layer_config` behaves like a sequence of length `config.num_hidden_layers`. Integer indices outside `[0, num_hidden_layers)` (after the negative-index wrap `layer_idx += len(self)` is applied) raise this standard IndexError, mirroring Python list semantics. It guards the layer-override lookup that follows so `_heterogeneity_spec.per_layer_overrides.get(layer_idx, {})` is only attempted for a real layer.","triggerScenarios":"Calling `config.per_layer_config[num_hidden_layers]`, `config.per_layer_config[-num_hidden_layers - 1]`, or computing an index from a different model's depth (e.g. hard-coding layer 31 on a 24-layer model).","commonSituations":"Hard-coded layer indices copied from another checkpoint; loops using `range(0, num_layers + 1)`; off-by-one errors after switching a script to a smaller/larger variant of the same architecture.","solutions":["Derive the bound from the config itself: iterate `range(len(config.per_layer_config))` or `range(config.num_hidden_layers)`.","For the last layer use index `-1` or `config.num_hidden_layers - 1`, never `num_hidden_layers`.","Validate externally supplied indices before use: `0 <= idx < config.num_hidden_layers`."],"exampleFix":"# before\nlast = config.per_layer_config[config.num_hidden_layers]  # IndexError\n\n# after\nlast = config.per_layer_config[-1]","handlingStrategy":"validation","validationCode":"idx = 31\nn = config.num_hidden_layers\nif not (-n <= idx < n):\n    raise IndexError(f\"layer {idx} out of range for {n} layers\")\nlayer_cfg = config.per_layer_config[idx]","typeGuard":null,"tryCatchPattern":"try:\n    layer_cfg = config.per_layer_config[idx]\nexcept IndexError:\n    layer_cfg = config.per_layer_config[min(max(idx, 0), config.num_hidden_layers - 1)]  # clamp policy","preventionTips":["Always size loops with len(config.per_layer_config) or config.num_hidden_layers, never a literal.","Use -1 for the last layer.","Treat indices parsed from user input or other checkpoints as untrusted and bounds-check them."],"tags":["config","index-error","heterogeneity","off-by-one"],"backgroundTag":null,"analyzedSha":"a597f974857b3d92939971296bc0deb93d33d780","analyzedAt":"2026-08-14T18:24:08.354Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}