一、准备及目标

采用的元器件:T型口数据线2;总线1;USB Blaster1;FPGA板子1;HC-05蓝牙模块*1。
使用的软件:手机:蓝牙串口SPP;电脑:Quartus。
实现的目标:手机输入一段信息,通过蓝牙传递信息给FPGA,FPGA收到信息后,再将该信息通过蓝牙传递回手机。
如图:

二、为什么要写这么一篇文章

太菜了QAQ,好多网上的东西看不懂,理解了UART,但是找不到一个基于UART且读得懂的代码。所有我把我的东西放在这里,恳请广大网友批评指正的同时,也帮助一些像我一样菜的同学理解一下蓝牙的串口协议。

三、原理

1、UART(异步收发传输器)串口协议

(1)为什么需要UART串口协议?
信息的传递有串行(异步)和并行(同步)两种。同步传输快但需要的线多,异步需要的线少但传输慢。以异步进行信息传递的叫UART,把异步信息和同步信息进行转换的标准叫串口协议。这个标准保证传递的信息时正确的。
(2)UART串口协议的原理:
这个不赘述,找到两个很棒的资料:
1、这个是文字的,细的一批—— FPGA——UART Verilog程序设计
2、这个是bilibili的视频,很直观——【Electronoobs】UART-I2C-SPI 基本串行通信协议 1080P (中英字幕)

2、手机、蓝牙、FPGA

当我给FPGA装上蓝牙模块后,我会很自然的认为信息的传递发生在手机和FPGA之间,这么想会给编程带来一定阻力。这种想法需要纠正为信息的传递发生在蓝牙模块和FPGA之间:手机和蓝牙连接上后相当于一个整体,里面流通的信息是一致的,而对他们而言,FPGA才是外部。所以我需要把蓝牙模块的输出(tx)所连接的FPGA上的引脚定义为(rx),蓝牙模块的输出(rx)所连接的FPGA上的引脚定义为(tx),即蓝牙模块的输入是FPGA的输出,蓝牙模块的输出是FPGA的输入。

3、实物连接

这个不难:

四、代码

代码很非常丑陋且基础,但毕竟自己写的,读得懂:

1、主模块:

module bluetooth(input sys_clk,input rx,output tx,output wire[1:0]led
);                                                                              //sys_clk为系统板载时钟(50MHz),rx对应蓝牙模块的tx,tx对应蓝牙模块的rx;led是我设置来判断读入数据错没错的wire[7:0]message;                                                          //message为读入的数据wire sig;                                                                    //sig是读入的完成信号,下降沿表示读入完成,同时作为输出的开始信号uart_r uart_r_1(.clk(sys_clk),.rx(rx),.message(message),.over(sig));       //读入uart_t uart_t_1(.clk(sys_clk),.tx(tx),.message(message),.run(sig));         //输出assign led[0]=message[0];                                                  //这两个看数据最后两位存的对不对的assign led[1]=message[1];
endmodule

2、输入模块:

module uart_r(input clk,input wire rx,output reg [7:0]message,output reg over=0
);                                                      //clk为FPGA板载时钟(50MHz),rx为读入的串行信号,message为对应的并行信号,over的下降沿将表示读入转换完成reg [12:0]cnt_clk=0;                              //需要一个量来数clk的个数,每5208个clk,对应0.104us,即波特率9600对应的1bit占用的时常reg [4:0]cnt_message=0;                               //计数message的位数,表征传递进行到了第几位reg [7:0]message_mid=0;                               //message的前体,在over的下降沿传递给message,避免传递没结束,message就有输出值了reg r_start=1;                                      //判断第一个0位,表示传递开始always @(posedge clk)beginif (rx==0&&r_start==1) begincnt_clk<=cnt_clk+1;if (cnt_clk==2604&&rx==0) beginr_start<=0;cnt_clk<=0;cnt_message<=0;message_mid<=0;endend                                             //判断是否为开始位,是时开始计算clk,数2604下(0.5bit)即在开始位中间,开始读数else if (r_start==0) begincnt_clk<=cnt_clk+1;if (cnt_clk==5208) begin                    //每5208个clk读一次message_mid[cnt_message]<=rx;cnt_message<=cnt_message+1;cnt_clk<=0;end                                               else if (cnt_message==8) begin                //读完第8位不读了if (cnt_clk==3000) begin                //在数据位第8位的中间往右走2604个clk进入终止位(默认无奇偶校验位),在终止位中(往右走3000个clk和5000个clk之间)输出一个over信号over<=1;endif (cnt_clk==5000) begin              //over下降沿,传递完成,message_mid赋值给message,所有信号还原over<=0;cnt_clk<=0;cnt_message<=0;r_start<=1;message<=message_mid;message_mid<=0;endendend                                              //开始读数,每5208个clk读一次else beginr_start<=1;over<=0;endendendmodule

3、输出模块:

module uart_t(input wire [7:0]message,input clk,output reg tx=1,input wire run);                                                                    //大致思路与输入类似,tx连接蓝牙的rx,注意run信号为开始信号,连接的输入的over信号reg [12:0]cnt_clk=0;reg [4:0]cnt_message=0;reg t_start=1;always @(posedge clk) beginif (run==1&&t_start==1) begint_start<=0;cnt_clk<=0;endelse if (run==0&&t_start==0&&cnt_message==0) begin              //在run的下降沿开始输出tx<=0;cnt_clk<=cnt_clk+1;if (cnt_clk==5208) begintx<=message[cnt_message];cnt_clk<=0;cnt_message<=1;t_start<=0;endendelse if (cnt_message>=1) begincnt_clk<=cnt_clk+1;if (cnt_clk==5208) begincnt_clk<=0;if (cnt_message==8) begintx<=1;t_start<=1;cnt_message<=0;endelse begintx<=message[cnt_message];cnt_message<=cnt_message+1;endendendelse begintx=1;endend
endmodule

4、测试模块

`timescale 1ps/1ps
module testbench (output reg clk,output reg tx,input rx,input [1:0] led
);reg [23:0]i;initialbeginclk=0;for(i=0;i<668900;i=i+1)#10   clk=~clk;endinitial begintx=1; #200000 tx=0; #104200 tx=1; #104200 tx=0; #104200 tx=1; #104200 tx=0; #104200 tx=1; #104200 tx=0; #104200 tx=1; #104200 tx=0; #104200 tx=1; #104200tx=0; #104200 tx=0; #104200 tx=1; #104200 tx=0; #104200 tx=1; #104200 tx=0; #104200 tx=1; #104200 tx=0; #104200 tx=0; #104200 tx=1; #104200tx=1;endbluetooth blue1(.sys_clk(clk),.tx(rx),.rx(tx),.led(led));
endmodule

5、仿真效果


一个小Tip,Add Waves之后课以通过这一排按钮重新加载波形:

FPGA的UART信息回显相关推荐

  1. 基于Springboot外卖系统16:菜品修改模块+菜品信息回显+ID查询口味列表+组装数据并返回

    4.1 菜品修改模块需求分析 在菜品管理列表页面点击修改按钮,跳转到修改菜品页面,在修改页面回显菜品相关信息并进行修改,最后点击确定按钮完成修改操作. 4.2 菜品修改模块前端页面(add.html) ...

  2. SpringMVC+HibernateValidator,配置在properties文件中的错误信息回显前端页面出现中文乱码

    问题: 后台在springMVC中使用hibernate-validator做参数校验的时候(validator具体使用方法见GOOGLE),用properties文件配置了校验失败的错误信息.发现回 ...

  3. 基于Springboot外卖系统17: 新增套餐模块+餐品信息回显+多数据表存储

    1.1 新增套餐需求分析 后台系统中可以管理套餐信息,通过新增套餐功能来添加一个新的套餐,在添加套餐时需要选择当前套餐所属的套餐分类和包含的菜品,并且需要上传套餐对应的图片,在移动端会按照套餐分类来展 ...

  4. SSM框架下对信息执行修改操作时的信息弹窗回显以及对信息修改后对数据库的更新问题

    SSM框架下对信息执行修改操作时的信息弹窗回显以及对信息修改后的同步问题 概括 主要说一下前端的实现 概括 今天在做实训作业时,有个对数据信息进行修改的操作,要求点击修改按钮后弹出修改框,栏目中需要显 ...

  5. 全志 修改485转CAN串口回显 Patch

    问题起因:平台:全志A40I 系统:Android6.0 IC:TJ1050 客户:XX项目主板 发送指令给 XX设备, 会收到设备回复 ,同时会收到回显的信息.主板测试 把串口和TJA1050这个芯 ...

  6. java回显怎么实现_Java实现简单的server/client回显功能

    Java实现简单的server/client回显功能 Socket是指在一个特定编程模型下,进程间通信链路的端点.因为这个特定编程模型的流行,Socket这个名字在其他领域得到了复用,包括Java叫技 ...

  7. php 错误关闭_五种方法教你如何关闭php错误回显信息

    有几种方法可以屏蔽错误回显信息: 1.php.ini的display_errors在php.ini文件中找到display_errors设置项,如果前面有分号,需要删去分号,并将值改为off 2.ph ...

  8. v-region 地址组件无法回显问题(选择地址保存后,打开编辑,发现刚才选择的地址【省市县乡】信息消失,信息不回显)

    (Avue) 1.问题 v-region 地址组件无法回显(选择地址保存后,打开编辑,发现刚才选择的地址[省市县乡]信息消失,信息不回显) 选择好省市县乡后,保存,再次编辑,发现如下: 2.解决方案: ...

  9. Android:登录保存回显用户信息或配置文件(sharedpreferences)

    登录保存回显用户信息或配置文件(sharedpreferences) 目录 登录保存回显用户信息或配置文件(sharedpreferences) 1.项目目录结构 二.类:MainActivity 三 ...

最新文章

  1. 会声会影x7 每次安装均会提示:已安装这个产品的另一个版本
  2. PAT甲级1081 Rational Sum:[C++题解]分数求和、辗转相除法求最大公约数、long long有一个数据溢出
  3. 搞懂C语言指针,看这篇就够了!
  4. 检查Red Hat JBoss BRMS部署架构的规则和事件(第二部分)
  5. oracle 10g冷备份恢复处理详细步骤
  6. android model 设计,Android model层设计
  7. 信息学奥赛C++语言:派送蛋糕
  8. STM32 ADC模数转换
  9. 通达信里的统计函数及区块背景函数
  10. DETR代码学习笔记(二)
  11. 向日葵远程控制软件——使用方法(含MacOS)
  12. excel数据正在计算机,excel数据太多表格太卡-急!Excel数据量大,电脑卡死?
  13. ptp精准时间协议_精确时间协议PTP研究
  14. 程序员如何利写代码用抖音帮助自己增加额外收入?
  15. 海思屏幕HAL代码解析
  16. 【PTA】到底是不是太胖了
  17. MPLS TE原理描述
  18. APNS证书制作问题
  19. 100个实用的 Linux Shell 脚本经典案例,收藏备用~
  20. 2.4G无线小模块CI24R1超低成本

热门文章

  1. 最佳实践 | 基于腾讯云ES如何跨地域容灾?跨集群复制为您解忧!
  2. Poj 2965 The Pilots Brothers‘ refrigerator
  3. Vue打包后出错:Tip: built files are meant to be served over an HTTP server. Opening index.html over file
  4. 接口技术课程设计——一种基于MFC构造自动测量系统
  5. 自然语言处理NLP星空智能对话机器人系列:深入理解Transformer自然语言处理 Standard NLP tasks with specific vocabulary
  6. 数据库的基本概念-基础(课堂笔记)
  7. Android实战技巧之八:Ubuntu下切换JDK版本
  8. 爬虫入门(一)——初识爬虫
  9. 【ASML】EUV光刻技术PPT
  10. 超级电容锂电池混合储能Simulink仿真