blob: 1b54548979f215380af12e4a5293b9493c99426d [file] [log] [blame]
/*
* Usage:
* iverilog test_uart.v ../rtl/uart.v ../rtl/uart_rx.v ../rtl/uart_tx.v -o test_uart.out
* ./test_uart.out
* gtkwave test_uart.vcd [test_uart.gtkw]
*/
`timescale 1 ns / 1 ps
module test_uart;
// Testbench uses a 48 MHz clock
// Want to interface to 115200 baud UART
// 10000000 / 115200 = 87 Clocks Per Bit.
parameter c_CLOCK_MHZ = 48;
parameter c_UART_SPEED = 115200;
parameter c_CLOCK_PERIOD_NS = 1000/c_CLOCK_MHZ;
parameter c_CLKS_PER_BIT = c_CLOCK_MHZ*1000000/c_UART_SPEED;
parameter c_CLKS_PER_BYTE = (c_CLKS_PER_BIT+7)/8;
parameter c_BIT_PERIOD = c_CLKS_PER_BIT*c_CLOCK_PERIOD_NS;
integer i;
integer j;
reg [15:0] prescale = c_CLKS_PER_BYTE;
reg clk = 0;
reg rst = 0;
// Inputs
reg m_axis_tready = 0;
reg rxd = 1;
// Outputs
wire [7:0] m_axis_tdata;
wire m_axis_tvalid;
wire rx_busy;
wire rx_overrun_error;
wire rx_frame_error;
// Inputs
reg [7:0] s_axis_tdata = 8'd0;
reg s_axis_tvalid = 1'b0;
reg [9:0] r_Tx_Data = 0;
// Outputs
wire s_axis_tready;
wire txd;
wire tx_busy;
// Write a byte to RX pin
task UART_WRITE_RX_AND_RCV;
input [7:0] i_Data;
integer ii;
begin
m_axis_tready <= 1;
// Write Start Bit
#(c_BIT_PERIOD) rxd <= 1'b0;
// Write Data
for (ii=0; ii<8; ii=ii+1)
begin
#(c_BIT_PERIOD) rxd <= i_Data[ii];
end
// Write Stop Bit
#(c_BIT_PERIOD) rxd <= 1'b1;
@(posedge m_axis_tvalid);
end
endtask
// Send a byte and read back data from TX pin
task UART_SEND_AND_READ_TX;
output [9:0] o_Data;
integer ii;
begin
// Send byte
@(posedge clk);
s_axis_tvalid <= 1'b1;
@(posedge clk);
s_axis_tvalid <= 1'b0;
@(posedge tx_busy);
// Read Data
for (ii=0; ii<10; ii=ii+1)
begin
#(c_BIT_PERIOD) o_Data[ii] <= txd;
end
@(posedge s_axis_tready);
end
endtask
always
#(c_CLOCK_PERIOD_NS/2) clk <= !clk;
initial begin
$dumpfile("test_uart.vcd");
$dumpvars(0, test_uart);
// Exercise Rx
j=0;
for (i=0; i<256; i=i+1)
begin
UART_WRITE_RX_AND_RCV(i);
if (m_axis_tdata == i)
j=j+1;
else
$display("RX Test Failed - Incorrect Byte Received");
end
if (j == 256)
$display("RX Test Passed - Correct Bytes Received");
// Exercise Tx
j=0;
for (i=0; i<256; i=i+1)
begin
s_axis_tdata <= i;
UART_SEND_AND_READ_TX(r_Tx_Data);
// Check that the correct byte was sent
if (r_Tx_Data[8:1] == i)
j=j+1;
else
$display("TX Test Failed - Incorrect Byte Sent");
end
if (j == 256)
$display("TX Test Passed - Correct Bytes Sent");
$finish;
end
uart #(
.DATA_WIDTH(8)
)
UUT (
.clk(clk),
.rst(rst),
// axi output
.m_axis_tdata(m_axis_tdata),
.m_axis_tvalid(m_axis_tvalid),
.m_axis_tready(m_axis_tready),
// input
.rxd(rxd),
// status
.rx_busy(rx_busy),
.rx_overrun_error(rx_overrun_error),
.rx_frame_error(rx_frame_error),
// axi input
.s_axis_tdata(s_axis_tdata),
.s_axis_tvalid(s_axis_tvalid),
.s_axis_tready(s_axis_tready),
// output
.txd(txd),
// status
.tx_busy(tx_busy),
// configuration
.prescale(prescale)
);
endmodule