基于FPGA自适应串口通信(Auto Baud Rate)
做的课设,相当于复习了一遍verilog。
实现了
1.接收端固定模式:8N1 BAUD:921600。
2.发送端8N1,任意波特率(不取极端值)。
3.数码管显示波特率(16进制)。
用了
1.两天一夜。
2.ego1平台+usb2uart。
整体框图

输入tx信号经过频率捕获层获得100Mhz下的计数值,送给波特率产生层得到接收层波特率。
接收层接收数据送给串口FIFO层,串口FIFO层根据发送层的反馈将数据送出FIFO。
发送层将数据按固定921600波特率发给PC机。从而实现波特率交换。
频率捕获层算法
1.uart协议

这里只考虑最常用的8N1,即8位数据,无校验,1位停止位。
在时钟线上升沿,tx线下降沿并维持到下一个上升沿即为一个开始位。然后8位数据(低位在前)。然后到第10位停止位高电平。
值得一提的是,tx线不会在某个电平完后恢复初始电平,比如说上一个数据位是低,当前位还是低,这个数据位结束后不会变回高再变低。
有什么影响?倘若tx发送0xff,那么其实只有一个低电平脉宽!即起始位那个脉宽。
2.算法
先打两拍,同步时钟以及滤除尖峰脉冲。考虑到输入的数据信号大多为ascii码。

我们从里面找一个最特殊的,U,这个字符二进制为10101010,再加上开始结束位的tx线电平变化为:
0101010101,这里有4个或者说5个低电平脉宽,这是最理想的情况。这样测出来的脉宽都是波特率。
但是如果是一般的字符,发送一个字节可能获得多个低电平脉宽,从里面找最小的有极大可能就是波特率(极小可能最小的低电平脉宽是波特率的倍数)。
所以我们的算法就是多次测频率,从里面找一个最小的,即认为是波特率。注意这里的频率,波特率都是相对于ego1的100Mhz时钟,并不需要化为实际波特率。
程序
`timescale 1ns / 1ps module cap_freqence(
input clk,
input rst_n,
input freq_in,
input cap_en,
output freq_cap//27bit 0-134,217,727 对输入信号波特率测得的频率
);
reg[:] freq_cap = 'd10416; //rst ??????
reg[:] tmp_cap,sequence_cap[:]; //cap 5 times and Use the smallest one as baud
reg [:] cap_cnt;
// reg cap_finish;
reg s0_RS_232_RX,s1_RS_232_RX; //同步寄存器,消除亚稳态
reg tmp0_RS_232_RX,tmp1_RS_232_RX; //数据寄存器,移位寄存器
reg cap_state; //0:idle 1:work
wire neg_RX;//下降沿
always@(posedge clk or negedge rst_n)//同步寄存器,消除亚稳态
if(!rst_n)
begin
s0_RS_232_RX <= 'b0;
s1_RS_232_RX <= 'b0;
end
else
begin
s0_RS_232_RX <= freq_in; //次态
s1_RS_232_RX <= s0_RS_232_RX;//现态
end
always@(posedge clk or negedge rst_n)//数据寄存器
if(!rst_n)
begin
tmp0_RS_232_RX <= 'b0;
tmp1_RS_232_RX <= 'b0;
end
else
begin
tmp0_RS_232_RX <= s1_RS_232_RX;
tmp1_RS_232_RX <= tmp0_RS_232_RX;
end
//共打两拍再检测输入脚
assign neg_RX = (!tmp0_RS_232_RX) & tmp1_RS_232_RX;//下降沿检测 always@(posedge clk or negedge rst_n)//cap工作状态
if(!rst_n)begin
cap_state <= ;
end
else if(neg_RX) //下降沿开始测频
cap_state <= ;
else if (tmp0_RS_232_RX) //高电平退出测频
cap_state <= ; always@(posedge clk or negedge rst_n)//以100Mhz时钟测输入引脚低电平脉宽
if(!rst_n)
begin
tmp_cap <= 'd0; end
else if(cap_state) //串口工作状态(接受)时计数
begin
if(tmp0_RS_232_RX) //计完一次频率
begin
sequence_cap[cap_cnt] <= tmp_cap;
tmp_cap <= 'd0;
cap_cnt <= cap_cnt + ;//0 1 2 3,4测完4次后为4
end
else
tmp_cap <= tmp_cap + 'b1;
end integer i;
reg[:] min_cap; always@(cap_cnt) //测完一个序列便从测频序列里找出最小脉宽即为bps
begin
if (cap_cnt == 'd5)
begin
min_cap=sequence_cap[];//1st one as minimal cap
for (i=;i<;i=i+)
if (sequence_cap[i] < min_cap)
if (sequence_cap[i] > )
min_cap = sequence_cap[i];
if (cap_en) //手动控制更新baud
freq_cap = min_cap;
end
end endmodule
这个程序有瑕疵,用了初始化。不懂
freq_cap
这个变量放在rst里面复位后,之后都不能被下面
freq_cap = min_cap;
这句更新,暂时这么写吧!
效果


基于FPGA自适应串口通信(Auto Baud Rate)的更多相关文章
- 012 基于FPGA的网口通信实例设计【转载】
一.网口通信设计分类 通过上面其他章节的介绍,网口千兆通信,可以使用TCP或者UDP协议,可以外挂PHY片或者不挂PHY片,总结下来就有下面几种方式完成通信: 图8‑17基于FPGA的网口通信实例设计 ...
- 【Delphi】基于状态机的串口通信
通信协议 串行通信接口(如RS232.RS485等)作为计算机与单片机交互数据的主要接口,广泛用于各类仪器仪表.工业监测及自动控制领域中. 通信协议是需要通信的双方所达成的一种约定,它对包括数据格式. ...
- 基于FPGA的光口通信开发案例|基于Kintex-7 FPGA SFP+光口的10G UDP网络通信开发案例
前言 自著名华人物理学家高锟先生提出"光传输理论",实用化的光纤传输产品始于1976年,经历了PDH→SDH→DWDM→ASON→MSTP的发展历程.本世纪初期,ASON/OADM ...
- 纠错:基于FPGA串口发送彩色图片数据至VGA显示
今天这篇文章是要修改之前的一个错误,前面我写过一篇基于FPGA的串口发送图片数据至VGA显示的文章,最后是显示成功了,但是显示的效果图,看起来确实灰度图,当时我默认我使用的MATLAB代码将图片数据转 ...
- QT5 TK1 串口通信
对TK1中基于QT5的串口通信过程进行总结.按照软件安装及通信实现的顺序. 1.QT5安装 较简洁方式:打开软件中心(类似A形),搜索qtcreator,点击安装即可. 2.串口通信库安装 采用上述方 ...
- 基于FPGA的红外遥控解码与PC串口通信
基于FPGA的红外遥控解码与PC串口通信 zouxy09@qq.com http://blog.csdn.net/zouxy09 这是我的<电子设计EDA>的课程设计作业(呵呵,这个月都拿 ...
- [python] 3 、基于串口通信的嵌入式设备上位机自动测试程序框架(简陋框架)
星期一, 20. 八月 2018 01:53上午 - beautifulzzzz 1.前言 做类似zigbee.ble mesh...无线网络节点性能测试的时候,手动操作然后看表象往往很难找出真正的原 ...
- PC和FPGA间的串口通信实现
应用笔记 V1.0 2015/03/26 PC和FPGA间的串口通信实现 概述 本文将介绍PC和FPGA间的串口通信实现的基本思路和Verilog代码,对于通信而言,收发双方都要有相应的控制. ...
- VS2008基于对话框的MFC上位机串口通信(C++实现)简单例程
首先,在 vs2008 环境下创建 MFC 运用程序 设置项目名称为 ComTest(这个地方随意命名,根据个人习惯),点击确定后,点击下一步 出现如下界面 选择"基于对话框"模式 ...
随机推荐
- LeetCode 674. 最长连续递增序列(Longest Continuous Increasing Subsequence) 18
674. 最长连续递增序列 674. Longest Continuous Increasing Subsequence 题目描述 给定一个未经排序的整型数组,找到最长且连续的递增序列. Given ...
- win10改装win7
参考链接: https://jingyan.baidu.com/article/3ea51489d0f3c852e61bba01.html 1. 制作win7 U盘启动盘 2. 设置BIOS 1:OS ...
- todo----mysql常用语句总结补充完成
todo----mysql常用语句总结补充完成
- React项目使用Redux
⒈创建React项目 初始化一个React项目(TypeScript环境) ⒉React集成React-Router React项目使用React-Router ⒊React集成Redux Redux ...
- WUSTOJ 1333: Sequential game(Java)
题目链接:1333: Sequential game Description Sequential detector is a very important device in Hardware ex ...
- pandas之时间序列笔记
时间戳tiimestamp:固定的时刻->pd.Timestamp 固定时期period:比如2016年3月份,再如2015年销售额->pd.Period 时间间隔interval:由起始 ...
- Linux 进程控制
分享知乎上看到的一句话,共勉: 学习周期分为学习,思考,实践,校正四个阶段,周期越短,学习效率越高. 前面讲的都是操作系统如何管理进程,接下来,看看用户如何进行进程控制. 1.进程创建 先介绍一下函数 ...
- 使用UltraISO制作Centos7 U盘启动盘遇到的坑
下载.安装UltraISO软件 安装好以后,打开软件 击菜单栏的"文件"选项,再点击"打开"按钮,选择要刻录的系统镜像 点击菜单栏的"启动" ...
- lock的等效代码
1.lock的等效代码 在.NET的多线程程序中,经常会遇到lock关键字来控制同步,比如下列代码: private object o = new object(); public void Work ...
- C#方法(用法,参数)
方法:是一种用于实现可以由对象或类执行的计算或操作的成员,是一个已命名的语句集.方法就是把一些相关的语句组织到一起,用来执行一个任务的语句块.比如每个C#程序至少带一个main函数 1.格式:修饰符 ...