{"record":{"id":"6762dfe594f09f04","repo":"Pumpkin-MC/Pumpkin","slug":"string-length-len-exceeds-maximum-of-max-string","errorCode":null,"errorMessage":"String length {len} exceeds maximum of {MAX_STRING_LENGTH}","messagePattern":"String length (.+?) exceeds maximum of (.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"warning","filePath":"crates/pumpkin-protocol/src/serial/deserializer.rs","lineNumber":159,"sourceCode":"                        }\n                    }\n                    return Err(err);\n                }\n            }\n        }\n        // SAFETY: All N elements were successfully initialized in the loop above.\n        Ok(buf.map(|elem| unsafe { elem.assume_init() }))\n    }\n}\n\nimpl PacketRead for String {\n    fn read<R: Read>(reader: &mut R) -> Result<Self, Error> {\n        const MAX_STRING_LENGTH: usize = 32767;\n\n        let len = VarUInt::read(reader)?.0 as usize;\n\n        if len > MAX_STRING_LENGTH {\n            return Err(Error::new(\n                ErrorKind::InvalidData,\n                format!(\"String length {len} exceeds maximum of {MAX_STRING_LENGTH}\"),\n            ));\n        }\n\n        let mut buf = vec![0u8; len];\n        reader.read_exact(&mut buf)?;\n\n        Self::from_utf8(buf)\n            .map_err(|_| Error::new(ErrorKind::InvalidData, \"Invalid UTF-8 sequence\"))\n    }\n}\n\nimpl<T: PacketRead> PacketRead for Vec<T> {\n    fn read<R: Read>(reader: &mut R) -> Result<Self, Error> {\n        let len = VarUInt::read(reader)?.0 as usize;\n        if len > 65536 {\n            return Err(Error::new(","sourceCodeStart":141,"sourceCodeEnd":177,"githubUrl":"https://github.com/Pumpkin-MC/Pumpkin/blob/8d4639e25a57c15e47448ec327c780d41bbf2356/crates/pumpkin-protocol/src/serial/deserializer.rs#L141-L177","documentation":"This error is thrown by the `PacketRead for String` deserializer in pumpkin-protocol when a string's length prefix (read as a VarUInt) exceeds MAX_STRING_LENGTH (32767). The limit protects against malformed or hostile packets causing huge allocations. It means the incoming packet's length prefix was too large to be a legitimate string.","triggerScenarios":"Deserializing a packet whose String field declares a length prefix > 32767 via <String as PacketRead>::read — e.g. corrupted data, desynced stream, or malicious client.","commonSituations":"A malicious/corrupted client sends an oversized string length; a packet stream desync (wrong VarUInt parse) makes a random byte sequence get read as a length; protocol version mismatch reinterprets fields.","solutions":["Verify the sender/protocol version matches the deserializer's expectations","Check for stream desync: log the byte offset and confirm the VarUInt position","Validate/limit input at a higher layer and drop the offending packet/connection","Inspect raw bytes at the read offset to confirm the length prefix is genuine"],"exampleFix":"// before\nlet name: String = packet.read()?; // panics/errs on oversized len\n// after\nmatch String::read(&mut reader) {\n    Ok(s) => s,\n    Err(e) => { log::warn!(\"bad packet: {e}\"); drop_connection(); return; }\n}","handlingStrategy":"validation","validationCode":"// peek the VarUInt before trusting it\nlet (len, _) = VarUInt::peek(reader)?;\nif len > 32767 { return Err(PacketError::OversizedString(len)); }","typeGuard":"fn is_valid_string_len(len: usize) -> bool { len <= 32767 }","tryCatchPattern":null,"preventionTips":["Keep client and server protocol versions in sync","Enforce packet-level size caps before field deserialization","Log the byte offset on failure to aid desync debugging"],"tags":["protocol","serialization","malformed-packet"],"backgroundTag":"value-out-of-range","analyzedSha":"8d4639e25a57c15e47448ec327c780d41bbf2356","analyzedAt":"2026-09-09T15:32:22.916Z","contentChangedAt":"2026-09-09T15:32:22.916Z","schemaVersion":2},"datasetVersion":"2026-09-16T04:17:20.429Z"}