slub 分配器初始化

文章详细介绍了Linux内核内存管理的初始化过程,从memblock、SPARSEMEM到zone的初始化,然后过渡到buddy系统和LRU。在slab系统初始化阶段,由于需要在slab系统尚未建立时创建structkmem_cache,内核使用预创建的静态结构boot_kmem_cache来解决这一先有鸡还是先有蛋的问题。文章主要关注UMA架构下slub分配器的初始化流程。
摘要由CSDN通过智能技术生成

源码基于:Linux5.4

0. 前言

zone初始化一文中简单剖析了 zone 的初始化流程,也是继 memblock初始化 SPARSEMEM初始化 之后有一个内存管理层,而zone 这一层管理层中,所有的物理内存都会被添加到zone 中的成员变量 free_area 数组管理,而它就是buddy 系统管理的核心数据结构。

memblock初始化SPARSEMEM初始化zone 初始化 进行了内存管理的初始化流程,而经过bootmem管理paging_init 的内核内存映射、sparse 模型创建zone 数据结构buddy 数据结构初始化完成后,需要通过 mm_init() 对内存进行最后的初始化工作,将内存管理从 bootmem移交到 buddy 系统和 LRU。

由于 slab 系统初始化前,Linux 内核已经完成了伙伴系统的初始化工作,内核可以很方便地通过伙伴系统提供内存。但是slab系统初始化时需要定义一些基本的数据结构来维护和管理slab系统 (如slab cache描述符 struct kmem_cache)。像 stcuct kmem_cache这些数据结构需要小块内存进行存储,且这些小块内存往往只有几十或者几百字节远远小于一个页的大小。若通过伙伴系统分配内存来存储着这些数据结构,则违背了slab系统设计的初衷(内存资源浪费,内存分配效率低下)。所以我们只能通过slab系统给struct kmem_cache结构体分配slab缓存,然后从刚分配的slab缓存中去获取对应的slab obj(小块内存)来存储struct kmem_cache结构中的数据。看到这里已经懵逼了,在slab系统中slab缓存的描述符就是strcut kmem_cache。此时 slab 系统还未开始初始化,也就是 struct kmem_cache还没有呢,又怎么能从slab系统中分配到小块内存呢?这活生生的一个是鸡生蛋,蛋生鸡的问题啊(slab系统只能在slab系统初始化完成后初始化),貌似无解???

机智的 Linux内核使用了一个特殊的技巧来解决上面slab系统初始化时遇到的问题。

linux内核镜像编译时创建的静态数据会在内核内存初始化时就会被加载到内存中去,后续内核使用该静态数据时并不需要分配内存来存储它。Linux 利用这一特性,使用了编译时创建的静态结构boot_kmem_cache 数据来作为系统中的第一个 slab 缓存,用它来为创建 struct kmem_cache时分配小块内存。

mm_init() 中的 mem_init() 会free memblock ,并对 buddy 系统的 free areas 进行最后的初始化,至此buddy 系统创建完成。在 mem_init() 完成之后会调用 kmem_cache_init(),完成 kmem_cache_nodekmem_cachekmalloc_caches 三个 slab cache 管理结构的初始化。

当然,需要注意的是mm_init() 之后slab 分配器,还会调用 kmem_cache_init_late() 进一步初始化,slob 只是标记 slab_state 为FULL,slub 中空实现。

总的初始化流程大致为:

start_kernel()
    ---->mm_init()
        ---->mem_init()
        ---->kmem_cache_init()
    ---->kmem_cache_init_late()

本文将中重点分析 UMA 架构下的 slub 分配器的初始化流程。

转自:https://justinwei.blog.csdn.net/article/details/127785111

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值