{"record":{"id":"7fcba5e7f059b2fc","repo":"pola-rs/polars","slug":"offset-exceeds-usize-limits","errorCode":null,"errorMessage":"offset exceeds usize limits","messagePattern":"offset exceeds usize limits","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/polars-core/src/frame/column/mod.rs","lineNumber":637,"sourceCode":"        self.slice(-(len as i64), len)\n    }\n    pub fn slice(&self, offset: i64, length: usize) -> Column {\n        match self {\n            Column::Series(s) => s.slice(offset, length).into(),\n            Column::Scalar(s) => {\n                let (_, length) = slice_offsets(offset, length, s.len());\n                s.resize(length).into()\n            },\n        }\n    }\n\n    pub fn split_at(&self, offset: i64) -> (Column, Column) {\n        match self {\n            Column::Scalar(c) => {\n                let len = c.len();\n                let offset = if offset < 0 {\n                    let offset_abs = usize::try_from(offset.strict_abs())\n                        .expect(\"offset exceeds usize limits\")\n                        .min(len);\n                    len - offset_abs\n                } else {\n                    usize::try_from(offset)\n                        .expect(\"offset exceeds usize limits\")\n                        .min(len)\n                };\n                (\n                    Column::Scalar(c.resize(offset)),\n                    Column::Scalar(c.resize(len - offset)),\n                )\n            },\n            Column::Series(_) => {\n                let (l, r) = self.as_materialized_series().split_at(offset);\n                (l.into(), r.into())\n            },\n        }\n    }","sourceCodeStart":619,"sourceCodeEnd":655,"githubUrl":"https://github.com/pola-rs/polars/blob/68506541d2de983056c9eb244e1ea05fab377dfc/crates/polars-core/src/frame/column/mod.rs#L619-L655","documentation":"Column::split_at converts its i64 offset into a usize to resize a scalar column (negative offsets are made absolute first). If the offset's magnitude does not fit in usize, usize::try_from fails and the expect panics with 'offset exceeds usize limits'. In practice this is reachable on 32-bit targets with offsets above u32::MAX, or with degenerate values such as i64::MIN.","triggerScenarios":"Calling Column::split_at / Series::split_at / DataFrame::split_at on a scalar column with an offset outside usize's range: e.g. i64::MAX or i64::MIN offsets on 32-bit builds, or offsets produced by overflowing arithmetic (e.g. -1 * huge_value).","commonSituations":"Running polars on 32-bit targets (wasm32, armv7) and passing offsets computed from user input or subtraction that underflowed/overflowed; offsets coming from a length that was itself an i64 converted without clamping.","solutions":["Clamp the offset to 0..=len before calling split_at: offset = offset.clamp(0, len as i64)","Fix the arithmetic that produced the out-of-range offset (check for i64::MIN/i64::MAX sentinels or overflow)","Build for a 64-bit target so usize covers the whole positive i64 range"],"exampleFix":"// before\nlet (l, r) = col.split_at(offset); // offset may be i64::MIN\n\n// after\nlet offset = offset.clamp(0, col.len() as i64);\nlet (l, r) = col.split_at(offset);","handlingStrategy":"validation","validationCode":"fn safe_offset(offset: i64, len: usize) -> usize {\n    let len = len as i64;\n    offset.clamp(0, len) as usize\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never pass raw external i64 offsets into split_at; clamp to [0, len] first","Audit subtraction/negation producing offsets for i64::MIN overflow","On 32-bit targets, treat any offset above u32::MAX as invalid input"],"tags":["rust","polars","integer-overflow","panic","split","scalar-column"],"backgroundTag":"integer-out-of-range","analyzedSha":"68506541d2de983056c9eb244e1ea05fab377dfc","analyzedAt":"2026-08-19T12:15:06.350Z","contentChangedAt":"2026-08-19T12:15:06.350Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}