涉及文件
event.h struct evbuffer定义,函数声明
buffer.c 函数实现
从后面添加数据到缓冲区,从前面读取缓冲区中的内容
写 : 从字符串,文件描述符文件写入到缓冲区
读 : 从缓冲区中读指定字符,一行到字符串;也可以读出来写到一个文件描述符文件
/********************************************************************/
struct evbuffer{
u_char *buffer; // 当前有效缓冲区的内存起始地址
u_char *orig_buffer; // 整个分配(realloc)用来缓冲的内存起始地址
size_t misalign; // origin_buffer和buffer之间的字节数
size_t totallen; // 整个分配用来缓冲的内存字节数
size_t off; // 当前有效缓冲区的长度(字节数)
void (*cb)(struct evbuffer *, size_t, size_t, void *);
void *cbarg;
};
origin_buffer buffer
| |
| |
——————————————————————————————————————————
| | | |
——————————————————————————————————————————
|<- misalign ->|<- off ->|
|<- totallen ->|
struct中最后两个参数和回调函数有关
void (*cb)(struct evbuffer *, size_t, size_t, void *);
回调函数, 每次读写导致缓冲区长度有变化时都会调用这个函数
参数
1: struct evbuffer指针
2: 原来缓冲区的长度
3: 变化后缓冲区的长度
4: cbarg
void *cbarg;
回调函数的第四个参数
回调函数和第四个参数通过evbuffer_setcb函数设置
如果通过evbuffer_setcb函数设置(默认为NULL指针)了回调函数
那么每次对缓冲区读写,都会调用这个回调函数
/********************************************************************/
写数据到缓冲区的函数有
evbuffer_read 从文件描述符文件中读数据到缓冲区
evbuffer_add 把一个字符串的内存添加到缓冲区的尾部
从缓冲区读数据的函数有
evbuffer_remove 从缓冲区中读最多指定个字节
evbuffer_readline 从缓冲区中读一行
evbuffer_write 把缓冲区中的数据写到文件描述符文件
以上所有函数,如果导致缓冲区长度有变化,都会调用回调函数cb
/********************************************************************/
两个内部使用的基本函数是
evbuffer_drain : 把已经读的从有效缓冲区中去掉,右移buffer指针,增大misalign,减小off,调用回调函数
evbuffer_expand : 重新分配缓冲区,这样能容纳准备写入到缓冲区中数据
/********************************************************************/
evbuffer_new
struct evbuffer *evbuffer_new(void)
在堆上分配一个struct evbuffer大小的内存
evbuffer_free
evbuffer_free(struct evbuffer *buffer)
释放struct evbuffer结构以及分配的缓冲区内存
evbuffer_remove
int evbuffer_remove(struct evbuffer *buf, void *data, size_t datlen)
从缓冲区读数据(最多datlen个字节),然后把已经读的从有效缓冲区中去掉(调用evbuffer_drain)
evbuffer_readline
char *evbuffer_readline(struct evbuffer *buffer)
从缓冲区读一行数据,放到新分配的堆上,需要调用者来free这些分配的内存
然后把已经读的从有效缓冲区中去掉(调用evbuffer_drain)
evbuffer_drain
void evbuffer_drain(struct evbuffer *buf, size_t len)
把buffer指针后移len个字节 -- 表示这些字节已经无效了(比如被读出了)
删除(就是移动指针,和相应修改misalign off字段的值)datlen个字符,如果都读出来了就会设置buffer = origin_buffer
evbuffer_align
static void evbuffer_align(struct evbuffer *buf)
把buffer前移到origin_buffer,这个函数在内部(evbuffer_expand)使用,别的不直接使用
evbuffer_expand
int evbuffer_expand(struct evbuffer *buf, size_t datlen)
增长整个缓冲区(realloc),使缓冲区至少还有datlen字节空闲
重新分配的缓冲区长度都是256的2的偶数次幂倍
if (length < 256)
length = 256;
while (length < need)
length <<= 1;
evbuffer_add
int evbuffer_add(struct evbuffer *buf, const void *data, size_t datlen)
从字符串添加到缓冲区后面,(长度不够时,会调用evbuffer_expand)
evbuffer_read
int evbuffer_read(struct evbuffer *buf, int fd, int howmuch)
从文件描述符文件中读数据到缓冲区,(长度不够时,会调用evbuffer_expand)
evbuffer_write
int evbuffer_write(struct evbuffer *buffer, int fd)
把缓冲区的内容写到一个文件描述符文件,然后把已经读的从有效缓冲区中去掉(调用evbuffer_drain)
evbuffer_find
u_char *evbuffer_find(struct evbuffer *buffer, const u_char *what, size_t len)
在缓冲区中查找有没有指定字符串
有则返回其指针,没有则返回NULL
evbuffer_setcb
void evbuffer_setcb(struct evbuffer *buffer,
void (*cb)(struct evbuffer *, size_t, size_t, void *),
void *cbarg)
阅读(2090) | 评论(0) | 转发(0) |