Add uriscv/tb.

This commit is contained in:
colin.liang 2023-01-07 16:14:56 +08:00
parent 5fb3787307
commit c2e4068c8a
9 changed files with 845854 additions and 0 deletions

4444
uriscv/tb/build/output.out Executable file

File diff suppressed because it is too large Load Diff

BIN
uriscv/tb/build/tcm.bin Executable file

Binary file not shown.

104
uriscv/tb/gtksettings.sav Normal file
View File

@ -0,0 +1,104 @@
[*]
[*] GTKWave Analyzer v3.3.86 (w)1999-2017 BSI
[*] Sat Jul 17 10:54:57 2021
[*]
[timestart] 0
[size] 2560 1385
[pos] -1 -1
*-14.000000 146555 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
[treeopen] tb_top.
[treeopen] tb_top.u_dut.
[sst_width] 202
[signals_width] 245
[sst_expanded] 1
[sst_vpaned_height] 420
@28
tb_top.u_dut.clk_i
tb_top.u_dut.rst_i
@200
-
@800200
-MEM_I
@200
-REQ
@28
tb_top.u_dut.mem_i_rd_o
@22
tb_top.u_dut.mem_i_pc_o[31:0]
@28
tb_top.u_dut.mem_i_accept_i
@200
-RESP
@28
tb_top.u_dut.mem_i_valid_i
@22
tb_top.u_dut.mem_i_inst_i[31:0]
@1000200
-MEM_I
@200
-
@800200
-MEM_D
@200
-REQ
@28
tb_top.u_dut.mem_d_rd_o
@22
tb_top.u_dut.mem_d_wr_o[3:0]
tb_top.u_dut.mem_d_addr_o[31:0]
tb_top.u_dut.mem_d_data_wr_o[31:0]
@28
tb_top.u_dut.mem_d_accept_i
@200
-RESP
@28
tb_top.u_dut.mem_d_ack_i
@22
tb_top.u_dut.mem_d_data_rd_i[31:0]
@1000200
-MEM_D
@200
-
@23
tb_top.u_dut.pc_q[31:0]
@200
-
@800200
-REGFILE
@22
tb_top.u_dut.x0_zero_w[31:0]
tb_top.u_dut.x1_ra_w[31:0]
tb_top.u_dut.x2_sp_w[31:0]
tb_top.u_dut.x3_gp_w[31:0]
tb_top.u_dut.x4_tp_w[31:0]
tb_top.u_dut.x5_t0_w[31:0]
tb_top.u_dut.x6_t1_w[31:0]
tb_top.u_dut.x7_t2_w[31:0]
tb_top.u_dut.x8_s0_w[31:0]
tb_top.u_dut.x9_s1_w[31:0]
tb_top.u_dut.x10_a0_w[31:0]
tb_top.u_dut.x11_a1_w[31:0]
tb_top.u_dut.x12_a2_w[31:0]
tb_top.u_dut.x13_a3_w[31:0]
tb_top.u_dut.x14_a4_w[31:0]
tb_top.u_dut.x15_a5_w[31:0]
tb_top.u_dut.x16_a6_w[31:0]
tb_top.u_dut.x17_a7_w[31:0]
tb_top.u_dut.x18_s2_w[31:0]
tb_top.u_dut.x19_s3_w[31:0]
tb_top.u_dut.x20_s4_w[31:0]
tb_top.u_dut.x21_s5_w[31:0]
tb_top.u_dut.x22_s6_w[31:0]
tb_top.u_dut.x23_s7_w[31:0]
tb_top.u_dut.x24_s8_w[31:0]
tb_top.u_dut.x25_s9_w[31:0]
tb_top.u_dut.x26_s10_w[31:0]
tb_top.u_dut.x27_s11_w[31:0]
tb_top.u_dut.x28_t3_w[31:0]
tb_top.u_dut.x29_t4_w[31:0]
tb_top.u_dut.x30_t5_w[31:0]
tb_top.u_dut.x31_t6_w[31:0]
@1000200
-REGFILE
[pattern_trace] 1
[pattern_trace] 0

62
uriscv/tb/makefile Normal file
View File

@ -0,0 +1,62 @@
###############################################################################
# Variables: Program ELF
###############################################################################
ELF_FILE ?= test.elf
OBJCOPY ?= /opt/riscv/bin/riscv32-unknown-elf-objcopy
ifeq ($(shell which $(OBJCOPY)),)
${error $(OBJCOPY) missing from PATH}
endif
ifeq ($(shell which iverilog),)
${error iverilog missing from PATH - Icarus Verilog required}
endif
###############################################################################
# Variables: Defaults
###############################################################################
TRACE ?= 1
SRC_V_DIR ?= ../src .
SRC_DIR ?= .
EXE ?= output.out
###############################################################################
# Variables: Verilog
###############################################################################
SRC_V ?= $(foreach src,$(SRC_V_DIR),$(wildcard $(src)/*.v))
VFLAGS += $(patsubst %,-I%,$(SRC_V_DIR))
VFLAGS += -DTRACE=$(TRACE)
VFLAGS += -Dverilog_sim
###############################################################################
# Variables: Lists of objects, source and deps
###############################################################################
BUILD_DIR ?= build/
###############################################################################
# Rules
###############################################################################
all: run
$(BUILD_DIR):
@mkdir -p $@
$(BUILD_DIR)/tcm.bin: $(ELF_FILE) | $(BUILD_DIR)
$(OBJCOPY) $< -O binary $@
$(BUILD_DIR)/$(EXE): $(SRC_V) | $(BUILD_DIR)
@echo "# Compiling verilog"
iverilog $(VFLAGS) -o $@ $(SRC_V)
run: $(BUILD_DIR)/$(EXE) $(BUILD_DIR)/tcm.bin
vvp $(BUILD_DIR)/$(EXE) -vcd
view:
gtkwave waveform.vcd gtksettings.sav
clean:
rm -rf $(BUILD_DIR) *.vcd

137
uriscv/tb/tb_top.v Normal file
View File

@ -0,0 +1,137 @@
module tb_top;
reg clk;
reg rst;
reg [7:0] mem[65535:0];
integer i;
integer f;
initial
begin
$display("Starting bench");
if (`TRACE)
begin
$dumpfile("waveform.vcd");
$dumpvars(0, tb_top);
end
// Reset
clk = 0;
rst = 1;
repeat (5) @(posedge clk);
rst = 0;
// Load TCM memory
for (i=0;i<65535;i=i+1)
mem[i] = 0;
f = $fopenr("./build/tcm.bin");
i = $fread(mem, f);
for (i=0;i<65535;i=i+1)
u_mem.write(i, mem[i]);
end
initial
begin
forever
begin
clk = #5 ~clk;
end
end
wire mem_i_rd_w;
wire mem_i_flush_w;
wire mem_i_invalidate_w;
wire [ 31:0] mem_i_pc_w;
wire [ 31:0] mem_d_addr_w;
wire [ 31:0] mem_d_data_wr_w;
wire mem_d_rd_w;
wire [ 3:0] mem_d_wr_w;
wire mem_d_cacheable_w;
wire [ 10:0] mem_d_req_tag_w;
wire mem_d_invalidate_w;
wire mem_d_writeback_w;
wire mem_d_flush_w;
wire mem_i_accept_w;
wire mem_i_valid_w;
wire mem_i_error_w;
wire [ 31:0] mem_i_inst_w;
wire [ 31:0] mem_d_data_rd_w;
wire mem_d_accept_w;
wire mem_d_ack_w;
wire mem_d_error_w;
wire [ 10:0] mem_d_resp_tag_w;
riscv_core
u_dut
//-----------------------------------------------------------------
// Ports
//-----------------------------------------------------------------
(
// Inputs
.clk_i(clk)
,.rst_i(rst)
,.mem_d_data_rd_i(mem_d_data_rd_w)
,.mem_d_accept_i(mem_d_accept_w)
,.mem_d_ack_i(mem_d_ack_w)
,.mem_d_error_i(mem_d_error_w)
,.mem_d_resp_tag_i(mem_d_resp_tag_w)
,.mem_i_accept_i(mem_i_accept_w)
,.mem_i_valid_i(mem_i_valid_w)
,.mem_i_error_i(mem_i_error_w)
,.mem_i_inst_i(mem_i_inst_w)
,.intr_i(1'b0)
,.reset_vector_i(32'h80000000)
,.cpu_id_i('b0)
// Outputs
,.mem_d_addr_o(mem_d_addr_w)
,.mem_d_data_wr_o(mem_d_data_wr_w)
,.mem_d_rd_o(mem_d_rd_w)
,.mem_d_wr_o(mem_d_wr_w)
,.mem_d_cacheable_o(mem_d_cacheable_w)
,.mem_d_req_tag_o(mem_d_req_tag_w)
,.mem_d_invalidate_o(mem_d_invalidate_w)
,.mem_d_writeback_o(mem_d_writeback_w)
,.mem_d_flush_o(mem_d_flush_w)
,.mem_i_rd_o(mem_i_rd_w)
,.mem_i_flush_o(mem_i_flush_w)
,.mem_i_invalidate_o(mem_i_invalidate_w)
,.mem_i_pc_o(mem_i_pc_w)
);
tcm_mem
u_mem
(
// Inputs
.clk_i(clk)
,.rst_i(rst)
,.mem_i_rd_i(mem_i_rd_w)
,.mem_i_flush_i(mem_i_flush_w)
,.mem_i_invalidate_i(mem_i_invalidate_w)
,.mem_i_pc_i(mem_i_pc_w)
,.mem_d_addr_i(mem_d_addr_w)
,.mem_d_data_wr_i(mem_d_data_wr_w)
,.mem_d_rd_i(mem_d_rd_w)
,.mem_d_wr_i(mem_d_wr_w)
,.mem_d_cacheable_i(mem_d_cacheable_w)
,.mem_d_req_tag_i(mem_d_req_tag_w)
,.mem_d_invalidate_i(mem_d_invalidate_w)
,.mem_d_writeback_i(mem_d_writeback_w)
,.mem_d_flush_i(mem_d_flush_w)
// Outputs
,.mem_i_accept_o(mem_i_accept_w)
,.mem_i_valid_o(mem_i_valid_w)
,.mem_i_error_o(mem_i_error_w)
,.mem_i_inst_o(mem_i_inst_w)
,.mem_d_data_rd_o(mem_d_data_rd_w)
,.mem_d_accept_o(mem_d_accept_w)
,.mem_d_ack_o(mem_d_ack_w)
,.mem_d_error_o(mem_d_error_w)
,.mem_d_resp_tag_o(mem_d_resp_tag_w)
);
endmodule

120
uriscv/tb/tcm_mem.v Normal file
View File

@ -0,0 +1,120 @@
module tcm_mem
(
// Inputs
input clk_i
,input rst_i
,input mem_i_rd_i
,input mem_i_flush_i
,input mem_i_invalidate_i
,input [ 31:0] mem_i_pc_i
,input [ 31:0] mem_d_addr_i
,input [ 31:0] mem_d_data_wr_i
,input mem_d_rd_i
,input [ 3:0] mem_d_wr_i
,input mem_d_cacheable_i
,input [ 10:0] mem_d_req_tag_i
,input mem_d_invalidate_i
,input mem_d_writeback_i
,input mem_d_flush_i
// Outputs
,output mem_i_accept_o
,output mem_i_valid_o
,output mem_i_error_o
,output [ 31:0] mem_i_inst_o
,output [ 31:0] mem_d_data_rd_o
,output mem_d_accept_o
,output mem_d_ack_o
,output mem_d_error_o
,output [ 10:0] mem_d_resp_tag_o
);
//-------------------------------------------------------------
// Dual Port RAM
//-------------------------------------------------------------
wire [31:0] data_r_w;
tcm_mem_ram
u_ram
(
// Instruction fetch
.clk0_i(clk_i)
,.rst0_i(rst_i)
,.addr0_i(mem_i_pc_i[15:2])
,.data0_i(32'b0)
,.wr0_i(4'b0)
// External access / Data access
,.clk1_i(clk_i)
,.rst1_i(rst_i)
,.addr1_i(mem_d_addr_i[15:2])
,.data1_i(mem_d_data_wr_i)
,.wr1_i(mem_d_wr_i)
// Outputs
,.data0_o(mem_i_inst_o)
,.data1_o(data_r_w)
);
//-------------------------------------------------------------
// Instruction Fetch
//-------------------------------------------------------------
reg mem_i_valid_q;
always @ (posedge clk_i )
if (rst_i)
mem_i_valid_q <= 1'b0;
else
mem_i_valid_q <= mem_i_rd_i;
assign mem_i_accept_o = 1'b1;
assign mem_i_valid_o = mem_i_valid_q;
assign mem_i_error_o = 1'b0;
//-------------------------------------------------------------
// Data Access / Incoming external access
//-------------------------------------------------------------
reg mem_d_accept_q;
reg mem_d_ack_q;
reg [10:0] mem_d_tag_q;
always @ (posedge clk_i )
if (rst_i)
begin
mem_d_ack_q <= 1'b0;
mem_d_tag_q <= 11'b0;
end
else if ((mem_d_rd_i || mem_d_wr_i != 4'b0 || mem_d_flush_i || mem_d_invalidate_i || mem_d_writeback_i) && mem_d_accept_o)
begin
mem_d_ack_q <= 1'b1;
mem_d_tag_q <= mem_d_req_tag_i;
end
else
mem_d_ack_q <= 1'b0;
assign mem_d_ack_o = mem_d_ack_q;
assign mem_d_resp_tag_o = mem_d_tag_q;
assign mem_d_data_rd_o = data_r_w;
assign mem_d_error_o = 1'b0;
assign mem_d_accept_o = 1'b1;
//-------------------------------------------------------------
// write: Write byte into memory
//-------------------------------------------------------------
task write; /*verilator public*/
input [31:0] addr;
input [7:0] data;
begin
case (addr[1:0])
2'd0: u_ram.ram[addr/4][7:0] = data;
2'd1: u_ram.ram[addr/4][15:8] = data;
2'd2: u_ram.ram[addr/4][23:16] = data;
2'd3: u_ram.ram[addr/4][31:24] = data;
endcase
end
endtask
endmodule

69
uriscv/tb/tcm_mem_ram.v Normal file
View File

@ -0,0 +1,69 @@
module tcm_mem_ram
(
// Inputs
input clk0_i
,input rst0_i
,input [ 13:0] addr0_i
,input [ 31:0] data0_i
,input [ 3:0] wr0_i
,input clk1_i
,input rst1_i
,input [ 13:0] addr1_i
,input [ 31:0] data1_i
,input [ 3:0] wr1_i
// Outputs
,output [ 31:0] data0_o
,output [ 31:0] data1_o
);
//-----------------------------------------------------------------
// Dual Port RAM 64KB
// Mode: Read First
//-----------------------------------------------------------------
/* verilator lint_off MULTIDRIVEN */
reg [31:0] ram [16383:0] /*verilator public*/;
/* verilator lint_on MULTIDRIVEN */
reg [31:0] ram_read0_q;
reg [31:0] ram_read1_q;
// Synchronous write
always @ (posedge clk0_i)
begin
if (wr0_i[0])
ram[addr0_i][7:0] <= data0_i[7:0];
if (wr0_i[1])
ram[addr0_i][15:8] <= data0_i[15:8];
if (wr0_i[2])
ram[addr0_i][23:16] <= data0_i[23:16];
if (wr0_i[3])
ram[addr0_i][31:24] <= data0_i[31:24];
ram_read0_q <= ram[addr0_i];
end
always @ (posedge clk1_i)
begin
if (wr1_i[0])
ram[addr1_i][7:0] <= data1_i[7:0];
if (wr1_i[1])
ram[addr1_i][15:8] <= data1_i[15:8];
if (wr1_i[2])
ram[addr1_i][23:16] <= data1_i[23:16];
if (wr1_i[3])
ram[addr1_i][31:24] <= data1_i[31:24];
ram_read1_q <= ram[addr1_i];
end
assign data0_o = ram_read0_q;
assign data1_o = ram_read1_q;
endmodule

BIN
uriscv/tb/test.elf Executable file

Binary file not shown.

840918
uriscv/tb/waveform.vcd Normal file

File diff suppressed because it is too large Load Diff