Linux SLUB分配器之三(释放对象的代码分析)
来源:互联网 发布:js取小数点前面的数字 编辑:程序博客网 时间:2024/05/22 13:55
void kfree(constvoid *x)
{
structpage *page;
if(unlikely(ZERO_OR_NULL_PTR(x)))
return;
page = virt_to_head_page(x);/*注意,对于SLAB而言,假设这个SLAB有多个Page,则除首Page之外的其它的所有Page都通过其first_page成员指向首Page(见Page数据结构) ,故而这里就得到该SLAB的首Page了*/
if(unlikely(!PageSlab(page))) {
put_page(page);
return;
}
slab_free(page->slab, page, (void *)x,__builtin_return_address(0));
}
static void__always_inline slab_free(struct kmem_cache *s,
struct page *page, void *x,void *addr)
{
void**object = (void *)x;
unsignedlong flags;
structkmem_cache_cpu *c;
local_irq_save(flags);
debug_check_no_locks_freed(object,s->objsize);
c =get_cpu_slab(s, smp_processor_id());
if (likely(page == c->page &&c->node >= 0)) {/*如果释放的对象在当前的SLAB上,就直接放到kmem_cache->cpu_slab->freelist里*/
object[c->offset]= c->freelist;
c->freelist= object;
} else
__slab_free(s,page, x, addr, c->offset);
local_irq_restore(flags);
}
static void__slab_free(struct kmem_cache *s, struct page *page,
void *x, void *addr,unsigned int offset)
{
void*prior;
void**object = (void *)x;
slab_lock(page);
if(unlikely(SlabDebug(page)))
gotodebug;
checks_ok:
prior = object[offset] =page->freelist;/*这里请注意,page为该object所在的SLAB的首Page,同时,此SLAB不是当前的SLAB,故而释放的对象不能放到kmem_cache->cpu_slab->freelist里,而需要放到该首Page的freelist结构里,见3.2节的分析;同时,另一点很重要,如果这里prior为NULL,则说明此前此SLAB上的对象已经被分配光了,即此SLAB杯deactivate了,故而后面要把该SLAB加入到Partial链表里*/
page->freelist= object;
page->inuse--;/*因为是放到了Page的freelist里,故而在使用的对象计数要减1*/
if(unlikely(SlabFrozen(page)))
gotoout_unlock;
if (unlikely(!page->inuse))/*该SLAB上的对象已经都被释放了,即都是空闲对象了,且该SLAB不是当前SLAB,这样,这个SLAB所占用的空间就可以释放给系统了*/
goto slab_empty;
/*
* Objects left in the slab. If it
* was not on the partial list before
* then add it.
*/
if (unlikely(!prior))
add_partial_tail(get_node(s,page_to_nid(page)), page);/* 此前此SLAB上的对象已经被分配光了,即此SLAB杯deactivate了,故而后面要把该SLAB加入到Partial链表里 */
out_unlock:
slab_unlock(page);
return;
slab_empty:
if(prior)
/*
* Slab still on the partial list.
*/
remove_partial(s, page);
slab_unlock(page);
discard_slab(s, page);/* 释放给系统*/
return;
debug:
if(!free_debug_processing(s, page, x, addr))
gotoout_unlock;
gotochecks_ok;
}
- Linux SLUB分配器之三(释放对象的代码分析)
- Linux SLUB分配器之二(申请对象的代码分析)
- Linux Slub分配器(五)--释放对象
- Linux Slub分配器(五)--释放对象 .
- Linux Slub分配器(五)--释放对象
- Linux SLUB分配器之四(kmem_cache初始化代码分析)
- Linux Slub分配器(六)--slab的分配与释放
- Linux Slub分配器(六)--slab的分配与释放
- Linux Slub分配器(六)--slab的分配与释放
- linux的最新slab分配器---slub分配器
- Linux Slob分配器(三)--释放对象
- Linux Slob分配器(三)--释放对象
- Linux Slub分配器(三)--创建缓存
- Linux Slub分配器(三)--创建缓存
- Linux Slub分配器(三)--创建缓存
- Linux Slub分配器(四)--分配对象
- Linux Slub分配器(四)--分配对象
- Linux Slub分配器(四)--分配对象
- Getting FTP to Work with Ant in Eclipse[转]
- VirtualHost声明的注意事项
- 挨踢世界的形形色色
- Linux SLUB分配器之二(申请对象的代码分析)
- Microsoft SQL Server Management Studio Express
- Linux SLUB分配器之三(释放对象的代码分析)
- 编译链接之一 目标文件
- Linux SLUB分配器之四(kmem_cache初始化代码分析)
- 微软日语输入法使用方法
- powershell 问题之二调用Excel的Com组件报错
- ORA-02437 错误,检查重复列 -违反主关键字
- 令人迷茫的计算机
- 用c编写求信息论中各种熵和信息量的程序
- 关于v$db_object_cache的一些脚本