【linux kernel】start_kernel函数详解系列之proc_caches_init

一、开篇

​ 在start_kernel函数中将调用proc_caches_init()用于为linux内核中内核对象初始化slab缓存描述符。该函数定义如下(/kernel/fork.c):

void __init proc_caches_init(void)
{
	sighand_cachep = kmem_cache_create("sighand_cache",
			sizeof(struct sighand_struct), 0,
			SLAB_HWCACHE_ALIGN|SLAB_PANIC|SLAB_DESTROY_BY_RCU|
			SLAB_NOTRACK, sighand_ctor);
	signal_cachep = kmem_cache_create("signal_cache",
			sizeof(struct signal_struct), 0,
			SLAB_HWCACHE_ALIGN|SLAB_PANIC|SLAB_NOTRACK, NULL);
	files_cachep = kmem_cache_create("files_cache",
			sizeof(struct files_struct), 0,
			SLAB_HWCACHE_ALIGN|SLAB_PANIC|SLAB_NOTRACK, NULL);
	fs_cachep = kmem_cache_create("fs_cache",
			sizeof(struct fs_struct), 0,
			SLAB_HWCACHE_ALIGN|SLAB_PANIC|SLAB_NOTRACK, NULL);

	mm_cachep = kmem_cache_create("mm_struct",
			sizeof(struct mm_struct), ARCH_MIN_MMSTRUCT_ALIGN,
			SLAB_HWCACHE_ALIGN|SLAB_PANIC|SLAB_NOTRACK, NULL);
	vm_area_cachep = KMEM_CACHE(vm_area_struct, SLAB_PANIC);
	mmap_init();
	nsproxy_cache_init();
}

在proc_caches_init的开头,会通过调用kmem_cache_create()函数去分配不同的SLAB缓存:

  • sighand_cachep — 管理有关已安装信号处理程序的信息。

  • signal_cachep — 管理有关进程信号描述符的信息。

  • files_cachep — 管理打开的文件信息。

  • fs_cachep —管理文件系统信息。

对于以上四种slab缓存区域,linux内核中对其分配、创建 、释放过程分别如下所示:

(1)sighand_cachep缓存

在这里插入图片描述

(2)signal_cachep缓存

在这里插入图片描述

(3)files_cachep缓存

在这里插入图片描述

(4)fs_cachep缓存

在这里插入图片描述


在此之后,还将为mm_struct结构分配SLAB缓存,如下代码片段:

mm_cachep = kmem_cache_create("mm_struct",
                         sizeof(struct mm_struct), ARCH_MIN_MMSTRUCT_ALIGN,
                         SLAB_HWCACHE_ALIGN|SLAB_PANIC|SLAB_NOTRACK, NULL);

linux内核中对mm_cachep缓存空间的分配、创建 、释放过程如下所示:

在这里插入图片描述

接着,将为重要的vm_area_struct结构分配SLAB缓存,linux内核使用它来管理虚拟内存空间:

vm_area_cachep = KMEM_CACHE(vm_area_struct, SLAB_PANIC);

linux内核中对vm_area_cachep缓存空间的分配、创建 、释放过程如下所示:

在这里插入图片描述

注意,这里使用的是KMEM_CACHE宏,而不是kmem_cache_create。这个宏在include/linux/slab.h中进行定义,只是展开本质为kmem_cache_create的调用,如下代码片段:

#define KMEM_CACHE(__struct, __flags) kmem_cache_create(#__struct,\
                sizeof(struct __struct), __alignof__(struct __struct),\
                (__flags), NULL)

KMEM_CACHEkmem_cache_create()有一个区别。体现在__alignof__操作符上,KMEM_CACHE宏将SLAB对齐到给定结构的大小,但是kmem_cache_create会使用给定的值来对齐空间。

接下来,proc_caches_init()将调用mmap_init和nsproxy_cache_init这两个函数。第一个函数用于初始化虚拟内存区域的Slab,第二个函数用于初始化名称空间的slab。

二、结尾

对于proc_caches_init()来说,其函数内核的实现是创建slab缓存描述符,包括:sighand_cachep、signal_cachep、files_cachep、fs_cachep、mm_cachep、vm_area_cachep等。

本文中一直出现slab这个关键词,slab是linux内核中的小内存分配器,对于linux内核来说,因为很多linux内核的对象不会使用内存页面分配的方式进行。故而会使用slab分配器来分配,在slab中分配小内存,首先要做的就是创建slab描述符,proc_caches_init()函数的用意就在于此!

关于linux内核的slab分配器,其内容很多,笔者计划在后续linux内核的内存管理文章中进行分享啦,文本已完!


搜索关注【嵌入式小生】wx公众号获取更多精彩内容。
请添加图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

iriczhao

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值