void mem_pool_free(struct mem_pool * pool, int index) { struct node * n; index += LEFT_LEAF(pool->order); for(;;) { n = &pool->nl[index]; if (n->status == FULL) break; index = PARENT(index); } n->status = FREE; mark_parent(pool, index); }
unsigned block_size(struct mem_pool * pool, int index) { struct node * n; index += LEFT_LEAF(pool->order); for(;;) { n = &pool->nl[index]; if (n->status == FULL) break; index = PARENT(index); } int h = HEIGHT(index); return POOL_SZ(pool->order - h); }
static char* __buddy_malloc(struct buddy_pool* self,int size) { char* ret_ptr = NULL; if(size <= 0) { return NULL; } unsigned char order = next_order_of_2(size); if (order < self->min_order) { order = self->min_order; } int index = 0; if(self->bh[0] < order) /*have no enough space*/ { return NULL; } int current_order = self->order; for(current_order = self->order ; current_order != order; current_order--) { if(self->bh[LEFT_LEAF(index)] >= order) index = LEFT_LEAF(index); else index = RIGHT_LEAF(index); } self->bh[index] = 0; ret_ptr = self->buffer + (index+1)*(1<<order)-(self->pool_size); while(index) { index = PARENT(index); self->bh[index] = MAX(self->bh[LEFT_LEAF(index)],self->bh[RIGHT_LEAF(index)]) ; } return ret_ptr; }
static void __buddy_free(struct buddy_pool* self,char* pointer ) { assert(self != NULL && self->bh != NULL &&self->buffer != NULL && pointer != NULL) ; int offset = pointer - self->buffer; assert(offset >= 0 && offset < self->pool_size); int current_order = self->min_order; int current_index = 0; int found = 0; unsigned char left_order,right_order ; while(offset % (1<<current_order) == 0) { current_index =(1<<(self->order-current_order))-1 + offset/(1<<current_order); if(self->bh[current_index] == 0) { found = 1; break; } current_order++; } assert(found == 1); self->bh[current_index] = current_order; while(current_index) { current_index = PARENT(current_index) ; current_order++; left_order = self->bh[LEFT_LEAF(current_index)]; right_order = self->bh[RIGHT_LEAF(current_index)]; if(left_order == (current_order -1 ) && right_order == (current_order - 1)) { self->bh[current_index] = current_order; } else { self->bh[current_index] = MAX(left_order,right_order); } } }
int mem_pool_alloc(struct mem_pool * pool, size_t size) { size_t sz = size >= ND_MIN_SZ ? size : ND_MIN_SZ; sz = IS_POW2(sz) ? sz : NEXT_POW2(sz); printf("aligning requested size %d to %d...\n", size, sz); unsigned order = pool->order + 4 - LOG2(sz); printf("requested order is %d\n", order); unsigned i = 0, rval = 0; if (!potential(pool, i, order)) { return -1; } for (;;) { printf("checking node %d ...\n", i); struct node * n = &pool->nl[i]; if (n->status == FREE && HEIGHT(i) == order) { n->status = FULL; mark_parent(pool, i); while (i < pool->valid_nr) { rval = i; i = LEFT(i); } return rval - LEFT_LEAF(pool->order); //good } else if (potential(pool, LEFT(i), order)) { i = LEFT(i); } else if (potential(pool, RIGHT(i), order)) { i = RIGHT(i); } else { break; } } return -1; }