apache/cassandra · error · IllegalStateException
Cannot serialize RedundantStatus larger than 0xFFFF. Require
Error message
Cannot serialize RedundantStatus larger than 0xFFFF. Requires serialization changes.
What it means
CommandStoreSerializers.cast packs a RedundantStatus value into 16 bits for the wire format. If the long value exceeds 0xFFFF (65535) it cannot fit in a short, so serialize throws IllegalStateException: supporting larger values would require a wire-format change. This is a hard limit of the current Accord RedundantBefore serialization scheme.
Source
Thrown at src/java/org/apache/cassandra/service/accord/serializers/CommandStoreSerializers.java:278
if (b.endEpoch == Long.MAX_VALUE) out.writeUnsignedVInt(0L);
else out.writeUnsignedVInt(1 + b.endEpoch - b.startEpoch);
serializeNullable(b.staleUntilAtLeast, out);
out.writeUnsignedVInt32(b.bounds.length);
for (TxnId bound : b.bounds)
{
CommandSerializers.txnId.serialize(bound, out);
}
for (int i = 0 ; i < b.bounds.length ; ++i)
{
out.writeShort(cast(b.status(i * 2)));
out.writeShort(cast(b.status(i * 2 + 1)));
}
}
private short cast(long v)
{
if ((v & ~0xFFFF) != 0)
throw new IllegalStateException("Cannot serialize RedundantStatus larger than 0xFFFF. Requires serialization changes.");
return (short)v;
}
@Override
public RedundantBefore.Bounds deserialize(DataInputPlus in) throws IOException
{
if (in.readByte() == 0)
return null;
Range range = KeySerializers.range.deserialize(in);
long startEpoch = in.readUnsignedVInt();
long endEpoch = in.readUnsignedVInt();
if (endEpoch == 0) endEpoch = Long.MAX_VALUE;
else endEpoch = endEpoch - 1 + startEpoch;
Timestamp staleUntilAtLeast = deserializeNullable(in);
int count = in.readUnsignedVInt32();
TxnId[] bounds = new TxnId[count];View on GitHub (pinned to 88fd0f6a0e)
Solutions
- Check the value being cast (epoch/position) to confirm it really exceeds 0xFFFF; if it is unexpected, investigate counter growth/reset logic.
- For legitimately large values, extend the wire format to 4+ bytes for RedundantStatus, coordinating the change across the cluster.
- As a short-term mitigation, restart/reset epoch counters so values stay below 65535 until the serialization change ships.
Example fix
// before
if ((v & ~0xFFFF) != 0)
throw new IllegalStateException("Cannot serialize RedundantStatus larger than 0xFFFF. Requires serialization changes.");
return (short)v;
// after (wire-format change)
in.putInt(v); out.writeInt(cast32(v));
private int cast32(long v) { if ((v & ~0xFFFFFFFFL) != 0) throw ...; return (int)v; } Defensive patterns
Strategy: validation
Validate before calling
long v = status.get();
if ((v & ~0xFFFFL) != 0)
throw new IllegalArgumentException("RedundantStatus value " + v + " exceeds 0xFFFF serialization limit");
serializer.serialize(status, out, version); Try / catch
try {
serializer.serialize(status, out, version);
} catch (IllegalStateException e) {
if (e.getMessage().contains("larger than 0xFFFF"))
logger.error("RedundantStatus overflow; epoch/counter growth exceeded wire format", e);
else throw e;
} Prevention
- Monitor Accord epoch/position counter growth; alert before values approach 65535.
- Plan wire-format upgrades (wider fields) before long-lived clusters hit the limit.
- Add assertions/tests that serialize boundary values 0xFFFF and 0x10000.
When it happens
Trigger: serialize calls cast with a RedundantStatus/Bounds value > 65535, e.g. an epoch or position counter that grew beyond 16 bits before being written for RedundantBefore.
Common situations: Very long-running clusters where Accord epochs or command IDs grow large; tests that synthetically inflate epoch counters; a future format change raising the limit but writing to nodes on the old format.
Understand the failure class
Background: "value must be between 0 and 1" / "out of range" / "must not be negative" errors: fixing range-validation failures across open-source libraries — this error's family across 42 libraries.
Related errors
- Unhandled CheckStatusReply kind:
- Unsupported collection type:
- Corrupted input: expected byte 1, 2, 3, 4, 5 or 6; received
- Corrupted input: expected byte 1, 2, 3, 4 or 5; received
- Corrupted input: expected byte 1 or 2, received " + b
AI-assisted analysis of apache/cassandra@88fd0f6a0e (2026-09-10).
Data as JSON: /api/errors/72f0a990b0612b41.
Report an issue: GitHub.