diff --git a/src/liblzma/common/common.c b/src/liblzma/common/common.c index efe6c226..28aa2b71 100644 --- a/src/liblzma/common/common.c +++ b/src/liblzma/common/common.c @@ -53,6 +53,27 @@ lzma_alloc(size_t size, const lzma_allocator *allocator) } +extern void * lzma_attribute((__malloc__)) lzma_attr_alloc_size(1) +lzma_alloc_zero(size_t size, const lzma_allocator *allocator) +{ + // Some calloc() variants return NULL if called with size == 0. + if (size == 0) + size = 1; + + void *ptr; + + if (allocator != NULL && allocator->alloc != NULL) { + ptr = allocator->alloc(allocator->opaque, 1, size); + if (ptr != NULL) + memzero(ptr, size); + } else { + ptr = calloc(1, size); + } + + return ptr; +} + + extern void lzma_free(void *ptr, const lzma_allocator *allocator) { diff --git a/src/liblzma/common/common.h b/src/liblzma/common/common.h index 42d27d83..b10a72e2 100644 --- a/src/liblzma/common/common.h +++ b/src/liblzma/common/common.h @@ -234,6 +234,12 @@ struct lzma_internal_s { extern void *lzma_alloc(size_t size, const lzma_allocator *allocator) lzma_attribute((__malloc__)) lzma_attr_alloc_size(1); +/// Allocates memory and zeroes it (like calloc()). This can be faster +/// than lzma_alloc() + memzero() while being backward compatible with +/// custom allocators. +extern void * lzma_attribute((__malloc__)) lzma_attr_alloc_size(1) + lzma_alloc_zero(size_t size, const lzma_allocator *allocator); + /// Frees memory extern void lzma_free(void *ptr, const lzma_allocator *allocator);