nginx使用内存池对内存进行管理,内存分配可以归结为大内存分配和小内存分配。若申请的内存大小比同页的内存池最大值max还大,则是大内存分配,否则为小内存分配。
- 大内存的分配请求不会直接在内存池上分配,而是直接向系统申请一块内存(就像直接使用malloc分配内存一样),然后将这块内存挂到内存池头部的large字段下
- 小内存分配,则是从已有的内存池数据区中分配出一部分内存。
// 内存池结构体 core/nginx_palloc.h// 内存池数据模块typedef struct {u_char *last; // 当前内存分配的结束位置,即下一段可分配内存的起始位置u_char *end; // 内存吃的结束位置ngx_pool_t *next; // 指向下一个内存池ngx_uint_t failed; // 记录内存池内存分配失败的次数} ngx_pool_data_t; // 维护内存池的数据块// 内存池管理模块,内存池头部结构struct ngx_pool_s {ngx_pool_data_t d; // 内存池数据模块size_t max; // 内存池数据块的最大值ngx_pool_t *current; // 指向当前内存池ngx_chain_t *chain; // 指向一个ngx_chain_t结构ngx_pool_large_t *large; // 大块内存链表,即分配空间超过max的内存ngx_pool_cleanup_t *cleanup; // 析构函数,释放内存池ngx_log_t *log; // 内存池日志};
大块内存分配如下:
typedef struct ngx_pool_large_s ngx_pool_large_t;struct ngx_pool_large_s {ngx_pool_large_t *next; // 指向下块要分配的内存void *alloc; // 指向分配的大块内存};
