【环形缓冲区】1-概念与编程

这一点很重要,后续还会做补充

一、环形缓冲区的引入

//下面是一个按键控制LCD的程序
main()
{
    while(1)
    {
        key = read_key();	 // 读取按键值
        LCD(key);			// 耗时 30min
    }
}
  • 想要在这 30min 中,不丢失按键,就需要引入中断;
// 中断回调函数
key_ISR()
{
    g_key = 记录key值;		// 为防新值覆盖旧值,需要用buf  ==> 环形buf
}
  • 因此引入环形缓冲区,一方写buffer、另一方读buffer
环形缓冲区示例
在这里插入图片描述

二、环形缓冲区 编程

//circle_buffer.h
#ifndef _CIRCLE_BUF_H
#define _CIRCLE_BUF_H

#include <stdint.h>

typedef struct circle_buf {
	uint32_t r;
	uint32_t w;
	uint32_t len;
	uint8_t *buf;
}circle_buf, *p_circle_buf;

void circle_buf_init(p_circle_buf pCircleBuf, uint32_t len, uint8_t *buf);

int circle_buf_read(p_circle_buf pCircleBuf, uint8_t *pVal);

int circle_buf_write(p_circle_buf pCircleBuf, uint8_t val);

#endif /* _CIRCLE_BUF_H */

//circle_buffer.c
#include <stdint.h>
#include "circle_buffer.h"

void circle_buf_init(p_circle_buf pCircleBuf, uint32_t len, uint8_t *buf)
{
	pCircleBuf->r = pCircleBuf->w = 0;
	pCircleBuf->len = len;
	pCircleBuf->buf = buf;
}

int circle_buf_read(p_circle_buf pCircleBuf, uint8_t *pVal)
{
	if (pCircleBuf->r != pCircleBuf->w)
	{
		*pVal = pCircleBuf->buf[pCircleBuf->r];
		
		pCircleBuf->r++;
		
		if (pCircleBuf->r == pCircleBuf->len)
			pCircleBuf->r = 0;
		return 0;
	}
	else
	{
		return -1;
	}
}

int circle_buf_write(p_circle_buf pCircleBuf, uint8_t val)
{
	uint32_t next_w;
	
	next_w = pCircleBuf->w + 1;
	if (next_w == pCircleBuf->len)
		next_w = 0;
	
	if (next_w != pCircleBuf->r)
	{
		pCircleBuf->buf[pCircleBuf->w] = val;
		pCircleBuf->w = next_w;
		return 0;
	}
	else
	{
		return -1;
	}
}

Logo

智能硬件社区聚焦AI智能硬件技术生态,汇聚嵌入式AI、物联网硬件开发者,打造交流分享平台,同步全国赛事资讯、开展 OPC 核心人才招募,助力技术落地与开发者成长。

更多推荐