-
Notifications
You must be signed in to change notification settings - Fork 5.3k
Description
RT-Thread Version
master
Hardware Type/Architectures
all
Develop Toolchain
IAR
Describe the bug
Describe the bug
In rt_smem_free() (file: src/mem.c), the following assertion is used:
RT_ASSERT(MEM_POOL(&small_mem->heap_ptr[mem->next]) == small_mem);
This assertion fails incorrectly when freeing a block located near the heap end (heap_end).
At this point, the logic actually refers to the previous block (mem->prev), not mem->next.
Since the heap_end block is always marked as USED, MEM_POOL(...) does not equal small_mem, causing a false assertion failure.
How to reproduce
- Initialize rt_smem with a small heap.
- Allocate and free a block close to the heap_end.
- Observe assert failed inside rt_smem_free.
Expected behavior
Memory should be freed correctly without triggering a false assertion.
Root cause
- The assertion checks mem->next, which may point to the sentinel heap_end.
- heap_end is always USED, so MEM_POOL() fails.
- The check should instead validate mem->prev at this point.
Proposed fix
Change the assertion from mem->next to mem->prev.
This aligns the implementation with the original lwIP small memory allocator.
--- a/src/mem.c
+++ b/src/mem.c
@@ void rt_smem_free(void *rmem)
- RT_ASSERT(MEM_POOL(&small_mem->heap_ptr[mem->next]) == small_mem);
+ RT_ASSERT(MEM_POOL(&small_mem->heap_ptr[mem->prev]) == small_mem);
Environment
- RT-Thread version: [master branch]
- Module: components src/mem.c
- Target: [all]
Additional context
- Verified with test cases: issue reproduced on small heap allocation/free.
- After patch, allocator works without false assertion.
- Behavior now matches lwIP mem_free() / plug_holes().
Other additional context
No response