From a967036afbf56208cbe30fc27ec732ced7ebe4c8 Mon Sep 17 00:00:00 2001 From: Lasse Collin Date: Fri, 24 Jul 2026 21:23:31 +0300 Subject: [PATCH] liblzma: Index decoder: Detect a too large allocation earlier Previously, if an Index had more than PREALLOC_MAX Records, then allocations were done in PREALLOC_DEFAULT chunks (512 Records). That makes little sense in practice because it's likely that one would run out of address space later. Return LZMA_MEM_ERROR error pre-emptively if PREALLOC_MAX would be exceeded. --- src/liblzma/common/index.c | 6 +++--- src/liblzma/common/index.h | 4 +++- src/liblzma/common/index_decoder.c | 5 ++++- 3 files changed, 10 insertions(+), 5 deletions(-) diff --git a/src/liblzma/common/index.c b/src/liblzma/common/index.c index 4d641f9b..ae2e2b4e 100644 --- a/src/liblzma/common/index.c +++ b/src/liblzma/common/index.c @@ -427,11 +427,11 @@ lzma_index_end(lzma_index *i, const lzma_allocator *allocator) } -extern void +extern bool lzma_index_prealloc(lzma_index *i, lzma_vli records) { if (records > PREALLOC_MAX) - records = PREALLOC_MAX; + return true; // If index_decoder.c calls us with records == 0, it's decoding // an Index that has no Records. In that case the decoder won't call @@ -454,7 +454,7 @@ lzma_index_prealloc(lzma_index *i, lzma_vli records) records = INDEX_GROUP_SIZE; i->prealloc = (size_t)(records); - return; + return false; } diff --git a/src/liblzma/common/index.h b/src/liblzma/common/index.h index 007e1188..c06528b2 100644 --- a/src/liblzma/common/index.h +++ b/src/liblzma/common/index.h @@ -38,7 +38,9 @@ extern uint32_t lzma_index_padding_size(const lzma_index *i); /// Set for how many Records to allocate memory the next time /// lzma_index_append() needs to allocate space for a new Record. /// This is used only by the Index decoder. -extern void lzma_index_prealloc(lzma_index *i, lzma_vli records); +/// +/// \return false on success, true if records is too large (SIZE_MAX issue) +extern bool lzma_index_prealloc(lzma_index *i, lzma_vli records); /// Round the variable-length integer to the next multiple of four. diff --git a/src/liblzma/common/index_decoder.c b/src/liblzma/common/index_decoder.c index be22d5a5..a59e4fbf 100644 --- a/src/liblzma/common/index_decoder.c +++ b/src/liblzma/common/index_decoder.c @@ -123,7 +123,10 @@ index_decode(void *coder_ptr, const lzma_allocator *allocator, // Tell the Index handling code how many Records this // Index has to allow it to allocate memory more efficiently. - lzma_index_prealloc(coder->index, coder->count); + // If the Record count is so high that memory allocation would + // fail later, return LZMA_MEM_ERROR now. + if (lzma_index_prealloc(coder->index, coder->count)) + return LZMA_MEM_ERROR; ret = LZMA_OK; coder->sequence = coder->count == 0