内存池设计

2012-06-29

1.内存池是用来干什么的

  • 可以避免频繁的小块内存分配导致内存碎片
  • 在用户层和操作系统层之间的一层,使得内存分配更稳定
  • 分配速度更快

2.总体设计

../img/mempool.jpg 二个层次,chunk管理层和slot分配器层,分别作为与操作系统接口和用户分配接口

chunk管理?

chunk数据结构设计。每个chunk大小为1KB。通过链表链接起来。

有个全局head指针指向第一个chunk,以便到最后释放内存

chunk块的插入使用头插法

每个chunk中还需要保存的信息必须有:

当前chunk中的可用空间首地址/指向下一chunk指针

slot管理?

slot数据结构设计

第一级slot大小是上一级slot大小的两倍。从4字节开始,一共8级

4B,8B,16B,32B,64B,128B,256B,512B

有个slot的表,它是一个指针数组,指向各级slot的头指针

3.用户接口:

pool_init //首次使用内存池时初始化
void *pool_alloc(int size) //分配函数
pool_free(void *ptr) //释放函数
pool_finalizer //不再使用内存池后释放

4.详细设计

考虑分配出去的内存,需要保存哪些信息才能被回收?

要记录它们在哪一个slot!

设计分配出去的数据结构

struct slot {
    int tag;
    char ptr[];
}
struct slot* slots[8];

考虑如何才能把slot管理起来?

指针!

设计slot数据结构

如果用户申请一块内存: <4B,从第一级slot分配
4B~8B,从第二级slot分配
8B~16B,从第三级slot分配…
512B~1K,直接分配一个chunk
大于1K,直接调用操作系统的malloc

5.一些编程技巧

给结构体里的某个域的指针,如何得到结构体指针?

共用的数据结构

有些时候不要使用结构体,避免结构体对齐带来的空间开销


本来是给一位小朋友练手的,这是写给她的文档

要求:

  1. 实实在在的编码完成
  2. 这样做的目的是练习动手能力,包括debug能力
  3. 上传到网上的代码托管.github或googlecode
  4. 第一个作用是起一个监督作用,放到网上别人都能看到的地方就迫使自己更严格要求自己
  5. 第二个作用是借此了解版本控制软件的使用,以及开源项目的运作原理
  6. 第三个作用是以后写简历,写进去可以出彩的
  7. 写博客记录自己的学习过程(可选但建议)
  8. 维护一个技术博客的过程,就是用几年时间做一份完整简历的过程.

结果自己先花了一个小时写了一下代码,很粗糙,反正也不是拿着用的,无所谓了 https://github.com/tiancaiamao/mempool

mempool