名称:RS232接口数据发送UART串口协议Verilog代码Quartus仿真(文末获取)
软件:Quartus
语言:Verilog
代码功能:
设计RS232接口数据转发协议,将8位并行数据转发为RS232协
议的串口数据发送出去。
entity rs232
port(clk: in std_ logic;--16MHz输入时钟
rdy: in std logic;-数据准备好信号,1个时钟周期的正脉冲data: in std logic vecton(7 downto0);--要发送的并行数据bps: in std logic_ vector( I downto0):--波特率设置
00:9600bps01:1920010:38400
d_out: out std_ logic);-串行数据输出
end rs232.
协议要求
(1)波特率:9600/19200/38400可选2)8位数据位,1为停止位,偶校验设计要求:
(1)采用VHDL或 Verilog语言设计上述电路;2)写出测试激励文件,并仿真;
(3)分析仿真结果,并撰写设计报告
(4)提交完整的电子版设计报告并附源代码
1. 工程文件
2. 程序文件
3. 程序编译
4. Testbench
5. 仿真图
部分代码展示:
module rs232( input clk, //系统时钟16MHz input rst_n, //系统复位,低电平有效 input rdy, //数据准备好信号,1时钟周期正脉冲 input [7:0] data, //待发送并行数据 input [1:0] bps, //波特率设置,00:9600bps 01:19200 10:38400 output reg d_out //串行数据输出 ); //parameter define parameter CLK_FREQ = 16000000; //系统时钟频率16MHz reg [31:0] UART_BPS = 9600; //串口波特率 always @(posedge clk or negedge rst_n) if (!rst_n) UART_BPS<=9600; else case(bps) 2'b00:UART_BPS<=9600;//9600bps 2'b01:UART_BPS<=19200;//19200bps 2'b10:UART_BPS<=38400;//38400bps default:; endcase wire [31:0] BPS_CNT;//为得到指定波特率,对系统时钟计数BPS_CNT次 assign BPS_CNT = CLK_FREQ/UART_BPS; //为得到指定波特率,对系统时钟计数BPS_CNT次 //reg define reg uart_en_d0; reg uart_en_d1; reg [15:0] clk_cnt; //系统时钟计数器 reg [ 3:0] tx_cnt; //发送数据计数器 reg tx_flag; //发送过程标志信号 reg [ 7:0] tx_data; //寄存发送数据 //wire define wire en_flag; //***************************************************** //** main code //***************************************************** //捕获uart_en上升沿,得到一个时钟周期的脉冲信号 assign en_flag = (~uart_en_d1) & uart_en_d0; //对发送使能信号uart_en延迟两个时钟周期 always @(posedge clk or negedge rst_n) begin if (!rst_n) begin uart_en_d0 <= 1'b0; uart_en_d1 <= 1'b0; end else begin uart_en_d0 <= rdy; uart_en_d1 <= uart_en_d0; end end //当脉冲信号en_flag到达时,寄存待发送的数据,并进入发送过程 always @(posedge clk or negedge rst_n) begin if (!rst_n) begin tx_flag <= 1'b0; tx_data <= 8'd0; end else if (en_flag) begin //检测到发送使能上升沿 tx_flag <= 1'b1; //进入发送过程,标志位tx_flag拉高 tx_data <= data; //寄存待发送的数据 end else if ((tx_cnt == 4'd10)&&(clk_cnt == BPS_CNT/2)) begin //计数到停止位中间时,停止发送过程 tx_flag <= 1'b0; //发送过程结束,标志位tx_flag拉低 tx_data <= 8'd0; end else begin tx_flag <= tx_flag; tx_data <= tx_data; end end //进入发送过程后,启动系统时钟计数器与发送数据计数器 always @(posedge clk or negedge rst_n) begin if (!rst_n) begin clk_cnt <= 16'd0; tx_cnt <= 4'd0; end else if (tx_flag) begin //处于发送过程 if (clk_cnt < BPS_CNT - 1) begin clk_cnt <= clk_cnt + 1'b1; tx_cnt <= tx_cnt; end else begin clk_cnt <= 16'd0; //对系统时钟计数达一个波特率周期后清零 tx_cnt <= tx_cnt + 1'b1; //此时发送数据计数器加1 end end else begin //发送过程结束 clk_cnt <= 16'd0; tx_cnt <= 4'd0; end
源代码
扫描文章末尾的公众号二维码