内核中有些地方的内存分配是不允许失败的。为了确保成功分配内存,建立了内存池。内存池是某种形式的高速后备缓存。试图始终保存空闲的内存,以便在紧急状态下使用。
类型:mempool_t,头文件:
mempool_t *mempool_create(int min_nr, mempool_alloc_t *alloc_fn, mempol_free_t *free_fn, void *pool_data);
min_nr:内存池始终保持的已分配对象的最少数目
alloc_fn:原型 typedef void *(mempool_alloc_t )(gfp_t gfp_mask, void *pool_data),通常值为mempool_alloc_slab(内核定义的函数)
free_fn:原型 typedef void (mempol_free_t )(void *element, void *pool_data),通常值为mempool_free_slab(内核定义的函数)
pool_data:被传入alloc_fn和free_fn
void *mempool_alloc(mempool_t *pool, int gfp_mask);
首先通过分配函数获得内存对象,如果失败,就会返回预先分配的内存对象
void mempool_free(void *element, mempool_t *pool);
如果预先分配的对象数目小于要求的最低数目,就会将该内存对象保留在内存池中,否则返回给系统
void mempool_destroy(mempool_t *pool);
在释放内存池时,必须将所有分配的内存对象返回到内存池中
- #include
- #include
- #include
- #include
- #include
-
- #define MEM_SIZE 8
- #define MIN_NR 8
-
- static mempool_t *pstPool = NULL;
- static struct kmem_cache *pKmemCache = NULL;
-
- void constructor(void *args)
- {
- //printk("constructor. \n");
- memset(args, 0x0, MEM_SIZE);
- strcpy(args, "hello");
- }
-
- static int __init hello_init(void)
- {
- printk("hello_init. \n");
-
- pKmemCache = kmem_cache_create("test", MEM_SIZE, 0, SLAB_HWCACHE_ALIGN, constructor);
- if (!pKmemCache)
- {
- printk("kmem_cache_create failed. \n");
- return -ENOMEM;
- }
-
- pstPool = mempool_create(MIN_NR, mempool_alloc_slab, mempool_free_slab, pKmemCache);
- if (!pstPool)
- {
- printk("mempool_create failed. \n");
- return -ENOMEM;
- }
-
- void *p = mempool_alloc(pstPool, GFP_KERNEL);
- if (!p)
- {
- printk("mempool_alloc failed. \n");
- return -ENOMEM;
- }
- printk("str:%s\n", p);
-
- mempool_free(p, pstPool);
- return 0;
- }
-
- static void __exit hello_exit(void)
- {
- printk("hello_exit. \n");
-
- if (NULL != pstPool)
- {
- mempool_destroy(pstPool);
- pstPool = NULL;
- }
- }
-
- MODULE_LICENSE("GPL");
- module_init(hello_init);
- module_exit(hello_exit);
内存池会分配一些内存块,空闲且不会得到真正的使用,容易浪费大量内存。尽量少用内存池。