Improve test firmware, increase testbench memory size to 128kB

Signed-off-by: Clifford Wolf <clifford@clifford.at>
This commit is contained in:
Clifford Wolf 2019-09-12 10:48:14 +02:00
parent 3bb692a954
commit 392ee1dd91
8 changed files with 132 additions and 16 deletions

View File

@ -4,7 +4,7 @@ RISCV_GNU_TOOLCHAIN_INSTALL_PREFIX = /opt/riscv32
SHELL = bash SHELL = bash
TEST_OBJS = $(addsuffix .o,$(basename $(wildcard tests/*.S))) TEST_OBJS = $(addsuffix .o,$(basename $(wildcard tests/*.S)))
FIRMWARE_OBJS = firmware/start.o firmware/irq.o firmware/print.o firmware/sieve.o firmware/multest.o firmware/stats.o FIRMWARE_OBJS = firmware/start.o firmware/irq.o firmware/print.o firmware/hello.o firmware/sieve.o firmware/multest.o firmware/stats.o
GCC_WARNS = -Werror -Wall -Wextra -Wshadow -Wundef -Wpointer-arith -Wcast-qual -Wcast-align -Wwrite-strings GCC_WARNS = -Werror -Wall -Wextra -Wshadow -Wundef -Wpointer-arith -Wcast-qual -Wcast-align -Wwrite-strings
GCC_WARNS += -Wredundant-decls -Wstrict-prototypes -Wmissing-prototypes -pedantic # -Wconversion GCC_WARNS += -Wredundant-decls -Wstrict-prototypes -Wmissing-prototypes -pedantic # -Wconversion
TOOLCHAIN_PREFIX = $(RISCV_GNU_TOOLCHAIN_INSTALL_PREFIX)i/bin/riscv32-unknown-elf- TOOLCHAIN_PREFIX = $(RISCV_GNU_TOOLCHAIN_INSTALL_PREFIX)i/bin/riscv32-unknown-elf-
@ -92,7 +92,7 @@ synth.v: picorv32.v scripts/yosys/synth_sim.ys
yosys -qv3 -l synth.log scripts/yosys/synth_sim.ys yosys -qv3 -l synth.log scripts/yosys/synth_sim.ys
firmware/firmware.hex: firmware/firmware.bin firmware/makehex.py firmware/firmware.hex: firmware/firmware.bin firmware/makehex.py
python3 firmware/makehex.py $< 16384 > $@ python3 firmware/makehex.py $< 32768 > $@
firmware/firmware.bin: firmware/firmware.elf firmware/firmware.bin: firmware/firmware.elf
$(TOOLCHAIN_PREFIX)objcopy -O binary $< $@ $(TOOLCHAIN_PREFIX)objcopy -O binary $< $@

View File

@ -20,6 +20,9 @@ void print_str(const char *p);
void print_dec(unsigned int val); void print_dec(unsigned int val);
void print_hex(unsigned int val, int digits); void print_hex(unsigned int val, int digits);
// hello.c
void hello(void);
// sieve.c // sieve.c
void sieve(void); void sieve(void);
@ -28,6 +31,10 @@ uint32_t hard_mul(uint32_t a, uint32_t b);
uint32_t hard_mulh(uint32_t a, uint32_t b); uint32_t hard_mulh(uint32_t a, uint32_t b);
uint32_t hard_mulhsu(uint32_t a, uint32_t b); uint32_t hard_mulhsu(uint32_t a, uint32_t b);
uint32_t hard_mulhu(uint32_t a, uint32_t b); uint32_t hard_mulhu(uint32_t a, uint32_t b);
uint32_t hard_div(uint32_t a, uint32_t b);
uint32_t hard_divu(uint32_t a, uint32_t b);
uint32_t hard_rem(uint32_t a, uint32_t b);
uint32_t hard_remu(uint32_t a, uint32_t b);
void multest(void); void multest(void);
// stats.c // stats.c

14
firmware/hello.c Normal file
View File

@ -0,0 +1,14 @@
// This is free and unencumbered software released into the public domain.
//
// Anyone is free to copy, modify, publish, use, compile, sell, or
// distribute this software, either in source code form or as a compiled
// binary, for any purpose, commercial or non-commercial, and by any
// means.
#include "firmware.h"
void hello(void)
{
print_str("hello world\n");
}

View File

@ -17,15 +17,35 @@ static uint32_t xorshift32(void) {
void multest(void) void multest(void)
{ {
for (int i = 0; i < 10; i++) for (int i = 0; i < 15; i++)
{ {
uint32_t a = xorshift32(); uint32_t a = xorshift32();
uint32_t b = xorshift32(); uint32_t b = xorshift32();
switch (i)
{
case 0:
a = 0x80000000;
b = 0xFFFFFFFF;
break;
case 1:
a = 0;
b = 0;
break;
case 2:
a |= 0x80000000;
b = 0;
break;
case 3:
a &= 0x7FFFFFFF;
b = 0;
break;
}
uint64_t au = a, bu = b; uint64_t au = a, bu = b;
int64_t as = (int32_t)a, bs = (int32_t)b; int64_t as = (int32_t)a, bs = (int32_t)b;
print_str("input ["); print_str("input [");
print_hex(as >> 32, 8); print_hex(as >> 32, 8);
print_str("] "); print_str("] ");
print_hex(a, 8); print_hex(a, 8);
@ -36,7 +56,7 @@ void multest(void)
print_chr('\n'); print_chr('\n');
uint32_t h_mul, h_mulh, h_mulhsu, h_mulhu; uint32_t h_mul, h_mulh, h_mulhsu, h_mulhu;
print_str("hard "); print_str("hard mul ");
h_mul = hard_mul(a, b); h_mul = hard_mul(a, b);
print_hex(h_mul, 8); print_hex(h_mul, 8);
@ -55,7 +75,7 @@ void multest(void)
print_chr('\n'); print_chr('\n');
uint32_t s_mul, s_mulh, s_mulhsu, s_mulhu; uint32_t s_mul, s_mulh, s_mulhsu, s_mulhu;
print_str("soft "); print_str("soft mul ");
s_mul = a * b; s_mul = a * b;
print_hex(s_mul, 8); print_hex(s_mul, 8);
@ -80,6 +100,52 @@ void multest(void)
} }
print_str(" OK\n"); print_str(" OK\n");
uint32_t h_div, h_divu, h_rem, h_remu;
print_str("hard div ");
h_div = hard_div(a, b);
print_hex(h_div, 8);
print_str(" ");
h_divu = hard_divu(a, b);
print_hex(h_divu, 8);
print_str(" ");
h_rem = hard_rem(a, b);
print_hex(h_rem, 8);
print_str(" ");
h_remu = hard_remu(a, b);
print_hex(h_remu, 8);
print_chr('\n');
uint32_t s_div, s_divu, s_rem, s_remu;
print_str("soft div ");
s_div = b ? as / bs : 0xffffffff;
print_hex(s_div, 8);
print_str(" ");
s_divu = b ? au / bu : 0xffffffff;
print_hex(s_divu, 8);
print_str(" ");
s_rem = b ? as % bs : a;
print_hex(s_rem, 8);
print_str(" ");
s_remu = b ? au % bu : a;
print_hex(s_remu, 8);
print_str(" ");
if (s_div != h_div || s_divu != h_divu || s_rem != h_rem || s_remu != h_remu) {
print_str("ERROR!\n");
__asm__ volatile ("ebreak");
return;
}
print_str(" OK\n");
} }
} }

View File

@ -8,9 +8,10 @@ means.
*/ */
MEMORY { MEMORY {
/* the memory in the testbench is 64k in size; /* the memory in the testbench is 128k in size;
* set LENGTH=48k and leave at least 16k for stack */ * set LENGTH=96k and leave at least 32k for stack */
mem : ORIGIN = 0x00000000, LENGTH = 0x0000c000 mem : ORIGIN = 0x00000000, LENGTH = 0x0000c000
mem : ORIGIN = 0x00000000, LENGTH = 0x00018000
} }
SECTIONS { SECTIONS {

View File

@ -6,6 +6,7 @@
// means. // means.
#define ENABLE_QREGS #define ENABLE_QREGS
#define ENABLE_HELLO
#define ENABLE_RVTST #define ENABLE_RVTST
#define ENABLE_SIEVE #define ENABLE_SIEVE
#define ENABLE_MULTST #define ENABLE_MULTST
@ -24,12 +25,17 @@
.section .text .section .text
.global irq .global irq
.global hello
.global sieve .global sieve
.global multest .global multest
.global hard_mul .global hard_mul
.global hard_mulh .global hard_mulh
.global hard_mulhsu .global hard_mulhsu
.global hard_mulhu .global hard_mulhu
.global hard_div
.global hard_divu
.global hard_rem
.global hard_remu
.global stats .global stats
reset_vec: reset_vec:
@ -372,6 +378,14 @@ start:
addi x30, zero, 0 addi x30, zero, 0
addi x31, zero, 0 addi x31, zero, 0
#ifdef ENABLE_HELLO
/* set stack pointer */
lui sp,(128*1024)>>12
/* call hello C code */
jal ra,hello
#endif
/* running tests from riscv-tests */ /* running tests from riscv-tests */
#ifdef ENABLE_RVTST #ifdef ENABLE_RVTST
@ -443,7 +457,7 @@ start:
TEST(simple) TEST(simple)
/* set stack pointer */ /* set stack pointer */
lui sp,(64*1024)>>12 lui sp,(128*1024)>>12
/* set gp and tp */ /* set gp and tp */
lui gp, %hi(0xdeadbeef) lui gp, %hi(0xdeadbeef)
@ -505,3 +519,19 @@ hard_mulhu:
mulhu a0, a0, a1 mulhu a0, a0, a1
ret ret
hard_div:
div a0, a0, a1
ret
hard_divu:
divu a0, a0, a1
ret
hard_rem:
rem a0, a0, a1
ret
hard_remu:
remu a0, a0, a1
ret

View File

@ -305,7 +305,7 @@ module axi4_memory #(
output reg tests_passed output reg tests_passed
); );
reg [31:0] memory [0:64*1024/4-1] /* verilator public */; reg [31:0] memory [0:128*1024/4-1] /* verilator public */;
reg verbose; reg verbose;
initial verbose = $test$plusargs("verbose") || VERBOSE; initial verbose = $test$plusargs("verbose") || VERBOSE;
@ -383,7 +383,7 @@ module axi4_memory #(
task handle_axi_rvalid; begin task handle_axi_rvalid; begin
if (verbose) if (verbose)
$display("RD: ADDR=%08x DATA=%08x%s", latched_raddr, memory[latched_raddr >> 2], latched_rinsn ? " INSN" : ""); $display("RD: ADDR=%08x DATA=%08x%s", latched_raddr, memory[latched_raddr >> 2], latched_rinsn ? " INSN" : "");
if (latched_raddr < 64*1024) begin if (latched_raddr < 128*1024) begin
mem_axi_rdata <= memory[latched_raddr >> 2]; mem_axi_rdata <= memory[latched_raddr >> 2];
mem_axi_rvalid <= 1; mem_axi_rvalid <= 1;
latched_raddr_en = 0; latched_raddr_en = 0;
@ -396,7 +396,7 @@ module axi4_memory #(
task handle_axi_bvalid; begin task handle_axi_bvalid; begin
if (verbose) if (verbose)
$display("WR: ADDR=%08x DATA=%08x STRB=%04b", latched_waddr, latched_wdata, latched_wstrb); $display("WR: ADDR=%08x DATA=%08x STRB=%04b", latched_waddr, latched_wdata, latched_wstrb);
if (latched_waddr < 64*1024) begin if (latched_waddr < 128*1024) begin
if (latched_wstrb[0]) memory[latched_waddr >> 2][ 7: 0] <= latched_wdata[ 7: 0]; if (latched_wstrb[0]) memory[latched_waddr >> 2][ 7: 0] <= latched_wdata[ 7: 0];
if (latched_wstrb[1]) memory[latched_waddr >> 2][15: 8] <= latched_wdata[15: 8]; if (latched_wstrb[1]) memory[latched_waddr >> 2][15: 8] <= latched_wdata[15: 8];
if (latched_wstrb[2]) memory[latched_waddr >> 2][23:16] <= latched_wdata[23:16]; if (latched_wstrb[2]) memory[latched_waddr >> 2][23:16] <= latched_wdata[23:16];

View File

@ -56,8 +56,6 @@ endmodule
`endif `endif
module picorv32_wrapper #( module picorv32_wrapper #(
parameter BOOTROM_MEMFILE = "",
parameter BOOTROM_MEMDEPTH = 16384 * 4,
parameter VERBOSE = 0 parameter VERBOSE = 0
) ( ) (
input wb_clk, input wb_clk,
@ -89,7 +87,7 @@ module picorv32_wrapper #(
wire wb_s2m_ack; wire wb_s2m_ack;
wb_ram #( wb_ram #(
.depth (16384 * 4), .depth (128*1024),
.VERBOSE (VERBOSE) .VERBOSE (VERBOSE)
) ram ( // Wishbone interface ) ram ( // Wishbone interface
.wb_clk_i(wb_clk), .wb_clk_i(wb_clk),
@ -266,7 +264,7 @@ module wb_ram #(
end end
always @(posedge wb_clk_i) begin always @(posedge wb_clk_i) begin
if (waddr2 < 64 * 1024 / 4) begin if (waddr2 < 128 * 1024 / 4) begin
if (we[0]) if (we[0])
mem[waddr2][7:0] <= wb_dat_i[7:0]; mem[waddr2][7:0] <= wb_dat_i[7:0];