分类: C/C++
2012-03-06 22:53:21
这次来看看buffer的实现。
buffer有两种,一种用文件,一种用内存。
buffer的结构如下:
struct ngx_buf_s {
u_char *pos; //指向未处理的内容
u_char *last; //大家都懂吧
off_t file_pos; //用文件形式的时候
off_t file_last;u_char *start; /* start of buffer */
u_char *end; /* end of buffer *///这些是表明buffer所属模块
ngx_buf_tag_t tag;
ngx_file_t *file;
ngx_buf_t *shadow;/* the buf's content could be changed */
unsigned temporary:1;/*
* the buf's content is in a memory cache or in a read only memory
* and must not be changed
*/
unsigned memory:1;/* the buf's content is mmap()ed and must not be changed */
//一些标记表明是否文件或者内存
unsigned mmap:1;unsigned recycled:1;
unsigned in_file:1;
unsigned flush:1;
unsigned sync:1;
unsigned last_buf:1;
unsigned last_in_chain:1;unsigned last_shadow:1;
unsigned temp_file:1;/* STUB */ int num;
};
//用下面的结构体连成链表
struct ngx_chain_s {
ngx_buf_t *buf;
ngx_chain_t *next;
};
来看创建buf的函数:
ngx_buf_t *
ngx_create_temp_buf(ngx_pool_t *pool, size_t size)
{
ngx_buf_t *b;b = ngx_calloc_buf(pool); (1)
if (b == NULL) {
return NULL;
}b->start = ngx_palloc(pool, size); (2)
if (b->start == NULL) {
return NULL;
}/*
* set by ngx_calloc_buf():
*
* b->file_pos = 0;
* b->file_last = 0;
* b->file = NULL;
* b->shadow = NULL;
* b->tag = 0;
* and flags
*/(3)
b->pos = b->start;
b->last = b->start;
b->end = b->last + size;
b->temporary = 1;return b;
}
(1) #define ngx_calloc_buf(pool) ngx_pcalloc(pool, sizeof(ngx_buf_t)) 从这这宏可以看出,这里是创建一个buf结构体,并分配内存及清零。
(2) 这里是分配真正存储buffer数据的地方。
(3) 进行一系列初始化。
接下来看看chain的创建,chain其实也就是多个buf组合而成的。它主要是用来缓存一些未发出去的,或者接收的buf 以及 writev以及readv而存在的。
struct ngx_chain_s {
ngx_buf_t *buf;
ngx_chain_t *next;
}; //显然是一链表
ngx_chain_t *
ngx_create_chain_of_bufs(ngx_pool_t *pool, ngx_bufs_t *bufs)
{
u_char *p;
ngx_int_t i;
ngx_buf_t *b;
ngx_chain_t *chain, *cl, **ll;p = ngx_palloc(pool, bufs->num * bufs->size); //(1)
if (p == NULL) {
return NULL;
}ll = &chain;
for (i = 0; i < bufs->num; i++) { //(2)
b = ngx_calloc_buf(pool);
if (b == NULL) {
return NULL;
}/*
* set by ngx_calloc_buf():
*
* b->file_pos = 0;
* b->file_last = 0;
* b->file = NULL;
* b->shadow = NULL;
* b->tag = 0;
* and flags
*
*/b->pos = p; //(3)
b->last = p;
b->temporary = 1;b->start = p;
p += bufs->size;
b->end = p;cl = ngx_alloc_chain_link(pool); //(4)
if (cl == NULL) {
return NULL;
}cl->buf = b;
*ll = cl;
ll = &cl->next;
}*ll = NULL;
return chain;
}
(1)分配内存池大小。
(2)为一个buf创建buf结构体。
(3)设置成员的值和标记。
(4)拿到内存池的buf链表(ngx_alloc_chain_link),把新建的buf查到链表中。
重复(2)到(4)直到所有buf插入完成。
先写到这里,洗完澡接着写。