Merge pull request #476 from enjoy-digital/serv
Add SERV support (The SErial RISC-V CPU)
This commit is contained in:
commit
443cc72d0a
|
@ -37,17 +37,19 @@ from litex.soc.cores.cpu.minerva import Minerva
|
|||
from litex.soc.cores.cpu.rocket import RocketRV64
|
||||
from litex.soc.cores.cpu.microwatt import Microwatt
|
||||
from litex.soc.cores.cpu.blackparrot import BlackParrotRV64
|
||||
from litex.soc.cores.cpu.serv import SERV
|
||||
|
||||
CPUS = {
|
||||
"None" : CPUNone,
|
||||
"lm32" : LM32,
|
||||
"mor1kx" : MOR1KX,
|
||||
"picorv32" : PicoRV32,
|
||||
"vexriscv" : VexRiscv,
|
||||
"minerva" : Minerva,
|
||||
"rocket" : RocketRV64,
|
||||
"microwatt" : Microwatt,
|
||||
"None" : CPUNone,
|
||||
"lm32" : LM32,
|
||||
"mor1kx" : MOR1KX,
|
||||
"picorv32" : PicoRV32,
|
||||
"vexriscv" : VexRiscv,
|
||||
"minerva" : Minerva,
|
||||
"rocket" : RocketRV64,
|
||||
"microwatt" : Microwatt,
|
||||
"blackparrot" : BlackParrotRV64,
|
||||
"serv" : SERV
|
||||
}
|
||||
|
||||
# CPU Variants/Extensions Definition ---------------------------------------------------------------
|
||||
|
|
|
@ -0,0 +1 @@
|
|||
from litex.soc.cores.cpu.serv.core import SERV
|
|
@ -0,0 +1,91 @@
|
|||
# This file is Copyright (c) 2020 Florent Kermarrec <florent@enjoy-digital.fr>
|
||||
# This file is Copyright (c) 2020 Greg Davill <greg.davill@gmail.com>
|
||||
# License: BSD
|
||||
|
||||
import os
|
||||
|
||||
from migen import *
|
||||
|
||||
from litex.soc.interconnect import wishbone
|
||||
from litex.soc.cores.cpu import CPU
|
||||
|
||||
|
||||
CPU_VARIANTS = ["standard"]
|
||||
|
||||
|
||||
class SERV(CPU):
|
||||
name = "serv"
|
||||
data_width = 32
|
||||
endianness = "little"
|
||||
gcc_triple = ("riscv64-unknown-elf", "riscv32-unknown-elf", "riscv-none-embed",
|
||||
"riscv64-linux", "riscv-sifive-elf", "riscv64-none-elf")
|
||||
linker_output_format = "elf32-littleriscv"
|
||||
io_regions = {0x80000000: 0x80000000} # origin, length
|
||||
|
||||
@property
|
||||
def gcc_flags(self):
|
||||
flags = "-march=rv32i "
|
||||
flags += "-mabi=ilp32 "
|
||||
flags += "-D__serv__ "
|
||||
return flags
|
||||
|
||||
def __init__(self, platform, variant="standard"):
|
||||
assert variant in CPU_VARIANTS, "Unsupported variant %s" % variant
|
||||
self.platform = platform
|
||||
self.variant = variant
|
||||
self.reset = Signal()
|
||||
self.ibus = ibus = wishbone.Interface()
|
||||
self.dbus = dbus = wishbone.Interface()
|
||||
self.buses = [ibus, dbus]
|
||||
self.interrupt = Signal(32)
|
||||
|
||||
# # #
|
||||
|
||||
self.cpu_params = dict(
|
||||
# clock / reset
|
||||
i_clk = ClockSignal(),
|
||||
i_i_rst = ResetSignal() | self.reset,
|
||||
|
||||
# timer irq
|
||||
i_i_timer_irq = 0,
|
||||
|
||||
# ibus
|
||||
o_o_ibus_adr = Cat(Signal(2), ibus.adr),
|
||||
o_o_ibus_cyc = ibus.cyc,
|
||||
i_i_ibus_rdt = ibus.dat_r,
|
||||
i_i_ibus_ack = ibus.ack,
|
||||
|
||||
# dbus
|
||||
o_o_dbus_adr = Cat(Signal(2), dbus.adr),
|
||||
o_o_dbus_dat = dbus.dat_w,
|
||||
o_o_dbus_sel = dbus.sel,
|
||||
o_o_dbus_we = dbus.we,
|
||||
o_o_dbus_cyc = dbus.cyc,
|
||||
i_i_dbus_rdt = dbus.dat_r,
|
||||
i_i_dbus_ack = dbus.ack,
|
||||
)
|
||||
self.comb += [
|
||||
ibus.stb.eq(ibus.cyc),
|
||||
ibus.sel.eq(0xf),
|
||||
dbus.stb.eq(dbus.cyc),
|
||||
]
|
||||
|
||||
# add verilog sources
|
||||
self.add_sources(platform)
|
||||
|
||||
def set_reset_address(self, reset_address):
|
||||
assert not hasattr(self, "reset_address")
|
||||
self.reset_address = reset_address
|
||||
self.cpu_params.update(p_RESET_PC=reset_address)
|
||||
|
||||
@staticmethod
|
||||
def add_sources(platform):
|
||||
# FIXME: add SERV as submodule
|
||||
os.system("git clone https://github.com/olofk/serv")
|
||||
vdir = os.path.join("serv", "rtl")
|
||||
platform.add_source_dir(vdir)
|
||||
platform.add_verilog_include_path(vdir)
|
||||
|
||||
def do_finalize(self):
|
||||
assert hasattr(self, "reset_address")
|
||||
self.specials += Instance("serv_rf_top", **self.cpu_params)
|
|
@ -132,6 +132,9 @@ class SoCCore(LiteXSoC):
|
|||
self.cpu_type = cpu_type
|
||||
self.cpu_variant = cpu_variant
|
||||
|
||||
if cpu_type == "serv":
|
||||
self.add_constant("UART_POLLING") # FIXME: use UART in polling mode for SERV bringup
|
||||
|
||||
self.integrated_rom_size = integrated_rom_size
|
||||
self.integrated_rom_initialized = integrated_rom_init != []
|
||||
self.integrated_sram_size = integrated_sram_size
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
.section .text, "ax", @progbits
|
||||
.global boot_helper
|
||||
boot_helper:
|
||||
jr x13
|
|
@ -8,7 +8,7 @@
|
|||
#include <uart.h>
|
||||
#include <stdio.h>
|
||||
|
||||
|
||||
|
||||
#if defined(__blackparrot__) /*TODO: Update this function for BP*/ //
|
||||
|
||||
void isr(void);
|
||||
|
@ -21,7 +21,7 @@ void isr(void)
|
|||
onetime++;
|
||||
}
|
||||
}
|
||||
#elif defined(__rocket__)
|
||||
#elif defined(__rocket__)
|
||||
void plic_init(void);
|
||||
void plic_init(void)
|
||||
{
|
||||
|
@ -65,7 +65,7 @@ void isr(void)
|
|||
void isr(void);
|
||||
void isr(void)
|
||||
{
|
||||
unsigned int irqs;
|
||||
__attribute__((unused)) unsigned int irqs;
|
||||
|
||||
irqs = irq_pending() & irq_getmask();
|
||||
|
||||
|
|
|
@ -653,6 +653,8 @@ int main(int i, char **c)
|
|||
printf("RocketRV64[imac]");
|
||||
#elif __blackparrot__
|
||||
printf("BlackParrotRV64[ia]");
|
||||
#elif __serv__
|
||||
printf("SERV");
|
||||
#else
|
||||
printf("Unknown");
|
||||
#endif
|
||||
|
|
|
@ -48,6 +48,8 @@ __attribute__((unused)) static void cdelay(int i)
|
|||
__asm__ volatile("nop");
|
||||
#elif defined (__blackparrot__)
|
||||
__asm__ volatile("nop");
|
||||
#elif defined (__serv__)
|
||||
__asm__ volatile("nop");
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
|
|
@ -72,9 +72,11 @@ static inline unsigned int irq_getie(void)
|
|||
#elif defined (__rocket__)
|
||||
return (csrr(mstatus) & CSR_MSTATUS_MIE) != 0;
|
||||
#elif defined (__microwatt__)
|
||||
return 0; // FIXME
|
||||
#elif defined (__blackparrot__)
|
||||
return (csrr(mstatus) & CSR_MSTATUS_MIE) != 0;//TODO
|
||||
return 0; /* No interrupt support on Microwatt */
|
||||
#elif defined (__blackparrot__)
|
||||
return (csrr(mstatus) & CSR_MSTATUS_MIE) != 0; /* FIXME */
|
||||
#elif defined (__serv__)
|
||||
return 0; /* No interrupt support on SERV */
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
@ -101,9 +103,11 @@ static inline void irq_setie(unsigned int ie)
|
|||
#elif defined (__rocket__)
|
||||
if(ie) csrs(mstatus,CSR_MSTATUS_MIE); else csrc(mstatus,CSR_MSTATUS_MIE);
|
||||
#elif defined (__microwatt__)
|
||||
// FIXME
|
||||
/* No interrupt support on Microwatt */
|
||||
#elif defined (__blackparrot__)
|
||||
if(ie) csrs(mstatus,CSR_MSTATUS_MIE); else csrc(mstatus,CSR_MSTATUS_MIE);//TODO:BP
|
||||
if(ie) csrs(mstatus,CSR_MSTATUS_MIE); else csrc(mstatus,CSR_MSTATUS_MIE); /* FIXME */
|
||||
#elif defined (__serv__)
|
||||
/* No interrupt support on SERV */
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
@ -132,9 +136,11 @@ static inline unsigned int irq_getmask(void)
|
|||
#elif defined (__rocket__)
|
||||
return *((unsigned int *)PLIC_ENABLED) >> 1;
|
||||
#elif defined (__microwatt__)
|
||||
return 0; // FIXME
|
||||
return 0; /* No interrupt support on Microwatt */
|
||||
#elif defined (__blackparrot__)
|
||||
//TODO:BP
|
||||
return 0; /* FIXME */
|
||||
#elif defined (__serv__)
|
||||
return 0; /* No interrupt support on SERV */
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
@ -157,9 +163,11 @@ static inline void irq_setmask(unsigned int mask)
|
|||
#elif defined (__rocket__)
|
||||
*((unsigned int *)PLIC_ENABLED) = mask << 1;
|
||||
#elif defined (__microwatt__)
|
||||
// FIXME
|
||||
/* No interrupt support on Microwatt */
|
||||
#elif defined (__blackparrot__)
|
||||
//TODO:BP
|
||||
/* FIXME */
|
||||
#elif defined (__serv__)
|
||||
/* No interrupt support on SERV */
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
@ -186,9 +194,11 @@ static inline unsigned int irq_pending(void)
|
|||
#elif defined (__rocket__)
|
||||
return *((unsigned int *)PLIC_PENDING) >> 1;
|
||||
#elif defined (__microwatt__)
|
||||
return 0; // FIXME
|
||||
return 0; /* No interrupt support on Microwatt */
|
||||
#elif defined (__blackparrot__)
|
||||
return csr_readl(PLIC_PENDING) >> 1;//TODO:BP
|
||||
return csr_readl(PLIC_PENDING) >> 1; /* FIXME */
|
||||
#elif defined (__serv__)
|
||||
return 0; /* No interrupt support on SERV */
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
|
|
@ -0,0 +1,63 @@
|
|||
#define MIE_MEIE 0x800
|
||||
|
||||
.global _start
|
||||
_start:
|
||||
j reset_vector
|
||||
|
||||
reset_vector:
|
||||
la sp, _fstack
|
||||
la t0, trap_vector
|
||||
csrw mtvec, t0
|
||||
|
||||
// initialize .bss
|
||||
la t0, _fbss
|
||||
la t1, _ebss
|
||||
1: beq t0, t1, 2f
|
||||
sw zero, 0(t0)
|
||||
addi t0, t0, 4
|
||||
j 1b
|
||||
2:
|
||||
// enable external interrupts
|
||||
li t0, MIE_MEIE
|
||||
csrs mie, t0
|
||||
|
||||
call main
|
||||
1: j 1b
|
||||
|
||||
trap_vector:
|
||||
addi sp, sp, -16*4
|
||||
sw ra, 0*4(sp)
|
||||
sw t0, 1*4(sp)
|
||||
sw t1, 2*4(sp)
|
||||
sw t2, 3*4(sp)
|
||||
sw a0, 4*4(sp)
|
||||
sw a1, 5*4(sp)
|
||||
sw a2, 6*4(sp)
|
||||
sw a3, 7*4(sp)
|
||||
sw a4, 8*4(sp)
|
||||
sw a5, 9*4(sp)
|
||||
sw a6, 10*4(sp)
|
||||
sw a7, 11*4(sp)
|
||||
sw t3, 12*4(sp)
|
||||
sw t4, 13*4(sp)
|
||||
sw t5, 14*4(sp)
|
||||
sw t6, 15*4(sp)
|
||||
call isr
|
||||
lw ra, 0*4(sp)
|
||||
lw t0, 1*4(sp)
|
||||
lw t1, 2*4(sp)
|
||||
lw t2, 3*4(sp)
|
||||
lw a0, 4*4(sp)
|
||||
lw a1, 5*4(sp)
|
||||
lw a2, 6*4(sp)
|
||||
lw a3, 7*4(sp)
|
||||
lw a4, 8*4(sp)
|
||||
lw a5, 9*4(sp)
|
||||
lw a6, 10*4(sp)
|
||||
lw a7, 11*4(sp)
|
||||
lw t3, 12*4(sp)
|
||||
lw t4, 13*4(sp)
|
||||
lw t5, 14*4(sp)
|
||||
lw t6, 15*4(sp)
|
||||
addi sp, sp, 16*4
|
||||
mret
|
|
@ -62,6 +62,8 @@ void flush_cpu_icache(void)
|
|||
#elif defined (__blackparrot__)
|
||||
/* TODO: BP do something useful here! */
|
||||
asm volatile("nop");
|
||||
#elif defined (__serv__)
|
||||
/* no instruction cache */
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
@ -114,6 +116,8 @@ void flush_cpu_dcache(void)
|
|||
#elif defined (__blackparrot__)
|
||||
/* FIXME: do something useful here! */
|
||||
asm volatile("nop");
|
||||
#elif defined (__serv__)
|
||||
/* no data cache */
|
||||
#else
|
||||
#error Unsupported architecture
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue