heap: add functions to get heap runtime statistics
add functions to get the sys_heap runtime statistics, include total free bytes, total allocated bytes. Signed-off-by: Chen Peng1 <peng1.chen@intel.com>
This commit is contained in:
parent
b330e3f374
commit
a71cd8790f
5 changed files with 75 additions and 0 deletions
|
@ -61,6 +61,25 @@ struct z_heap_stress_result {
|
|||
uint64_t accumulated_in_use_bytes;
|
||||
};
|
||||
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
|
||||
struct sys_heap_runtime_stats {
|
||||
size_t free_bytes;
|
||||
size_t allocated_bytes;
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief Get the runtime statistics of a sys_heap
|
||||
*
|
||||
* @param heap Pointer to specified sys_heap
|
||||
* @param stats_t Pointer to struct to copy statistics into
|
||||
* @return -EINVAL if null pointers, otherwise 0
|
||||
*/
|
||||
int sys_heap_runtime_stats_get(struct sys_heap *heap,
|
||||
struct sys_heap_runtime_stats *stats);
|
||||
|
||||
#endif
|
||||
|
||||
/** @brief Initialize sys_heap
|
||||
*
|
||||
* Initializes a sys_heap struct to manage the specified memory.
|
||||
|
|
|
@ -46,6 +46,11 @@ config SYS_HEAP_ALLOC_LOOPS
|
|||
keeps the maximum runtime at a tight bound so that the heap
|
||||
is useful in locked or ISR contexts.
|
||||
|
||||
config SYS_HEAP_RUNTIME_STATS
|
||||
bool "System heap runtime statistics"
|
||||
help
|
||||
Gather system heap runtime statistics.
|
||||
|
||||
choice
|
||||
prompt "Supported heap sizes"
|
||||
depends on !64BIT
|
||||
|
|
|
@ -386,3 +386,20 @@ void sys_heap_print_info(struct sys_heap *heap, bool dump_chunks)
|
|||
{
|
||||
heap_print_info(heap->heap, dump_chunks);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
|
||||
int sys_heap_runtime_stats_get(struct sys_heap *heap,
|
||||
struct sys_heap_runtime_stats *stats)
|
||||
{
|
||||
if ((heap == NULL) || (stats == NULL)) {
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
stats->free_bytes = heap->heap->free_bytes;
|
||||
stats->allocated_bytes = heap->heap->allocated_bytes;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
|
@ -38,6 +38,10 @@ static void free_list_remove_bidx(struct z_heap *h, chunkid_t c, int bidx)
|
|||
set_next_free_chunk(h, first, second);
|
||||
set_prev_free_chunk(h, second, first);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->free_bytes -= chunksz_to_bytes(h, chunk_size(h, c));
|
||||
#endif
|
||||
}
|
||||
|
||||
static void free_list_remove(struct z_heap *h, chunkid_t c)
|
||||
|
@ -72,6 +76,10 @@ static void free_list_add_bidx(struct z_heap *h, chunkid_t c, int bidx)
|
|||
set_next_free_chunk(h, first, c);
|
||||
set_prev_free_chunk(h, second, c);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->free_bytes += chunksz_to_bytes(h, chunk_size(h, c));
|
||||
#endif
|
||||
}
|
||||
|
||||
static void free_list_add(struct z_heap *h, chunkid_t c)
|
||||
|
@ -164,6 +172,9 @@ void sys_heap_free(struct sys_heap *heap, void *mem)
|
|||
mem);
|
||||
|
||||
set_chunk_used(h, c, false);
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->allocated_bytes -= chunksz_to_bytes(h, chunk_size(h, c));
|
||||
#endif
|
||||
free_chunk(h, c);
|
||||
}
|
||||
|
||||
|
@ -251,6 +262,9 @@ void *sys_heap_alloc(struct sys_heap *heap, size_t bytes)
|
|||
}
|
||||
|
||||
set_chunk_used(h, c, true);
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->allocated_bytes += chunksz_to_bytes(h, chunk_size(h, c));
|
||||
#endif
|
||||
return chunk_mem(h, c);
|
||||
}
|
||||
|
||||
|
@ -318,6 +332,9 @@ void *sys_heap_aligned_alloc(struct sys_heap *heap, size_t align, size_t bytes)
|
|||
}
|
||||
|
||||
set_chunk_used(h, c, true);
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->allocated_bytes += chunksz_to_bytes(h, chunk_size(h, c));
|
||||
#endif
|
||||
return mem;
|
||||
}
|
||||
|
||||
|
@ -353,6 +370,10 @@ void *sys_heap_aligned_realloc(struct sys_heap *heap, void *ptr,
|
|||
return ptr;
|
||||
} else if (chunk_size(h, c) > chunks_need) {
|
||||
/* Shrink in place, split off and free unused suffix */
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->allocated_bytes -=
|
||||
(chunk_size(h, c) - chunks_need) * CHUNK_UNIT;
|
||||
#endif
|
||||
split_chunks(h, c, c + chunks_need);
|
||||
set_chunk_used(h, c, true);
|
||||
free_chunk(h, c + chunks_need);
|
||||
|
@ -362,6 +383,10 @@ void *sys_heap_aligned_realloc(struct sys_heap *heap, void *ptr,
|
|||
/* Expand: split the right chunk and append */
|
||||
chunkid_t split_size = chunks_need - chunk_size(h, c);
|
||||
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->allocated_bytes += split_size * CHUNK_UNIT;
|
||||
#endif
|
||||
|
||||
free_list_remove(h, rc);
|
||||
|
||||
if (split_size < chunk_size(h, rc)) {
|
||||
|
@ -415,6 +440,11 @@ void sys_heap_init(struct sys_heap *heap, void *mem, size_t bytes)
|
|||
h->end_chunk = heap_sz;
|
||||
h->avail_buckets = 0;
|
||||
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
h->free_bytes = 0;
|
||||
h->allocated_bytes = 0;
|
||||
#endif
|
||||
|
||||
int nb_buckets = bucket_idx(h, heap_sz) + 1;
|
||||
chunksz_t chunk0_size = chunksz(sizeof(struct z_heap) +
|
||||
nb_buckets * sizeof(struct z_heap_bucket));
|
||||
|
|
|
@ -69,6 +69,10 @@ struct z_heap {
|
|||
chunkid_t chunk0_hdr[2];
|
||||
chunkid_t end_chunk;
|
||||
uint32_t avail_buckets;
|
||||
#ifdef CONFIG_SYS_HEAP_RUNTIME_STATS
|
||||
size_t free_bytes;
|
||||
size_t allocated_bytes;
|
||||
#endif
|
||||
struct z_heap_bucket buckets[0];
|
||||
};
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue