Add support for testcase return code propagation to rvcpp.
Hook up mtvec in bitmanip testcases to exit sim when exception taken.
This commit is contained in:
parent
32f65fb142
commit
e1bb341876
|
@ -19,7 +19,7 @@ define make-test-target
|
||||||
$(CROSS_PREFIX)objdump -d tmp/$1.elf >> tmp/$1.dis
|
$(CROSS_PREFIX)objdump -d tmp/$1.elf >> tmp/$1.dis
|
||||||
$(CROSS_PREFIX)objdump -j .testdata -d tmp/$1.elf >> tmp/$1.dis
|
$(CROSS_PREFIX)objdump -j .testdata -d tmp/$1.elf >> tmp/$1.dis
|
||||||
$(CROSS_PREFIX)objcopy -O binary tmp/$1.elf tmp/$1.bin
|
$(CROSS_PREFIX)objcopy -O binary tmp/$1.elf tmp/$1.bin
|
||||||
$(SIM_EXEC) --bin tmp/$1.bin --vcd tmp/$1.vcd --dump 0x400000 0x410000 > tmp/$1.log
|
$(SIM_EXEC) --cpuret --bin tmp/$1.bin --vcd tmp/$1.vcd --dump 0x400000 0x410000 > tmp/$1.log
|
||||||
../riscv-compliance/compare_testvec tmp/$1.log reference/$1.reference_output
|
../riscv-compliance/compare_testvec tmp/$1.log reference/$1.reference_output
|
||||||
endef
|
endef
|
||||||
|
|
||||||
|
|
|
@ -11,6 +11,7 @@ ENTRY(_start)
|
||||||
SECTIONS
|
SECTIONS
|
||||||
{
|
{
|
||||||
.text : {
|
.text : {
|
||||||
|
KEEP(*(.vectors))
|
||||||
. = ORIGIN(RAM) + 0x40;
|
. = ORIGIN(RAM) + 0x40;
|
||||||
PROVIDE (_start = .);
|
PROVIDE (_start = .);
|
||||||
*(.text*)
|
*(.text*)
|
||||||
|
|
|
@ -76,10 +76,20 @@ prolog = """
|
||||||
#define IO_PRINT_U32 (IO_BASE + 0x4)
|
#define IO_PRINT_U32 (IO_BASE + 0x4)
|
||||||
#define IO_EXIT (IO_BASE + 0x8)
|
#define IO_EXIT (IO_BASE + 0x8)
|
||||||
|
|
||||||
|
.section .vectors
|
||||||
|
__initial_mtvec:
|
||||||
|
li a0, IO_EXIT
|
||||||
|
li a1, -1
|
||||||
|
sw a1, (a0)
|
||||||
|
|
||||||
.section .text
|
.section .text
|
||||||
|
|
||||||
.global _start
|
.global _start
|
||||||
_start:
|
_start:
|
||||||
|
// Should be the initial value anyways, but just make sure:
|
||||||
|
la a0, __initial_mtvec
|
||||||
|
csrw mtvec, a0
|
||||||
|
|
||||||
la sp, test_signature_start
|
la sp, test_signature_start
|
||||||
|
|
||||||
"""
|
"""
|
||||||
|
|
|
@ -871,6 +871,8 @@ const char *help_str =
|
||||||
" --dump start end : Print out memory contents between start and end (exclusive)\n"
|
" --dump start end : Print out memory contents between start and end (exclusive)\n"
|
||||||
" after execution finishes. Can be passed multiple times.\n"
|
" after execution finishes. Can be passed multiple times.\n"
|
||||||
" --cycles n : Maximum number of cycles to run before exiting.\n"
|
" --cycles n : Maximum number of cycles to run before exiting.\n"
|
||||||
|
" --cpuret : Testbench's return code is the return code written to\n"
|
||||||
|
" IO_EXIT by the CPU, or -1 if timed out.\n"
|
||||||
" --memsize n : Memory size in units of 1024 bytes, default is 16 MB\n"
|
" --memsize n : Memory size in units of 1024 bytes, default is 16 MB\n"
|
||||||
" --trace : Print out execution tracing info\n"
|
" --trace : Print out execution tracing info\n"
|
||||||
;
|
;
|
||||||
|
@ -890,6 +892,7 @@ int main(int argc, char **argv) {
|
||||||
bool load_bin = false;
|
bool load_bin = false;
|
||||||
std::string bin_path;
|
std::string bin_path;
|
||||||
bool trace_execution = false;
|
bool trace_execution = false;
|
||||||
|
bool propagate_return_code = false;
|
||||||
|
|
||||||
for (int i = 1; i < argc; ++i) {
|
for (int i = 1; i < argc; ++i) {
|
||||||
std::string s(argv[i]);
|
std::string s(argv[i]);
|
||||||
|
@ -930,6 +933,9 @@ int main(int argc, char **argv) {
|
||||||
else if (s == "--trace") {
|
else if (s == "--trace") {
|
||||||
trace_execution = true;
|
trace_execution = true;
|
||||||
}
|
}
|
||||||
|
else if (s == "--cpuret") {
|
||||||
|
propagate_return_code = true;
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
std::cerr << "Unrecognised argument " << s << "\n";
|
std::cerr << "Unrecognised argument " << s << "\n";
|
||||||
exit_help("");
|
exit_help("");
|
||||||
|
@ -956,13 +962,18 @@ int main(int argc, char **argv) {
|
||||||
RVCore core;
|
RVCore core;
|
||||||
|
|
||||||
int64_t cyc;
|
int64_t cyc;
|
||||||
|
int rc = 0;
|
||||||
try {
|
try {
|
||||||
for (cyc = 0; cyc < max_cycles; ++cyc)
|
for (cyc = 0; cyc < max_cycles; ++cyc)
|
||||||
core.step(mem, trace_execution);
|
core.step(mem, trace_execution);
|
||||||
|
if (propagate_return_code)
|
||||||
|
rc = -1;
|
||||||
}
|
}
|
||||||
catch (TBExitException e) {
|
catch (TBExitException e) {
|
||||||
printf("CPU requested halt. Exit code %d\n", e.exitcode);
|
printf("CPU requested halt. Exit code %d\n", e.exitcode);
|
||||||
printf("Ran for %ld cycles\n", cyc + 1);
|
printf("Ran for %ld cycles\n", cyc + 1);
|
||||||
|
if (propagate_return_code)
|
||||||
|
rc = e.exitcode;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (auto [start, end] : dump_ranges) {
|
for (auto [start, end] : dump_ranges) {
|
||||||
|
@ -972,5 +983,5 @@ int main(int argc, char **argv) {
|
||||||
printf("\n");
|
printf("\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue