环形队列+DMA空闲中断+接收串口数据
环形队列+DMA空闲中断+接收串口数据
- 一.序言
- 二.实验原理
- 三.实战是检验真理的唯一标准
- 3.1 usart1.c
- 3.2 串口中断
- 三.队列代码
- 4.1 fifo.c
- 4.2 fifo.h
- 五.结语
一.序言
本次实验利用环形队列+DMA空闲中断+串口。。通过这个实验可以非常深入的理解队列,DMA,串口的知识。如果你能自己实现掌握这个实验,那么你应该基本掌握了队列,DMA,串口的知识。
二.实验原理
本次使用的是用环形队列当缓冲器区接收串口数据。我们可以先区了解DMA的空闲中断。本次实验就是使用DMA空闲中断。这里就简单介绍一下,当串口接收到一帧数据后就会产生中断,那么如何判断数据是一帧呢?这里的判断机制就是,如果收到数据后,大概接收一个字节的时间,都没有接收到数据的话,就判断已经接收的数据是一帧。接收一帧数据后,串口就会产生空闲中断。同时DMA会把串口DR移位寄存器的值搬运到环形队列缓冲区。我们只需要在环形队列缓冲器拿数据即可。
三.实战是检验真理的唯一标准
仅仅通过理论,只能说你知道有这个东西,但是你可能并不会。下面我通过代码讲解也帮助深入理解理论。
3.1 usart1.c
void Usart1_Init(void)
{GPIO_InitTypeDef GPIO_InitStructure;USART_InitTypeDef USART_InitStructure;NVIC_InitTypeDef NVIC_InitStructure;DMA_InitTypeDef DMA_InitStructure;RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1|RCC_APB2Periph_GPIOA, ENABLE); //USART1_TX GPIOA.9GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; //PA.9GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; GPIO_Init(GPIOA, &GPIO_InitStructure);//³õʼ»¯GPIOA.9//USART1_RX GPIOA.10³õʼ»¯GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;//PA10GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;GPIO_Init(GPIOA, &GPIO_InitStructure);////Usart1 NVIC ÅäÖÃNVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=5 ;NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure); //¸ù¾ÝÖ¸¶¨µÄ²ÎÊý³õʼ»¯VIC¼Ä´æÆ÷USART_InitStructure.USART_BaudRate = 115200USART_InitStructure.USART_WordLength = USART_WordLength_8bUSART_InitStructure.USART_StopBits = USART_StopBits_1;USART_InitStructure.USART_Parity = USART_Parity_No;USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; USART_Init(USART1, &USART_InitStructure); //使能空闲中断USART_ITConfig(USART1, USART_IT_IDLE , ENABLE);//使能发送完成中断--通过串口发送数据USART_ITConfig(USART1, USART_IT_TC , ENABLE);USART_DMACmd(USART1, USART_DMAReq_Tx|USART_DMAReq_Rx, ENABLE);USART_Cmd(USART1, ENABLE); RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE); DMA_DeInit(DMA1_Channel5);//外设地址--串口1 的DR寄存器DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)(&USART1->DR);DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)Uart1_Rx_Buffer; DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC; DMA_InitStructure.DMA_BufferSize = BSP_UART1_RX_SIZE; DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_Byte;DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_Byte;DMA_InitStructure.DMA_Mode = DMA_Mode_Circular; DMA_InitStructure.DMA_Priority = DMA_Priority_Medium;DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;//串口1的接收引脚为DAM1的通道5DMA_Init(DMA1_Channel5, &DMA_InitStructure);DMA_Cmd (DMA1_Channel5,ENABLE); //初始化环形队列Fifo_Init(&Uart1_Rx_Fifo,Uart1_Rx_Buffer,BSP_UART1_RX_SIZE);
3.2 串口中断
void USART1_IRQHandler(void)
{ //加上volatile 关键字只是为了防止警告volatile uint32_t temp = 0;BaseType_t xHigherPriorityTaskWoken = pdFALSE;if(USART_GetITStatus(USART1,USART_IT_IDLE)!= RESET)//¿ÕÏÐÖжÏ{//根据数据量数据入队列//DMA_GetCurrDataCounter(DMA1_Channel5); 通道5还剩下多少个数据应该传输。//初始化的时候设置的通道5传输多少数据。Uart1_Rx_Fifo.in = BSP_UART1_RX_SIZE - DMA_GetCurrDataCounter(DMA1_Channel5);//先读SR 再读DR 只是为了消除空闲中断标志位。手册上有说明temp = USART1->SR; temp = USART1->DR;USART_ClearITPendingBit(USART1,USART_IT_IDLE);}
三.队列代码
代码可能看起来简单,但是不是那么容易理解。得自己慢慢体会,才能真正掌握,
而不是一昧的copy,不然出了问题也解决不了,自己代码水平也不能提高。
4.1 fifo.c
#include "sys.h"
#include "app_fifo.h"//初始化
void Fifo_Init(FIFO_Type* fifo, uint8_t* buffer, uint16_t size)
{fifo->buffer = buffer;fifo->in = 0 ;fifo->out = 0;fifo->size = size;
}
//从队列中拿数据
uint16_t Fifo_Get(FIFO_Type* fifo, uint8_t* buffer, uint16_t len)
{uint16_t lenght;uint16_t in = fifo->in; uint16_t i;lenght = (in + fifo->size - fifo->out)%fifo->size;if(lenght > len)lenght = len;for(i = 0; i < lenght; i++){buffer[i] = fifo->buffer[(fifo->out + i)%fifo->size];}fifo->out = (fifo->out + lenght)%fifo->size;return lenght;
}
4.2 fifo.h
#ifndef FIFO_H
#define FIFO_H
#include "stm32f10x.h"
typedef struct {uint8_t* buffer; uint16_t in; uint16_t out; uint16_t size;
}FIFO_Type;void Fifo_Init(FIFO_Type* fifo, uint8_t* buffer, uint16_t size);uint16_t Fifo_Get(FIFO_Type* fifo, uint8_t* buffer, uint16_t len);#endif
五.结语
代码放出来的就是以上这些,都放上去也比较麻烦,同时也没什么意义。写这篇博客是想让大家有大致的思路以及参考代码,从而根据自己的项目或者需求区进行改动。最后,如果真的需要全部代码的可以私信博主!最好点点关注!!!
相关文章:
环形队列+DMA空闲中断+接收串口数据
环形队列DMA空闲中断接收串口数据 一.序言二.实验原理三.实战是检验真理的唯一标准3.1 usart1.c3.2 串口中断 三.队列代码4.1 fifo.c4.2 fifo.h 五.结语 一.序言 本次实验利用环形队列DMA空闲中断串口。。通过这个实验可以非常深入的理解队列,DMA,串口的知识。如果…...
LeetCode 31题:下一个排列
目录 题目 思路 代码 题目 整数数组的一个 排列 就是将其所有成员以序列或线性顺序排列。 例如,arr [1,2,3] ,以下这些都可以视作 arr 的排列:[1,2,3]、[1,3,2]、[3,1,2]、[2,3,1] 。 整数数组的 下一个排列 是指其整数的下一个字典序…...
CMake:检测python模块和包
CMake:检测python模块和包 导言项目结构CMakeLists.txt相关源码 导言 上一篇,我们基本了解了如何去检测python的解释器和python库。通常,代码是依赖于特定的python模块,无论是python工具、嵌入python的程序,还是扩展python的库。…...
02Mysql之多表查询--例题讲解
一、题目详情,以及表的建立 新增员工表emp和部门表deptcreate table dept (dept1 int ,dept_name varchar(11));create table emp (sid int ,name varchar(11),age int,worktime_start date,incoming int,dept2 int);insert into dept values(101,财务),(102,销售)…...
虹科方案 | 汽车总线协议转换解决方案
汽车总线: 汽车总线是一种用于在车辆电子系统中传输数据和控制信息的通信系统。它允许不同的电子控制单元(ECU)在车辆中相互通信,协调各个系统的操作,以实现功能的集成和协同工作。 在现代汽车中,综合通信…...
Mr. Cappuccino的第59杯咖啡——简单手写SpringIOC框架
简单手写SpringIOC框架 环境搭建基于XML方式项目结构项目代码运行结果 基于注解方式项目结构项目代码运行结果 简单手写SpringIOC框架核心原理基于XML方式原理项目结构项目代码运行结果 基于注解方式原理项目结构项目代码运行结果 环境搭建 基于XML方式 项目结构 项目代码 p…...
爬虫 学习HTML标签和元素的基本概念,了解网页的结构和内容
HTML(Hypertext Markup Language)是一种用于创建网页的标记语言,由一系列的标签组成。标签使用尖括号(< 和 >)包围,并且通常成对出现,一个是开始标签,一个是结束标签。 HTML文…...
mysql将id重新修改为递增
文章目录 场景解决,排序的话可以先按照一定大小改一下,然后将id字段删掉,再重新生成即可清空表数据,并将自增id改为1开始 场景 好比我有个配置表: CREATE TABLE config (id int NOT NULL AUTO_INCREMENT,config_key varchar(20) NOT NULL,config_value varchar(500) NOT NU…...
http、https笔记
目录 HTTP 基本概念状态码:get和post的区别:http 常⻅字段:http的缺点: HTTP/1.1HTTP/3HTTPSHTTPS和HTTP区别对称加密和⾮对称加密⾮对称加密 HTTP 基本概念 状态码: 1xx 中间状态,比如post的continue 20…...
飞凌嵌入式「国产」嵌入式核心板大盘点(三)——龙芯中科、赛昉科技
为了帮助各位工程师朋友详细了解飞凌嵌入式推出的“国产化”产品,小编专门开设了「国产平台大盘点专题」。上周,已经带大家盘点了飞凌嵌入式联合瑞芯微电子和全志科技两个国产处理器品牌打造的平台,今天,将继续为大家介绍龙芯和赛…...
以vue2为例,用npm开发环境在后端部署vue2项目(更推荐使用nginx部署)
因为之前一致出现的跨域问题,从而想到了这个办法,属于偏方。推荐使用nginx部署,再去解决跨域问题。 接下来聊一聊本文所使用的方法。 首先将你的前端vue项目拷贝一份到服务器,准备一个dockerfile文件,用这个进行部署首…...
docker容器监控:Cadvisor +Prometheus+Grafana的安装部署
目录 Cadvisor PrometheusGrafana的安装部署 一、安装docker: 1、安装docker-ce 2、阿里云镜像加速器 3、下载组件镜像 4、创建自定义网络 二、部署Cadvisor 1、被监控主机上部署Cadvisor容器 2、访问cAdvisor页面 三、安装prometheus 1、部署Prometheus…...
前端食堂技术周刊第 93 期:7 月登陆 Web 平台的新功能、Node.js 工具箱、Nuxt3 开发技巧、MF 重构方案
美味值:🌟🌟🌟🌟🌟 口味:橙橙冰萃美式 食堂技术周刊仓库地址:https://github.com/Geekhyt/weekly 大家好,我是童欧巴。欢迎来到前端食堂技术周刊,我们先来…...
获取 Android 的 SHA1 值
1、调试版,可以直接在 Android studio 中的 gradle 中查看。也可以用下面方法进行 前提要先确定签名文件所在的路径:调试版默认使用的签名文件是debug.keystore,文件处于 C 盘用户目录下的.android文件夹下。打开命令行工具, 1、…...
! [remote rejected] develop -> develop (pre-receive hook declined)
问题 git push 远程提交dao develop 分支失败,出现下面错误信息 remote: GitLab: You are not allowed to push code to protected branches on this project. To https://xxx.com.cn/xxx/xxx/xxx/xxx.git/! [remote rejected] develop -> develop (pre-receiv…...
最强的表格组件—AG Grid使用以及License Key Crack
PS: 想要官方 License Key翻到最后面 Ag Grid简介 Ag-Grid 是一个高级数据网格,适用于JavaScript/TypeScript应用程序,可以使用React、Angular和Vue等流行框架进行集成。它是一种功能强大、灵活且具有高度可定制性的表格解决方案,提供了丰富…...
【算法】逆波兰表达式
文章目录 定义求法代码思想: 定义 逆波兰表达式也称为“后缀表达式”,是将运算符写在操作数之后的运算式。 求法 *如:(ab)c-(ab)/e的转换过程: 先加上所有的括号。 (((ab)*c)-((ab)/e))将所有的运算符移到括号外面 (((ab) c)* …...
添加SQLCipher 到项目中
文章目录 一、克隆下载SQLCipher二、手动导入1. 生成sqlite3.c2. 在项目中添加命令3. 添加 Security.framework 三、CocoaPods导入 SQLCipher官方地址 一、克隆下载SQLCipher $ cd ~/Documents/code $ git clone https://github.com/sqlcipher/sqlcipher.git二、手动导入 1.…...
轻松预约,尽享美食,详解餐厅预约小程序的设计与实现
随着智能手机的普及和人们生活水平的提高,餐厅预约已经成为人们日常生活中的一部分。为了更好地满足人们的需求,许多餐厅开始使用小程序来提供更方便快捷的预约服务。本文将介绍如何制作一款餐厅预约小程序的详细步骤。 1. 进入乔拓云网后台,…...
数据结构--栈和队列3.1(栈-顺序结构)
目录 栈(Stack)栈顶(top)栈底(bottom)空栈(不含任何元素) 创建栈 入栈操作 出栈操作 销毁一个栈 计算栈的当前容量 实例分析 栈的插入操作叫做进栈(Push…...
Ubuntu系统下交叉编译openssl
一、参考资料 OpenSSL&&libcurl库的交叉编译 - hesetone - 博客园 二、准备工作 1. 编译环境 宿主机:Ubuntu 20.04.6 LTSHost:ARM32位交叉编译器:arm-linux-gnueabihf-gcc-11.1.0 2. 设置交叉编译工具链 在交叉编译之前&#x…...
1688商品列表API与其他数据源的对接思路
将1688商品列表API与其他数据源对接时,需结合业务场景设计数据流转链路,重点关注数据格式兼容性、接口调用频率控制及数据一致性维护。以下是具体对接思路及关键技术点: 一、核心对接场景与目标 商品数据同步 场景:将1688商品信息…...
[ICLR 2022]How Much Can CLIP Benefit Vision-and-Language Tasks?
论文网址:pdf 英文是纯手打的!论文原文的summarizing and paraphrasing。可能会出现难以避免的拼写错误和语法错误,若有发现欢迎评论指正!文章偏向于笔记,谨慎食用 目录 1. 心得 2. 论文逐段精读 2.1. Abstract 2…...
跨链模式:多链互操作架构与性能扩展方案
跨链模式:多链互操作架构与性能扩展方案 ——构建下一代区块链互联网的技术基石 一、跨链架构的核心范式演进 1. 分层协议栈:模块化解耦设计 现代跨链系统采用分层协议栈实现灵活扩展(H2Cross架构): 适配层…...
C++ 求圆面积的程序(Program to find area of a circle)
给定半径r,求圆的面积。圆的面积应精确到小数点后5位。 例子: 输入:r 5 输出:78.53982 解释:由于面积 PI * r * r 3.14159265358979323846 * 5 * 5 78.53982,因为我们只保留小数点后 5 位数字。 输…...
【JavaSE】绘图与事件入门学习笔记
-Java绘图坐标体系 坐标体系-介绍 坐标原点位于左上角,以像素为单位。 在Java坐标系中,第一个是x坐标,表示当前位置为水平方向,距离坐标原点x个像素;第二个是y坐标,表示当前位置为垂直方向,距离坐标原点y个像素。 坐标体系-像素 …...
OpenPrompt 和直接对提示词的嵌入向量进行训练有什么区别
OpenPrompt 和直接对提示词的嵌入向量进行训练有什么区别 直接训练提示词嵌入向量的核心区别 您提到的代码: prompt_embedding = initial_embedding.clone().requires_grad_(True) optimizer = torch.optim.Adam([prompt_embedding...
【论文阅读28】-CNN-BiLSTM-Attention-(2024)
本文把滑坡位移序列拆开、筛优质因子,再用 CNN-BiLSTM-Attention 来动态预测每个子序列,最后重构出总位移,预测效果超越传统模型。 文章目录 1 引言2 方法2.1 位移时间序列加性模型2.2 变分模态分解 (VMD) 具体步骤2.3.1 样本熵(S…...
基于IDIG-GAN的小样本电机轴承故障诊断
目录 🔍 核心问题 一、IDIG-GAN模型原理 1. 整体架构 2. 核心创新点 (1) 梯度归一化(Gradient Normalization) (2) 判别器梯度间隙正则化(Discriminator Gradient Gap Regularization) (3) 自注意力机制(Self-Attention) 3. 完整损失函数 二…...
jmeter聚合报告中参数详解
sample、average、min、max、90%line、95%line,99%line、Error错误率、吞吐量Thoughput、KB/sec每秒传输的数据量 sample(样本数) 表示测试中发送的请求数量,即测试执行了多少次请求。 单位,以个或者次数表示。 示例:…...
