#ifndef INCLUDED_C_BUDDYALLOCATOR_H #define INCLUDED_C_BUDDYALLOCATOR_H #ifndef INCLUDED_C_BUDDY_H #include #endif /*INCLUDED_C_BUDDY_H*/ #ifndef INCLUDED_C_ALLOCATOR_H #include #endif /*INCLUDED_C_ALLOCATOR_H*/ /* ------------------------------------------------------------------------------------------------------------------ */ /* */ typedef struct { c_Buddy_t* buddy; }c_BuddyAllocator_t; C_STATIC_FORCE_INLINE void c_BuddyAllocator_Init(c_BuddyAllocator_t* allocator, c_Buddy_t* buddy) { allocator->buddy = buddy; } /* ------------------------------------------------------------------------------------------------------------------ */ /* */ C_STATIC_FORCE_INLINE C_ALLOCATOR_ALLOC_FN(c_BuddyAllocator_Alloc) { c_BuddyAllocator_t* self = (c_BuddyAllocator_t*)ud; if (!self || !self->buddy) return NULL; return c_Buddy_Alloc(self->buddy, (int)nBytes); } C_STATIC_FORCE_INLINE C_ALLOCATOR_FREE_FN(c_BuddyAllocator_Free) { c_BuddyAllocator_t* self = (c_BuddyAllocator_t*)ud; if (!self || !self->buddy) return; c_Buddy_Free(self->buddy, ptr); } C_STATIC_FORCE_INLINE C_ALLOCATOR_REALLOC_FN(c_BuddyAllocator_Realloc) { c_BuddyAllocator_t* self = (c_BuddyAllocator_t*)ud; if (!self || !self->buddy) return NULL; // 情况 1: 指针为空,直接分配新内存 if (!ptr) { return c_Buddy_Alloc(self->buddy, (int)nNewSize); } // 情况 2: 新大小为 0,直接释放内存 if (nNewSize==0) { c_Buddy_Free(self->buddy, ptr); return NULL; } // 核心优化:利用 Header 逆向获取该块在底层伙伴系统中的真实物理大小 const c_BuddyBlock_t *block = (c_BuddyBlock_t *) ((uint8_t *) ptr - self->buddy->alignment); const int actual_block_size = block->size; // 【就地复用判定】:如果新申请的大小没有超过当前伙伴块的物理承载上限,并且新大小不至于小到需要缩容割裂 // 直接返回原指针,零拷贝,零内存搬迁! if ((int)nNewSize <= actual_block_size && (int)nNewSize > (actual_block_size / 2)) { return ptr; } // 情况 3: 伙伴块大小不匹配(需要升级或降级阶数),申请新块 void* new_ptr = c_Buddy_Alloc(self->buddy, (int)nNewSize); if (!new_ptr) return NULL; // 计算安全的拷贝长度 const c_size_t copy_size = ((c_size_t)actual_block_size < nNewSize) ? (c_size_t)actual_block_size : nNewSize; // 数据迁移 memcpy(new_ptr, ptr, copy_size); // 释放旧伙伴块 c_Buddy_Free(self->buddy, ptr); return new_ptr; } /* ------------------------------------------------------------------------------------------------------------------ */ /* */ C_STATIC_FORCE_INLINE c_Allocator_t c_BuddyAllocator_Build(c_BuddyAllocator_t* self, c_Buddy_t* buddy) { c_BuddyAllocator_Init(self, buddy); c_Allocator_t allocator={0}; allocator.ud = self; allocator.alloc = c_BuddyAllocator_Alloc; allocator.free = c_BuddyAllocator_Free; allocator.realloc = c_BuddyAllocator_Realloc; return allocator; } #endif /*INCLUDED_C_BUDDYALLOCATOR_H*/