aeron-io/aeron · error · IllegalArgumentException
lengthTwo < 0
Error message
lengthTwo < 0: {lengthTwo} What it means
Thrown by Publication.validateAndComputeLength when lengthTwo is negative in a vectored (two-buffer) offer. The helper checks both component lengths before summing them, so the second buffer's length must also be non-negative.
Solutions
- Validate lengthTwo >= 0 before the vectored offer call.
- Ensure the second buffer is in read mode (flip() after writes) before computing its length.
- Add boundary assertions where the two lengths are derived so negative values cannot reach offer().
Example fix
// before
int bodyLen = bodyEnd - bodyStart; // negative when bodyStart > bodyEnd
publication.offer(header, 0, headerLen, body, 0, bodyLen);
// after
int bodyLen = bodyEnd - bodyStart;
if (bodyLen < 0)
{
throw new IllegalArgumentException("invalid body length: " + bodyLen);
}
publication.offer(header, 0, headerLen, body, 0, bodyLen); Defensive patterns
Strategy: validation
Validate before calling
if (lengthTwo < 0) { throw new IllegalArgumentException("second buffer length must be >= 0, got " + lengthTwo); } Type guard
boolean isValidSecondLength(int lengthTwo) { return lengthTwo >= 0; } Try / catch
try
{
publication.offer(buf1, off1, len1, buf2, off2, len2);
}
catch (IllegalArgumentException e)
{
// negative lengthTwo: correct the payload buffer sizing logic
log.error("invalid vectored offer", e);
} Prevention
- Flip the payload buffer before measuring; un-flipped buffers yield negative remaining().
- Assert slice boundaries (start <= end) where the second length is derived.
- Validate decoded/wire lengths before using them as buffer lengths.
- Keep vectored length computation in tested utility methods.
When it happens
Trigger: publication.offer(bufferOne, offsetOne, lengthOne, bufferTwo, offsetTwo, lengthTwo) with lengthTwo < 0 — commonly a negative remaining() on the second buffer or a miscomputed payload length.
Common situations: Header+payload sends where the payload buffer wasn't flipped; deserialized length fields applied directly as buffer lengths; slicing errors producing inverted offsets on the second buffer.
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
- lengthOne < 0
- padding exceeds maxFramedLength of , length=
- invalid block length , remaining space in term is
- invalid length:
- overflow totalLength=
AI-assisted analysis of aeron-io/aeron@6d60124e15 (2026-09-12).
Data as JSON: /api/errors/61cf990c5732a3ae.
Report an issue: GitHub.
Appendix: source
Thrown at aeron-client/src/main/java/io/aeron/Publication.java:726
final void checkMaxMessageLength(final int length)
{
if (length > maxMessageLength)
{
throw new IllegalArgumentException(
"message exceeds maxMessageLength of " + maxMessageLength + ", length=" + length);
}
}
static int validateAndComputeLength(final int lengthOne, final int lengthTwo)
{
if (lengthOne < 0)
{
throw new IllegalArgumentException("lengthOne < 0: " + lengthOne);
}
if (lengthTwo < 0)
{
throw new IllegalArgumentException("lengthTwo < 0: " + lengthTwo);
}
final int totalLength = lengthOne + lengthTwo;
if (totalLength < 0)
{
throw new IllegalArgumentException("overflow totalLength=" + totalLength);
}
return totalLength;
}
/**
* Returns a string representation of a position. Generally used for errors. If the position is a valid error then
* String name of the error will be returned. If the value is 0 or greater the text will be "NONE". If the position
* is negative, but not a known error code then "UNKNOWN" will be returned.
*
* @param position position value returned from a call to offer.
* @return String representation of the error.View on GitHub (pinned to 6d60124e15)