水滴
分类: LINUX
2021-12-27 09:45:19
环形队列,分配固定大小空间,循环记录信息,当超过固定大小限制,进行覆盖。
typedef struct {
char *buffer; //分配的缓存区
unsigned int in; //存入数据计数
unsigned int out; //取出数据计数
unsigned int size; //缓存区总大小
} cfifo_t;
void cfifo_init(cfifo_t *fifo, unsigned int size)
{
if(!is_power_of_2(size))
size = roundup_power_of_2(size);
fifo->buffer = (char*)(malloc(size * sizeof(char)));
fifo->in = 0;
fifo->out = 0;
fifo->size = size;
}
void cfifo_exit(cfifo_t *fifo)
{
if(fifo->buffer != NULL)
{
free(fifo->buffer);
fifo->buffer = NULL;
}
}
unsigned int cfifo_put(cfifo_t *fifo, char *data, unsigned int len)
{
unsigned int fl;
unsigned int l;
//get fifo free space
fl = fifo->size - fifo->in + fifo->out;
if(fl < len)
{
fifo->out += len - fl;
}
//len = min(len, fifo->size - fifo->in + fifo->out);
//get fifo->in to buffer end free space
l = min(len, fifo->size - (fifo->in & (fifo->size -1)));
//first put the data starting from fifo->in to buffer end
memcpy(fifo->buffer + (fifo->in & (fifo->size -1)), data, l);
//then put the rest (if any) at the beginning of the buffer
memcpy(fifo->buffer, data+l, len - l);
fifo->in += len;
//zlog_info(o, "fifo->in = %d", fifo->in);
return len;
}
unsigned int cfifo_get_datalength(cfifo_t *fifo)
{
unsigned int len = 0;
len = (fifo->in - fifo->out);
return len;
}
unsigned int cfifo_get(cfifo_t *fifo, char *data, unsigned int len)
{
unsigned int l;
unsigned int dl;
//get fifo data length
dl = fifo->in - fifo->out;
len = min(len, dl);
//get fifo->out to buffer end data length
l = min(len, fifo->size - (fifo->out & (fifo->size -1)));
//first get the data from fifo->out until the end of the buffer
memcpy(data, fifo->buffer + (fifo->out & (fifo->size -1)), l);
//then get the rest data (if any) from the beginning of the buufer
memcpy(data+l, fifo->buffer, len-l);
fifo->out += len;
//zlog_info(o, "fifo->out = %d", fifo->out);
return len;
}
void cfifo_rollback_data(cfifo_t *fifo, unsigned int size)
{
fifo->out -= size;
}