apache/cassandra · error · IOException

Corrupted key cache. Key length of %d is longer than maximum

Error message

Corrupted key cache. Key length of %d is longer than maximum of %d

What it means

While loading the saved key cache from disk, CacheService.KeyCacheSerializer.deserialize reads each entry's key length and rejects values exceeding FBUtilities.MAX_UNSIGNED_SHORT (65535) as an IOException, since such a length cannot have been written by a valid serializer run. This indicates the cache file is corrupt, truncated mid-entry, or was written by an incompatible version whose stream layout shifted.

Source

Thrown at src/java/org/apache/cassandra/service/CacheService.java:505

        {
            AbstractRowIndexEntry entry = CacheService.instance.keyCache.getInternal(key);
            if (entry == null)
                return;

            writeSSTable(cfs, key.desc, out);
            out.writeInt(key.key.length);
            out.write(key.key);
            entry.serializeForCache(out);
        }

        public Future<Pair<KeyCacheKey, AbstractRowIndexEntry>> deserialize(DataInputPlus input) throws IOException
        {
            Pair<KeyCacheSupport<?>, SSTableFormat<?, ?>> reader = readSSTable(input);
            boolean skipEntry = reader.left == null || !reader.left.getKeyCache().isEnabled();

            int keyLength = input.readInt();
            if (keyLength > FBUtilities.MAX_UNSIGNED_SHORT)
                throw new IOException(String.format("Corrupted key cache. Key length of %d is longer than maximum of %d",
                                                    keyLength, FBUtilities.MAX_UNSIGNED_SHORT));
            ByteBuffer key = ByteBufferUtil.read(input, keyLength);

            if (skipEntry)
            {
                // The sstable doesn't exist anymore, so we can't be sure of the exact version and assume its the current version. The only case where we'll be
                // wrong is during upgrade, in which case we fail at deserialization. This is not a huge deal however since 1) this is unlikely enough that
                // this won't affect many users (if any) and only once, 2) this doesn't prevent the node from starting and 3) CASSANDRA-10219 shows that this
                // part of the code has been broken for a while without anyone noticing (it is, btw, still broken until CASSANDRA-10219 is fixed).
                SSTableFormat.KeyCacheValueSerializer<?, ?> serializer = reader.right.getKeyCacheValueSerializer();

                serializer.skip(input);
                return null;
            }
            long pos = ((RandomAccessReader) input).getPosition();
            AbstractRowIndexEntry cacheValue;
            try
            {

View on GitHub (pinned to 88fd0f6a0e)

Solutions

  1. Delete the corrupted key cache file (saved_caches directory, e.g. /var/lib/cassandra/saved_caches/*) and restart — Cassandra rebuilds the cache.
  2. Clear the whole saved_caches directory if multiple cache files fail to load.
  3. Check filesystem/disk health (dmesg, fsck) if corruption recurs.
  4. After version upgrades, do not carry over cache files from the previous version's data directory.

Example fix

// before
systemctl start cassandra   # fails/loops on corrupted key cache
// after
rm -f /var/lib/cassandra/saved_caches/*
systemctl start cassandra   # cache rebuilt from SSTables
Defensive patterns

Strategy: try-catch

Validate before calling

// Pre-start check: file size must plausibly hold valid entries (not truncated)
File f = new File(savedCachesDir, "KeyCache-*.db");
if (f.exists() && f.length() < 8) Files.delete(f.toPath()); // too small to be valid, delete and let it rebuild

Try / catch

try {
    cacheService.loadCaches();
} catch (IOException e) {
    if (e.getMessage().startsWith("Corrupted key cache")) {
        logger.warn("Key cache file corrupted, deleting and rebuilding", e);
        FileUtils.deleteQuietly(new File(savedCachesDir, "KeyCache-*.db"));
        cacheService.loadCaches(); // retry after cleanup
    } else {
        throw e;
    }
}

Prevention

When it happens

Trigger: Node startup cache load reading a key cache file where the int read as keyLength exceeds 65535 — i.e. misaligned reads after truncation, disk corruption, or deserializing a file produced by an incompatible Cassandra version.

Common situations: Unclean shutdown (OOM/kill -9) that truncated the cache file; disk-level corruption; restore of cache files from a mismatched backup; upgrades across versions with changed cache serialization layout.

Understand the failure class

Background: Checksum mismatch errors: "checksum verification failed", "digest mismatch", "expected vs actual checksum" — what they mean and how to fix them — this error's family across 41 libraries.

Related errors


AI-assisted analysis of apache/cassandra@88fd0f6a0e (2026-09-10). Data as JSON: /api/errors/254c3dc8042b5ae0. Report an issue: GitHub.