FPGA模拟串口自收发-Verilog

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

实现功能,FPGA 里实现从PC 串口接收数据,接着把接收到的数据发回去。波特率可选 9600bps,可调1bit 起始位,8bit 数据,1bit 停止位,无校验位。

参考《VHDL 硬件描述语言与和数字逻辑电路设计》

模块介绍如下

一、串口数据接收模块: 特别注意一个数据位占 4个clk_bps_4时钟周期。

串口数据接收控制

当数据接收端rxd 出现起始位低电平,启动接收控制计数器rx_cnt,置位为 8' b0111_00(28),

即 rx_cnt[5:2]

== 4 ' b0111(7),rx_cnt[1:0]

== 2'b00(0); —个计数周期开始,伴随

clk_bps_4, rx_cnt 加1 (每一个数据位加 4) 串口接收数据移位控制(关键采样点的选取)

每当rx_cnt[1:0] == 2'b01, 为了保证在 rxd 一位数据靠近中间位置采样;每 4个 clk_bps_4, rx_cnt[5:2] 力口 1 当 rx_cnt[5:2] == 8,9,10

….15,完成 8 位的数据采样,

串并变换

置位标志位rxdF 数据接收标志

rxd 出现起始位低电平,rxdF 置1 ,表示数据接收开始;当rx_cnt 计数到

rxd

flk reser

r

do hich

F

1 fr

'豔

K

/ tt

/ L J

L

--

X

rdbLLL

CLK RESET

I r

rpset

|

EMPTY

8'b1111_11( 63), 数据接收完成,rxdF 置0

置位标志位rdFULL; 5,完成一位起始位,8 位的数据位发送,随后txd 置1(停止位),完成并串转换

置位标志位txdF ,tdEMPTY st_n(rst_n),

.clk_bps_4(clk_bps_4),

.wr(wr),

.tdEMPTY(tdEMPTY),

.DATA(DATA),

.txd(txd)

);st_n(rst_n),

.clk_bps_4(clk_bps_4),

.rd(rd),

.rdFULL(rdFULL),

.do_latch(do_latch),

.rxd(rxd)

);

/* 针对9600bps ,生成的时钟信号,用于接收数据采样与数据发送*/ Baudrate baud(.clk(clk),

.rst_n(rst_n), .clk_bps_4(clk_bps_4));

Endmodule

串口数据接收模块:

module Uart_RX(rst_n, clk_bps_4, rd, rdFULL, do_latch, rxd);

input rst_n; // 低电平复位

input clk_bps_4; //4 倍于波特率时钟信号即一个数据位占4 个时钟周期

input rd;// 接收使能, 低电平有效

output reg[7:0] do_latch;// 接收数据锁存

output reg rdFULL;// 接收锁存器满标志

input rxd;// 串口引脚输入

reg[7:0] data_r = 8'bx; // 接收数据寄存器

reg[5:0] rx_cnt;

reg rxdF;// 数据接收标志,RX模块内部信号

/* 当数据接收端rxd 出现起始位低电平,启动接收控制计数器rx_cnt, 置位为b0111_00(28),

8'即rx_cnt[5:2]== 4 'b0111(7),rx_cnt[1:0] == 2'b00(0);

一个计数周期开始,伴随clk_bps_4, rx_cnt 加1(每一个数据位加4) */ always@(posedge

clk_bps_4 or negedge rst_n)

begin

if(!rst_n)

begin rx_cnt <= 0; end

else if(rx_cnt <= 27 && rxd == 0)

begin rx_cnt <= 28; end

else if(rx_cnt <= 27 && rxd == 1)// 串口无数据时,rx_cnt 保持0 begin rx_cnt <= 0;

end

else

begin rx_cnt <= rx_cnt + 1;end

end

/* 空闲时rdFULL 置0,当数据接收完成,数据锁存到do_latch,

同时rdFULL置1,向上层模块表示数据以准备0K可以来读取;

rd 置0, 表示上层模块开始读取数据,rdFULL 置0,表示数据已读走*/ always@(posedge

clk_bps_4 or negedge rst_n)// 置位标志位rdFULL begin

if(!rst_n)

begin rdFULL <= 0; end

else if(rd == 0)

begin rdFULL <= 0; end

else if(rxdF == 1 && rx_cnt == 63)

begin

do_latch <= data_r;// 数据锁存

rdFULL <= 1;// 锁存器数据准备0K

end

end

/*rxd 出现起始位低电平, rxdF 置1 ,表示数据接收开始;

当rx_cnt计数到8' b1111_11(63),数据接收完成,rxdF置0* always@(posedge clk_bps_4 or negedge rst_n)// 置位标志位rxdF

相关文档
最新文档