mirror of
https://gitlab.freedesktop.org/mesa/mesa.git
synced 2026-05-09 02:28:10 +02:00
util/ralloc: Add helpers for growing zero-initialized memory
Unfortunately, we can't quite follow the standard C conventions for these because ralloc doesn't know the sizes of pointers. Reviewed-by: Eric Anholt <eric@anholt.net>
This commit is contained in:
parent
6212326941
commit
6c0f75c953
2 changed files with 87 additions and 0 deletions
|
|
@ -197,6 +197,21 @@ reralloc_size(const void *ctx, void *ptr, size_t size)
|
|||
return resize(ptr, size);
|
||||
}
|
||||
|
||||
void *
|
||||
rerzalloc_size(const void *ctx, void *ptr, size_t old_size, size_t new_size)
|
||||
{
|
||||
if (unlikely(ptr == NULL))
|
||||
return rzalloc_size(ctx, new_size);
|
||||
|
||||
assert(ralloc_parent(ptr) == ctx);
|
||||
ptr = resize(ptr, new_size);
|
||||
|
||||
if (new_size > old_size)
|
||||
memset((char *)ptr + old_size, 0, new_size - old_size);
|
||||
|
||||
return ptr;
|
||||
}
|
||||
|
||||
void *
|
||||
ralloc_array_size(const void *ctx, size_t size, unsigned count)
|
||||
{
|
||||
|
|
@ -224,6 +239,16 @@ reralloc_array_size(const void *ctx, void *ptr, size_t size, unsigned count)
|
|||
return reralloc_size(ctx, ptr, size * count);
|
||||
}
|
||||
|
||||
void *
|
||||
rerzalloc_array_size(const void *ctx, void *ptr, size_t size,
|
||||
unsigned old_count, unsigned new_count)
|
||||
{
|
||||
if (new_count > SIZE_MAX/size)
|
||||
return NULL;
|
||||
|
||||
return rerzalloc_size(ctx, ptr, size * old_count, size * new_count);
|
||||
}
|
||||
|
||||
void
|
||||
ralloc_free(void *ptr)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -121,6 +121,23 @@ void *rzalloc_size(const void *ctx, size_t size) MALLOCLIKE;
|
|||
*/
|
||||
void *reralloc_size(const void *ctx, void *ptr, size_t size);
|
||||
|
||||
/**
|
||||
* Resize a ralloc-managed array, preserving data and initializing any newly
|
||||
* allocated data to zero.
|
||||
*
|
||||
* Similar to \c realloc. Unlike C89, passing 0 for \p size does not free the
|
||||
* memory. Instead, it resizes it to a 0-byte ralloc context, just like
|
||||
* calling ralloc_size(ctx, 0). This is different from talloc.
|
||||
*
|
||||
* \param ctx The context to use for new allocation. If \p ptr != NULL,
|
||||
* it must be the same as ralloc_parent(\p ptr).
|
||||
* \param ptr Pointer to the memory to be resized. May be NULL.
|
||||
* \param old_size The amount of memory in the previous allocation, in bytes.
|
||||
* \param new_size The amount of memory to allocate, in bytes.
|
||||
*/
|
||||
void *rerzalloc_size(const void *ctx, void *ptr,
|
||||
size_t old_size, size_t new_size);
|
||||
|
||||
/// \defgroup array Array Allocators @{
|
||||
|
||||
/**
|
||||
|
|
@ -177,6 +194,28 @@ void *reralloc_size(const void *ctx, void *ptr, size_t size);
|
|||
#define reralloc(ctx, ptr, type, count) \
|
||||
((type *) reralloc_array_size(ctx, ptr, sizeof(type), count))
|
||||
|
||||
/**
|
||||
* \def rerzalloc(ctx, ptr, type, count)
|
||||
* Resize a ralloc-managed array, preserving data and initializing any newly
|
||||
* allocated data to zero.
|
||||
*
|
||||
* Similar to \c realloc. Unlike C89, passing 0 for \p size does not free the
|
||||
* memory. Instead, it resizes it to a 0-byte ralloc context, just like
|
||||
* calling ralloc_size(ctx, 0). This is different from talloc.
|
||||
*
|
||||
* More than a convenience function, this also checks for integer overflow when
|
||||
* multiplying \c sizeof(type) and \p count. This is necessary for security.
|
||||
*
|
||||
* \param ctx The context to use for new allocation. If \p ptr != NULL,
|
||||
* it must be the same as ralloc_parent(\p ptr).
|
||||
* \param ptr Pointer to the array to be resized. May be NULL.
|
||||
* \param type The element type.
|
||||
* \param old_count The number of elements in the previous allocation.
|
||||
* \param new_count The number of elements to allocate.
|
||||
*/
|
||||
#define rerzalloc(ctx, ptr, type, old_count, new_count) \
|
||||
((type *) rerzalloc_array_size(ctx, ptr, sizeof(type), old_count, new_count))
|
||||
|
||||
/**
|
||||
* Allocate memory for an array chained off the given context.
|
||||
*
|
||||
|
|
@ -217,6 +256,29 @@ void *rzalloc_array_size(const void *ctx, size_t size, unsigned count) MALLOCLIK
|
|||
*/
|
||||
void *reralloc_array_size(const void *ctx, void *ptr, size_t size,
|
||||
unsigned count);
|
||||
|
||||
/**
|
||||
* Resize a ralloc-managed array, preserving data and initializing any newly
|
||||
* allocated data to zero.
|
||||
*
|
||||
* Similar to \c realloc. Unlike C89, passing 0 for \p size does not free the
|
||||
* memory. Instead, it resizes it to a 0-byte ralloc context, just like
|
||||
* calling ralloc_size(ctx, 0). This is different from talloc.
|
||||
*
|
||||
* More than a convenience function, this also checks for integer overflow when
|
||||
* multiplying \c sizeof(type) and \p count. This is necessary for security.
|
||||
*
|
||||
* \param ctx The context to use for new allocation. If \p ptr != NULL,
|
||||
* it must be the same as ralloc_parent(\p ptr).
|
||||
* \param ptr Pointer to the array to be resized. May be NULL.
|
||||
* \param size The size of an individual element.
|
||||
* \param old_count The number of elements in the previous allocation.
|
||||
* \param new_count The number of elements to allocate.
|
||||
*
|
||||
* \return True unless allocation failed.
|
||||
*/
|
||||
void *rerzalloc_array_size(const void *ctx, void *ptr, size_t size,
|
||||
unsigned old_count, unsigned new_count);
|
||||
/// @}
|
||||
|
||||
/**
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue