思维分析图
rom模块的代码逻辑
`timescale 1ns / 1ps
module rom_2(
input sys_clk ,
input sys_rst_n ,
input tx_done ,
output [7:0] rom_data ,//输出给tx
output reg rom_done //一个8bit数据输出的结束信号
);
reg [3:0] cnt;
reg ena ;
reg [7: 0] addra ;
reg flag;
reg [3:0] cnt_done;//计数tx——done
always@(posedge sys_clk)
if(!sys_rst_n)
cnt<=0;
else if(cnt==10)
cnt<=cnt;
else
cnt<=cnt+1;
//
always@(posedge sys_clk)
if(!sys_rst_n)
flag<=0;
else if(cnt==9)
flag<=1;
else
flag<=0;
//cnt_done计数tx_done的次数
always@(posedge sys_clk)
if(!sys_rst_n)
cnt_done<=0;
else if(tx_done)begin
if(cnt_done==9)
cnt_done<=cnt_done;
else
cnt_done<=cnt_done+1;
end
else
cnt_done<=cnt_done;
//
always@(posedge sys_clk)
if(!sys_rst_n)
rom_done<=0;
else if(flag)
rom_done<=1;
else if(tx_done && cnt_done<9)
rom_done<=1;
else if(tx_done && cnt_done==9)
rom_done<=0;
else
rom_done<=0;
//
always@(posedge sys_clk)
if(!sys_rst_n)
ena<=0;
else
ena<=1;
always@(posedge sys_clk)
if(!sys_rst_n)
addra<=0;
else if(tx_done)begin
if(addra==9)
addra<=addra;
else
addra<=addra+1;
end
else
addra<=addra;
rom_ten your_instance_name (
.clka(sys_clk), // input wire clka
.ena(ena), // input wire ena
.addra(addra), // input wire [7: 0] addra
.douta(rom_data) // output wire [7 : 0] douta
);
endmodule
tx端口模块
`timescale 1ns / 1ps
module tx(
input sysclk ,
input rst_n ,
input [7:0] data ,//数据并行输入
input done ,//tx的开始信号
output tx ,//数据输出--串行输出
output tx_done
);
parameter clk = 50_000_000,//1s内部时钟晶振次数
bps = 9600,//波特率
CNT_MAX = clk/bps;//传输一个Bit需要的时间周期
reg [31:0] cnt_bps;//传输一个bit需要的计时器
reg [3:0] cnt_bit;//bit位计数器,看传输到第几个bit
reg en;//工作时间阈值(包装数据--->tx)
reg [7:0] data_reg;//输入数据寄存器
reg tx_reg;
reg done_d1 =0;
always@(posedge sysclk)begin
done_d1<=done;
end
//en工作阈值
always@(posedge sysclk)
if(!rst_n)
en<=0;
else if(done==1)
en<=1;
else if(cnt_bit==9 && cnt_bps==CNT_MAX-1)
en<=0;
else
en<=en;
//输入数据寄存模块
always@(posedge sysclk)
if(!rst_n)
data_reg<=0;
else if(done_d1)//开始工作时就寄存并行输入的data
data_reg<=data;
else
data_reg<=data_reg;
//cnt_bps-->包装一个bit需要的时间计时器
always@(posedge sysclk )
if(!rst_n)
cnt_bps<=0;
else if(en==1)begin
if(cnt_bps==CNT_MAX-1)
cnt_bps<=0;
else
cnt_bps<=cnt_bps+1;
end
else
cnt_bps<=0;
//cnt_bit-->表示包装到了哪一个Bit--bie位计数器
always@(posedge sysclk )
if(!rst_n)
cnt_bit<=0;
else if(en==1)begin
if(cnt_bps==CNT_MAX-1)
cnt_bit<=cnt_bit+1;
else
cnt_bit<=cnt_bit;
end
else
cnt_bit<=0;
//tx_reg-->表示开始包装数据(数据包装流水线)
always@(posedge sysclk )
if(!rst_n)
tx_reg<=1;//空闲,不需要打包数据
else if(en==1)begin
if(cnt_bit==0)//包装起始位
tx_reg<=0;
else if(cnt_bit==9)//包装停止位
tx_reg<=1;
else
tx_reg<=data_reg[cnt_bit-1];//数据串行包装(由低位开始)
end
else
tx_reg<=1;
assign tx = tx_reg;
assign tx_done = (cnt_bit==9&&cnt_bps==CNT_MAX-1)?1:0;
endmodule
顶层模块
`timescale 1ns / 1ps
module top(
input sysclk ,
input rst_n ,
output tx //数据输出--串行输出
);
wire done ;//tx的开始信号
wire tx_done ;
wire [7:0] rom_data;
rom_2 u(
. sys_clk ( sysclk ) ,
. sys_rst_n ( rst_n) ,
. tx_done ( tx_done ) ,
. rom_data ( rom_data ) ,//输出给tx
. rom_done ( done ) //一个8bit数据输出的结束信号
);
tx tx_u(
. sysclk ( sysclk ) ,
. rst_n ( rst_n ) ,
. data ( rom_data ) ,//数据并行输入
. done ( done ) ,//tx的开始信号
. tx ( tx ) ,//数据输出--串行输出
. tx_done ( tx_done )
);
endmodule