Treat pipeline cache rows with inconsistent sizes as misses

Dawn asks for a blob's size before allocating and copying it. A row whose
stored length, declared size or zstd frame size disagree, or whose
compression flag is unknown, made it allocate the declared size and copy
or decompress past the stored blob. Such rows are now logged and skipped.

From upstream patchzyy/Wiicompiled 6f14bde (#244, KartPad 70951022).

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Wg7mB8ogCWmp9GH19Uc82B
This commit is contained in:
Claude committed 2026-10-05 13:17:48 +00:00
1 parent 5bf1904ca8
commit c12b6b7d99
1 file changed
+28 -2
+28 -2
View File
@@ -6,6 +6,7 @@
#include <deque>
#include <memory>
#include <mutex>
#include <limits>
#include <string>
#include <filesystem>
#include <thread>
@@ -313,8 +314,33 @@ static size_t load_from_database(const XXH128_hash_t& keyHash, void* value, size
if (ret == SQLITE_ROW) {
// Hit
const auto foundPtr = sqlite3_column_blob(load_stmt, 0);
foundSize = sqlite3_column_int64(load_stmt, 1);
const bool compressed = sqlite3_column_int(load_stmt, 2) != 0;
const auto declaredSize = sqlite3_column_int64(load_stmt, 1);
const auto storedSize = sqlite3_column_bytes(load_stmt, 0);
const auto compression = sqlite3_column_int(load_stmt, 2);
const bool compressed = compression == 1;
// Dawn asks for the size before allocating its destination. Validate here,
// not only during the copy: corrupt metadata must become a cache miss.
bool valid = declaredSize > 0 &&
static_cast<uint64_t>(declaredSize) <= std::numeric_limits<size_t>::max() &&
foundPtr != nullptr && storedSize > 0 && (compression == 0 || compression == 1);
if (valid && compressed) {
#if defined(AURORA_CACHE_USE_ZSTD)
// Our writer uses ZSTD_compress, which records the original content size.
const auto frameSize = ZSTD_getFrameContentSize(foundPtr, static_cast<size_t>(storedSize));
valid = frameSize != ZSTD_CONTENTSIZE_ERROR && frameSize != ZSTD_CONTENTSIZE_UNKNOWN &&
frameSize == static_cast<uint64_t>(declaredSize);
#else
valid = false;
#endif
} else if (valid) {
valid = declaredSize == storedSize;
}
if (!valid) {
Log.error("Ignoring cache entry with inconsistent size or compression metadata");
check(sqlite3_reset(load_stmt));
return 0;
}
foundSize = static_cast<size_t>(declaredSize);
if (value == nullptr) {
g_hits.fetch_add(1, std::memory_order_relaxed);
} else {