{"record":{"id":"41407edcde09e1e7","repo":"prestodb/presto","slug":"first-column-value-length-is-negative","errorCode":null,"errorMessage":"First column value length is negative","messagePattern":"First column value length is negative","errorType":"exception","errorClass":"RcFileCorruptionException","httpStatus":null,"severity":"error","filePath":"presto-rcfile/src/main/java/com/facebook/presto/rcfile/RcFileReader.java","lineNumber":638,"sourceCode":"                int valueLength = readNextValueLength();\n                currentOffset += valueLength;\n            }\n        }\n\n        private int readNextValueLength()\n                throws IOException\n        {\n            if (runLength > 0) {\n                runLength--;\n                return lastValueLength;\n            }\n\n            int valueLength = toIntExact(readVInt(lengthsInput));\n\n            // negative length is used to encode a run or the last value\n            if (valueLength < 0) {\n                if (lastValueLength == -1) {\n                    throw new RcFileCorruptionException(\"First column value length is negative\");\n                }\n                runLength = (~valueLength) - 1;\n                return lastValueLength;\n            }\n\n            runLength = 0;\n            lastValueLength = valueLength;\n            return valueLength;\n        }\n\n        private Slice getDataBuffer()\n                throws IOException\n        {\n            if (compressed) {\n                if (decompressedBuffer.length < uncompressedDataSize) {\n                    decompressedBuffer = new byte[uncompressedDataSize];\n                }\n                Slice buffer = Slices.wrappedBuffer(decompressedBuffer, 0, uncompressedDataSize);","sourceCodeStart":620,"sourceCodeEnd":656,"githubUrl":"https://github.com/prestodb/presto/blob/55bb57d202de3b926896fa966c2c4a44c779634e/presto-rcfile/src/main/java/com/facebook/presto/rcfile/RcFileReader.java#L620-L656","documentation":"In RCFile run-length encoding of value lengths, a negative length encodes a run or terminator and requires a previously seen lastValueLength to resolve. If the very first decoded length for a column is negative there is no prior value to reference, so the reader throws RcFileCorruptionException.","triggerScenarios":"Reading a column whose first encoded value length is negative — i.e. the length stream starts with run-length metadata instead of an actual length, which only happens when the stream is misaligned or corrupt.","commonSituations":"Files written by buggy or incompatible RCFile writers; seeking into the middle of a compressed stream so the length stream starts mid-run; byte-level corruption in the column length stream.","solutions":["Treat the file as corrupt and re-generate or re-copy it from the source","Confirm the reader and writer versions/Hive compatibility match","Verify you are not seeking to a non-sync-bound offset inside the file","Catch RcFileCorruptionException and skip/report the offending file"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"try { reader.read(); }\ncatch (RcFileCorruptionException e) {\n    if (e.getMessage().contains(\"value length is negative\")) {\n        // mark file/stripe corrupt; skip or re-generate\n    } else { throw e; }\n}","preventionTips":["Read RCFiles only from sync-marker-aligned offsets, never mid-stream","Keep writer/reader Hive versions compatible","Checksum column streams after writing","Treat seek-then-read patterns as high risk for corruption errors"],"tags":["rcfile","corruption","run-length-encoding"],"backgroundTag":"file-corruption-detected","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"}