FPGA 按键控制串口发送

按键消抖

消抖时间一般为10ms,我使用的板子是ACX720,晶振为50MHZ,20ns为一周期。

在这里插入图片描述

状态机

在这里插入图片描述

模块设计

在这里插入图片描述

设计文件

`timescale 1ns / 1ps
//
// Company: 
// Engineer: 
// 
// Create Date: 2023/01/11 12:18:36
// Design Name: 
// Module Name: key_filter
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//module key_filter(Clk,Rst_n,Key_in,Key_flag, //按键按下标志位Key_State //高电平,按键按下
);input Clk;input Rst_n;input Key_in;output reg Key_flag;output reg Key_State;parameter Filter_Time=500_000; //10mslocalparam S1=4'b0001,//按键松开S2=4'b0010,//消抖计数S3=4'b0100,//按键松开S4=4'b1000;//消抖计数//捕捉按键上升沿和下降沿reg [2:0] Pos_Neg_r;wire pos_edge;wire neg_edge;always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)Pos_Neg_r<=0;else beginPos_Neg_r={Pos_Neg_r[1:0],Key_in};endendassign pos_edge=Pos_Neg_r[2:1]==2'b01;//上升沿  //按键松开assign neg_edge=Pos_Neg_r[2:1]==2'b10;//下降沿  //按键按下//消抖延迟计数器reg [18:0] counter_cnt;reg En_counter_cnt;//按键消抖计数的条件wire end_counter_cnt;always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)counter_cnt<=19'd0;else if(En_counter_cnt)beginif(end_counter_cnt)counter_cnt<=19'd0;elsecounter_cnt<=counter_cnt+1'd1;endelsecounter_cnt<=19'd0;endassign end_counter_cnt=counter_cnt>=(Filter_Time-1);reg	[3:0]	cur_state;					//定义现态寄存器reg	[3:0]	next_state;					//定义次态寄存器/*-----------------------------------------------------------------------状态机第一段:同步时序描述状态转移-----------------------------------------------------------------------*/always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)cur_state <= S1;				//复位初始状态elsecur_state <= next_state;		//次态转移到现态end/*-----------------------------------------------------------------------状态机第二段:组合逻辑判断状态转移条件,描述状态转移规律以及输出-----------------------------------------------------------------------*/always@(*)begincase(cur_state)S1:begin                    //按键松开状态if(neg_edge)            //按键按下--检测到下降沿next_state=S2;elsenext_state=cur_state;endS2:beginif(pos_edge)next_state=S1;else if(end_counter_cnt)next_state=S3;elsenext_state=cur_state;endS3:begin                    //按键按下状态if(pos_edge)            //按键松开--检测到上升沿next_state=S4;elsenext_state=cur_state;endS4:begin    if(neg_edge)next_state=S3;else if(end_counter_cnt)next_state=S1;elsenext_state=cur_state;enddefault:next_state=cur_state;endcaseend/*-----------------------------------------------------------------------状态机第三段:时序逻辑描述输出-----------------------------------------------------------------------*///消抖计数使能always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)En_counter_cnt <= 1'b0;			      //复位、初始状态 elsecase(cur_state)					      //根据当前状态进行输出S1:	En_counter_cnt <= 1'b0;		  //不计数			S2:	En_counter_cnt <= 1'b1;		  //计数S3:	En_counter_cnt <= 1'b0;		  //不计数S4:	En_counter_cnt <= 1'b1;		  //计数default:En_counter_cnt <= 1'b0;   //默认不计数endcaseend//按键按下标志位always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)Key_flag <= 1'b0;                    //复位、初始状态 //Key_State存在一拍else if(cur_state==S2 && end_counter_cnt) Key_flag<=1'd1;else Key_flag<=1'd0;end//输出按键状态always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)Key_State <= 1'b0;                    //复位、初始状态 else if(cur_state==S3) Key_State<=1'd1;else if(cur_state==S4 && end_counter_cnt)Key_State<=1'd0;elseKey_State<=Key_State;endendmodule

仿真验证

`timescale 1ns / 1ps
//
// Company: 
// Engineer: 
// 
// Create Date: 2023/01/06 16:24:27
// Design Name: 
// Module Name: key_filter_tb
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//module key_filter_tb();reg Clk;reg Rst_n;reg Key_in;wire Key_flag;wire Key_State;key_filter#(.Filter_Time(5000)//100us)key_filter(Clk,Rst_n,Key_in,Key_flag, //按键按下标志位Key_State //高电平,按键按下);initial Clk=1;always #10 Clk=~Clk;initial beginRst_n=0;Key_in=1;#201;Rst_n=1;Key_in=1;#20000;Key_in=0;#20000;Key_in=1;#10000;Key_in=0;#20000;Key_in=1;#20000;Key_in=0;#600000;Key_in=1;#20000;Key_in=0;#20000;Key_in=1;#10000;Key_in=0;#20000;Key_in=1;#20000;Key_in=0;#20000;Key_in=1;#10000;Key_in=0;#20000;Key_in=1;#20000;Key_in=0;#20000;Key_in=1;#10000;Key_in=1;#600000;$stop;endendmodule

在这里插入图片描述

串口发送

**注意:**电平信号的传输线中有一个参考电平线(一般是GND),然后信号线上的信号值是由信号线电平和参考电平线的电压差决定。所以我们一定要养成模块之间共地的好习惯。

串口帧

在这里插入图片描述

模块设计

在这里插入图片描述

`timescale 1ns / 1ps
//
// Company: 
// Engineer: 
// 
// Create Date: 2023/01/06 11:30:58
// Design Name: 
// Module Name: UART_Byte_Tx
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//module UART_Byte_Tx#(parameter BaudRate = 115200,//波特率parameter ClockRate = 50_000_000//系统时钟)
(Clk,Rst_n,Send_En,data_byte,Tx_Data,Tx_Done,uart_state
);input Clk;input Rst_n;input Send_En;input [7:0] data_byte;output reg Tx_Data;output reg Tx_Done;output reg uart_state;//设置使能reg tx_en;always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)tx_en<=0;else if(Send_En)tx_en<=1'd1;else if(Tx_Done)tx_en<=1'd0;elsetx_en<=tx_en;end//设置波特率localparam Buad_Num = ClockRate/BaudRate;//设置计数器reg [12:0] buad_cnt;wire add_buad_cnt;wire end_buad_cnt;always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)buad_cnt<=0;else if(add_buad_cnt)beginif(end_buad_cnt)buad_cnt<=0;else buad_cnt<=buad_cnt+1'b1;endelsebuad_cnt<=0;endassign add_buad_cnt=tx_en;assign end_buad_cnt=buad_cnt>=(Buad_Num-1'd1);//设置发送bit计数reg [3:0] bit_cnt;wire add_bit_cnt;wire end_bit_cnt;always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)bit_cnt<=0;else if(add_bit_cnt)bit_cnt<=bit_cnt+1'd1;else if(end_bit_cnt)bit_cnt<=0;elsebit_cnt<=bit_cnt;endassign add_bit_cnt=buad_cnt==1;assign end_bit_cnt=(bit_cnt==4'd10 && add_bit_cnt) || !tx_en;//发送数据always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)Tx_Data<=1;else begincase(bit_cnt)4'd1:Tx_Data<=0;4'd2:Tx_Data<=data_byte[0];4'd3:Tx_Data<=data_byte[1];4'd4:Tx_Data<=data_byte[2];4'd5:Tx_Data<=data_byte[3];4'd6:Tx_Data<=data_byte[4];4'd7:Tx_Data<=data_byte[5];4'd8:Tx_Data<=data_byte[6];4'd9:Tx_Data<=data_byte[7];4'd10:Tx_Data<=1;default:Tx_Data<=1;endcaseendend//发送结束always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)Tx_Done<=0;else if(bit_cnt==4'd10 && add_bit_cnt)Tx_Done<=1;elseTx_Done<=0;end//发送状态(有效数据)wire En_uart_state;wire Nen_uart_state;always@(posedge Clk or negedge Rst_n)beginif(!Rst_n)uart_state<=0;else if(En_uart_state)uart_state<=1;else if(Nen_uart_state)uart_state<=0;endassign En_uart_state=bit_cnt==4'd1 && add_bit_cnt;assign Nen_uart_state=bit_cnt==4'd9 && add_bit_cnt;endmodule

仿真验证

`timescale 1ns / 1ps
//
// Company: 
// Engineer: 
// 
// Create Date: 2023/01/06 11:31:09
// Design Name: 
// Module Name: UART_Byte_Tx_tb
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//module UART_Byte_Tx_tb();reg Clk;reg Rst_n;reg Send_En;reg [7:0]data_byte;wire Tx_Data;wire Tx_Done;wire uart_state;initial Clk=1;always #10 Clk=~Clk;initial beginRst_n=0;Send_En=0;data_byte=0;#201;Rst_n=1;data_byte=8'b1001_0110;Send_En=1;#20;Send_En=0;#100000;data_byte=8'b0111_0110;Send_En=1;#20;Send_En=0;#100000;$stop;endUART_Byte_Tx UART_Byte_Tx(.Clk(Clk),.Rst_n(Rst_n),.Send_En(Send_En),.data_byte(data_byte),.Tx_Data(Tx_Data),.Tx_Done(Tx_Done),.uart_state(uart_state));endmodule

在这里插入图片描述

按键控制串口发送

RTL视图

在这里插入图片描述

`timescale 1ns / 1ps
//
// Company: 
// Engineer: 
// 
// Create Date: 2023/01/07 13:43:42
// Design Name: 
// Module Name: Uart_Key_Send_cmd
// Project Name: 
// Target Devices: 
// Tool Versions: 
// Description: 
// 
// Dependencies: 
// 
// Revision:
// Revision 0.01 - File Created
// Additional Comments:
// 
//module Uart_Key_Send_cmd(Clk,Rst_n,Key_in,uart_tx
);input Clk;input Rst_n;input Key_in;output uart_tx;//按键模块wire Key_flag;wire Key_State;key_filter key_filter(Clk,Rst_n,Key_in,Key_flag, //按键按下标志位Key_State //高电平,按键按下);//串口发送reg [7:0] data_byte;wire Tx_Done;wire uart_state;//assign data_byte=8'b0100_0001; //发送Aalways@(posedge Clk or negedge Rst_n)beginif(!Rst_n)  data_byte<=8'b0100_0001; //发送Aelse if(Tx_Done)data_byte<=data_byte+1'b1;//数据加一endUART_Byte_Tx UART_Byte_Tx(.Clk(Clk),.Rst_n(Rst_n),.Send_En(Key_flag),.data_byte(data_byte),.Tx_Data(uart_tx),.Tx_Done(Tx_Done),.uart_state(uart_state));endmodule

板级验证

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/274814.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

重学SpringBoot3-ErrorMvcAutoConfiguration类

更多SpringBoot3内容请关注我的专栏&#xff1a;《SpringBoot3》 期待您的点赞&#x1f44d;收藏⭐评论✍ 重学SpringBoot3-ErrorMvcAutoConfiguration类 ErrorMvcAutoConfiguration类的作用工作原理定制 ErrorMvcAutoConfiguration示例代码1. 添加自定义错误页面2.自定义错误控…

基于Qt 和python 的自动升级功能

需求&#xff1a; 公司内部的一个客户端工具&#xff0c;想加上一个自动升级功能。 服务端&#xff1a; 1&#xff0c;服务端使用python3.7 &#xff0c;搭配 fastapi 和uvicorn 写一个简单的服务&#xff0c;开出一个get接口&#xff0c;用于客户端读取安装包的版本&#…

Pycharm的Project Structure (项目结构)

文章目录 一、Sources二、Tests三、Exeluded四、Namespace packages五、Templates六、Resources 一、Sources 源代码根目录&#xff1a;包含项目的主要源代码&#xff0c;它会在这个目录下搜索代码&#xff0c;然后自动补全和只能提示都通过这里的代码提供。若项目运行自定义代…

System类 --java学习笔记

System System代表程序所在的系统&#xff0c;也是一个工具类 常见System方法&#xff1a; 按照惯例&#xff0c;exit括号中非零状态码表示异常终止&#xff0c;填零则表示人为终止 currentTimeMillis&#xff08;&#xff09;返回的是long类型的时间毫秒值&#xff1a;指的…

重学SpringBoot3-WebMvcAutoConfiguration类

更多SpringBoot3内容请关注我的专栏&#xff1a;《SpringBoot3》 期待您的点赞&#x1f44d;收藏⭐评论✍ 重学SpringBoot3-WebMvcAutoConfiguration类 是什么什么用生效条件作用 自定义配置的三种方式自定义配置举例1. 自定义 DispatcherServlet 配置2. 静态资源配置3. 自定义…

前端 --- HTML

1. HTML 结构 1.1 HTML 文件基本结构 <html><head><title>第一个html程序</title></head><body>hello world!</body> </html> html 标签是整个 html 文件的根标签(最顶层标签)head 标签中写页面的属性.body 标签中写的是页…

设计模式一 ---单例设计模式(动力节点,JavaSE基础)

设计模式 1.什么是设计模式&#xff1f; 2.设计模式的分类 单例设计模式就是GoF模式中的一种。 3.GoF设计模式的分类&#xff1a; 单例设计模式&#xff1a; 顾名思义&#xff1a;单个实例的设计模式&#xff01;

k8s+wordpress+zabbix+elastic+filebeat+kibana服务搭建以及测试

一&#xff0c;环境&#xff1a;docker&#xff0c;k8s&#xff0c;zabbix&#xff0c;以及搭建worpdress&#xff0c;elasticsearch&#xff0c;filebeat&#xff0c;kibana 二&#xff0c;主机分配&#xff1a; 名称host详述个人博客3192.168.142.133 搭配mysql8.0.36的数据…

集合实现类研究底层(部分):手撕ArrayList底层源码、手撕LinkedList底层源码、手写单向链表和双向链表

day26上 集合框架图 标绿已经学习底层&#xff0c;深入底层主要是研究实现类底层 继承关系图 手撕ArrayList底层源码 ps:研究添加元素的过程 思路&#xff1a; 1.研究继承关系 2.研究属性 3.理解创建集合的过程 – 构造方法的底层原理 4.研究添加元素的过程 提升&#xff1a…

jmeter发送请求参数如何使用变量

问题描述 发送jmeter请求时&#xff0c;想设置请求参数为变量 解决方法

基于yolov5的草莓成熟度检测系统,可进行图像目标检测,也可进行视屏和摄像检测(pytorch框架)【python源码+UI界面+功能源码详解】

功能演示&#xff1a; 基于yolov5的草莓成熟度检测系统&#xff0c;系统既能够实现图像检测&#xff0c;也可以进行视屏和摄像实时检测_哔哩哔哩_bilibili &#xff08;一&#xff09;简介 基于yolov5的草莓成熟度系统是在pytorch框架下实现的&#xff0c;这是一个完整的项目…

基于YOLOv8/YOLOv7/YOLOv6/YOLOv5的条形码二维码检测系统(深度学习+UI界面+训练数据集+Python代码)

摘要&#xff1a;在物流和制造业中&#xff0c;开发一套高效的条形码与二维码识别系统显得尤为关键。本博文深入探讨了如何利用深度学习技术打造出一套先进的条形码及二维码检测系统&#xff0c;并且提供了一套完整的实施方案。该系统搭载了性能卓越的YOLOv8算法&#xff0c;并…

php7.3.4连接sqlserver(windows平台)

前言 有个项目需要手上laravel连接客户的sqlserver数据库读取数据&#xff0c;故在本地开发的lnmp环境中&#xff0c;php需要增加扩展 过程 从微软官网下载sqlsrv扩展,注意注意php版本&#xff0c;下载地址 解压的文件会有nts和ts两个版本&#xff0c;本地打开phpinfo查看 将…

如何在Linux系统安装SVN并配置固定公网地址远程访问【内网穿透】

文章目录 前言1. Ubuntu安装SVN服务2. 修改配置文件2.1 修改svnserve.conf文件2.2 修改passwd文件2.3 修改authz文件 3. 启动svn服务4. 内网穿透4.1 安装cpolar内网穿透4.2 创建隧道映射本地端口 5. 测试公网访问6. 配置固定公网TCP端口地址6.1 保留一个固定的公网TCP端口地址6…

C++开发基础——IO操作与文件流

一&#xff0c;基础概念 C的IO操作是基于字节流&#xff0c;并且IO操作与设备无关&#xff0c;同一种IO操作可以在不同类型的设备上使用。 C的流是指流入/流出程序的字节序列&#xff0c;在输入操作中数据从外部设备(键盘&#xff0c;文件&#xff0c;网络等)流入程序&#x…

关于c++的protected关键字

关于c的protected关键字 分类引言例子1&#xff09;错误的demo2&#xff09;改正的demo protected在c中的含义与作用 分类 c基础知识 引言 做了很业务&#xff0c;c基础知识却忘了很多&#xff0c;今天看了一个例子&#xff0c;唤醒了我关于c三大特性之一----封装&#xff0…

信息抽取在旅游行业的应用:以景点信息抽取为例

开源项目推荐 今天先给大家推荐一个开源项目&#xff0c;多模态AI能力引擎平台: 免费的自然语言处理、情感分析、实体识别、图像识别与分类、OCR识别、语音识别接口&#xff0c;功能强大&#xff0c;欢迎体验。 https://gitee.com/stonedtx/free-nlp-api 场景描述 在旅游行业…

echarts vue里画一个简单的环状饼图

<!--观察记录--><div class"teach-plan observe-record"><div class"title-common"><div class"title-common-left">观察记录</div></div><div class"teach-plan-cont"><div class"…

pytest生成allure的报告

首先要下载安装配置allure allure serve ./outputs/allure_report 可以生成html的文件自动在默认浏览器中打开

蓝桥杯每日一题 走迷宫bfs 超超详细解释!!!

昨天学习了bfs的基本概念&#xff0c;今天来做一道经典习题练练手吧&#xff01; bfs常用的两类题型 1.从A出发是否存在到达B的路径(dfs也可) 2.从A出发到B的最短路径&#xff08;数小:<20才能用dfs&#xff09; 遗留的那个问题的答案- 题目&#xff1a;走迷宫 答案&…