apache/cassandra · error · IllegalArgumentException
new position should not be negative
Error message
new position should not be negative
What it means
RandomAccessReader.seek(newPosition) validates that the target offset is non-negative before moving the read cursor. Negative offsets cannot exist in a file, so this indicates a caller bug (underflow or bad offset arithmetic) and throws IllegalArgumentException.
Solutions
- Validate offsets read from files before seeking (reject negatives with a clear corrupt-file error)
- Clamp: if (off >= 0) seek(off) else throw/handle corruption
- Fix the offset arithmetic so it cannot underflow (e.g. check minuend >= subtrahend)
- Run an sstable verify/scrub — a negative offset usually means on-disk corruption
Example fix
// before
long offset = readLongFromFile() - headerSize; // may underflow
reader.seek(offset);
// after
long offset = readLongFromFile() - headerSize;
if (offset < 0)
throw new CorruptFileException("negative offset " + offset);
reader.seek(offset); Defensive patterns
Strategy: validation
Validate before calling
if (offset < 0) throw new CorruptFileException("negative offset: " + offset); reader.seek(offset); Type guard
boolean seekable = offset >= 0 && offset <= reader.getLength();
Try / catch
try { reader.seek(offset); } catch (IllegalArgumentException e) { throw new CorruptFileException(e.getMessage()); } Prevention
- Validate offsets read from disk before use
- Watch for long underflow in offset math
- Scrub corrupt files rather than trusting stored offsets
When it happens
Trigger: Calling rar.seek(negativeLong) — commonly from callers like readSyncMarker, keyIterator/keyReader, createReader, reset, or skipBytes when an offset computation underflows (e.g. position - size where size > position) or a corrupted length/offset field is read from disk and used directly.
Common situations: Reading a corrupted or partially-written sstable whose stored offsets are bogus; subtracting a header size from offset 0; using unsigned values read from disk in signed long math.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- Unable to seek to position
- Attempted skipBytes() on a closed RAR
- Attempted to seek in a closed RAR
- Length must be positive
- Length must not be negative
AI-assisted analysis of apache/cassandra@88fd0f6a0e (2026-09-10).
Data as JSON: /api/errors/ebf2a6d7084d971c.
Report an issue: GitHub.
Appendix: source
Thrown at src/java/org/apache/cassandra/io/util/RandomAccessReader.java:221
/**
* Class to hold a mark to the position of the file
*/
private static class BufferedRandomAccessFileMark implements DataPosition
{
final long pointer;
private BufferedRandomAccessFileMark(long pointer)
{
this.pointer = pointer;
}
}
@Override
public void seek(long newPosition)
{
if (newPosition < 0)
throw new IllegalArgumentException("new position should not be negative");
if (buffer == null)
throw new IllegalStateException("Attempted to seek in a closed RAR");
long bufferOffset = bufferHolderOffset;
if (newPosition >= bufferOffset && newPosition < bufferOffset + buffer.limit())
{
buffer.position((int) (newPosition - bufferOffset));
return;
}
if (newPosition > length())
throw new IllegalArgumentException(String.format("Unable to seek to position %d in %s (%d bytes) in read-only mode",
newPosition, getPath(), length()));
reBufferAt(newPosition);
}
@OverrideView on GitHub (pinned to 88fd0f6a0e)