{"record":{"id":"95fe02edbc16aa74","repo":"prestodb/presto","slug":"length-longer-than-value-length","errorCode":null,"errorMessage":"Length longer than value length","messagePattern":"Length longer than value length","errorType":"validation","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"presto-common/src/main/java/com/facebook/presto/common/block/AbstractVariableWidthBlock.java","lineNumber":114,"sourceCode":"    {\n        checkReadablePosition(position);\n        return getRawSlice(position).equals(getPositionOffset(position) + offset, length, otherSlice, otherOffset, length);\n    }\n\n    @Override\n    public long hash(int position, int offset, int length)\n    {\n        checkReadablePosition(position);\n        return XxHash64.hash(getRawSlice(position), getPositionOffset(position) + offset, length);\n    }\n\n    @Override\n    public int compareTo(int position, int offset, int length, Block otherBlock, int otherPosition, int otherOffset, int otherLength)\n    {\n        checkReadablePosition(position);\n        Slice rawSlice = getRawSlice(position);\n        if (getSliceLength(position) < length) {\n            throw new IllegalArgumentException(\"Length longer than value length\");\n        }\n        return -otherBlock.bytesCompare(otherPosition, otherOffset, otherLength, rawSlice, getPositionOffset(position) + offset, length);\n    }\n\n    @Override\n    public int bytesCompare(int position, int offset, int length, Slice otherSlice, int otherOffset, int otherLength)\n    {\n        checkReadablePosition(position);\n        return getRawSlice(position).compareTo(getPositionOffset(position) + offset, length, otherSlice, otherOffset, otherLength);\n    }\n\n    @Override\n    public void writeBytesTo(int position, int offset, int length, BlockBuilder blockBuilder)\n    {\n        checkReadablePosition(position);\n        blockBuilder.writeBytes(getRawSlice(position), getPositionOffset(position) + offset, length);\n    }\n","sourceCodeStart":96,"sourceCodeEnd":132,"githubUrl":"https://github.com/prestodb/presto/blob/55bb57d202de3b926896fa966c2c4a44c779634e/presto-common/src/main/java/com/facebook/presto/common/block/AbstractVariableWidthBlock.java#L96-L132","documentation":"AbstractVariableWidthBlock.compareTo requires that the requested length does not exceed the actual length of the slice at the given position. If getSliceLength(position) < length, the comparison would read past the value, so the library throws IllegalArgumentException \"Length longer than value length\".","triggerScenarios":"Calling compareTo(position, offset, length, ...) with a length greater than the variable-width value's stored length — e.g. a fixed-length assumption applied to a VARCHAR block, or a length computed from a different block.","commonSituations":"Custom operator code comparing slices using lengths from another block or from fixed-width assumptions; corrupted deserialized slices whose reported lengths shrank; mismatches when comparing CHAR vs VARCHAR encodings.","solutions":["Clamp length: use Math.min(length, getSliceLength(position) - offset) before calling compareTo, or compute length via block.getSliceLength(position).","Fix the caller to derive lengths from the same block/position being compared.","Check for CHAR/FIXED-width assumptions in code operating on VARCHAR blocks.","If slices come from deserialization, validate slice lengths during the read path to catch corruption earlier."],"exampleFix":"// before\nint len = 10; // assumed fixed width\nleftBlock.compareTo(pos, 0, len, rightBlock, otherPos, 0, len);\n// after\nint len = Math.min(10, leftBlock.getSliceLength(pos) - 0);\nleftBlock.compareTo(pos, 0, len, rightBlock, otherPos, 0, len);","handlingStrategy":"validation","validationCode":"static int safeCompareLength(Block varWidthBlock, int position, int requestedLength) {\n    int valueLength = varWidthBlock.getSliceLength(position);\n    checkArgument(requestedLength <= valueLength,\n        \"requested length %s exceeds value length %s\", requestedLength, valueLength);\n    return requestedLength;\n}","typeGuard":null,"tryCatchPattern":"try {\n    int cmp = varBlock.compareTo(position, 0, length, other, otherPosition, 0, length);\n} catch (IllegalArgumentException e) {\n    if (e.getMessage() != null && e.getMessage().contains(\"Length longer than value length\")) {\n        throw new DataCorruptionException(\"comparison length exceeds slice length\", e);\n    }\n    throw e;\n}","preventionTips":["Derive lengths from block.getSliceLength(position) rather than fixed-width assumptions.","Do not mix CHAR-width computations with VARCHAR blocks.","Validate slice lengths after deserializing pages from external sources."],"tags":["presto","block","variable-width","slice","illegal-argument"],"backgroundTag":"length-exceeds-value-length","analyzedSha":"55bb57d202de3b926896fa966c2c4a44c779634e","analyzedAt":"2026-09-04T12:50:26.162Z","contentChangedAt":"2026-09-04T12:50:26.162Z","schemaVersion":2},"datasetVersion":"2026-09-11T21:17:09.523Z"}