diff --git a/litex/soc/cores/cpu/__init__.py b/litex/soc/cores/cpu/__init__.py index 244869b80..202f994ef 100644 --- a/litex/soc/cores/cpu/__init__.py +++ b/litex/soc/cores/cpu/__init__.py @@ -9,6 +9,7 @@ from litex.soc.cores.cpu.picorv32 import PicoRV32 from litex.soc.cores.cpu.vexriscv import VexRiscv from litex.soc.cores.cpu.minerva import Minerva from litex.soc.cores.cpu.rocket import RocketRV64 +from litex.soc.cores.cpu.serv import SERV # CPU Variants/Extensions Definition --------------------------------------------------------------- diff --git a/litex/soc/cores/cpu/serv/__init__.py b/litex/soc/cores/cpu/serv/__init__.py new file mode 100644 index 000000000..b46284ac8 --- /dev/null +++ b/litex/soc/cores/cpu/serv/__init__.py @@ -0,0 +1 @@ +from litex.soc.cores.cpu.serv.core import SERV diff --git a/litex/soc/cores/cpu/serv/core.py b/litex/soc/cores/cpu/serv/core.py new file mode 100644 index 000000000..0f9a2622c --- /dev/null +++ b/litex/soc/cores/cpu/serv/core.py @@ -0,0 +1,93 @@ +# This file is Copyright (c) 2019 Florent Kermarrec + +# License: BSD + +import os + +from migen import * + +from litex.soc.interconnect import wishbone + +CPU_VARIANTS = ["standard"] + + +class SERV(Module): + @property + def name(self): + return "serv" + + @property + def endianness(self): + return "little" + + @property + def gcc_triple(self): + return ("riscv64-unknown-elf", "riscv32-unknown-elf") + + @property + def gcc_flags(self): + flags = "-march=rv32i " + flags += "-mabi=ilp32 " + flags += "-D__serv__ " + return flags + + @property + def linker_output_format(self): + return "elf32-littleriscv" + + @property + def reserved_interrupts(self): + return {} + + def __init__(self, platform, cpu_reset_address, variant="standard"): + assert variant is "standard", "Unsupported variant %s" % variant + self.platform = platform + self.variant = variant + self.reset = Signal() + self.ibus = wishbone.Interface() + self.dbus = wishbone.Interface() + self.interrupt = Signal(32) + + # # # + + self.specials += Instance("serv_top", + p_RESET_PC=cpu_reset_address, + + # clock / reset + i_clk = ClockSignal(), + i_i_rst = ResetSignal(), + + # timer irq + i_i_timer_irq = 0, + + # ibus + o_o_ibus_adr = self.ibus.adr, + o_o_ibus_cyc = self.ibus.cyc, + i_i_ibus_rdt = self.ibus.dat_r, + i_i_ibus_ack = self.ibus.ack, + + + # dbus + o_o_dbus_adr = self.dbus.adr, + o_o_dbus_dat = self.dbus.dat_w, + o_o_dbus_sel = self.dbus.sel, + o_o_dbus_we = self.dbus.we, + o_o_dbus_cyc = self.dbus.cyc, + i_i_dbus_rdt = self.dbus.dat_r, + i_i_dbus_ack = self.dbus.ack, + ) + self.comb += [ + self.ibus.stb.eq(self.ibus.cyc), + self.dbus.stb.eq(self.dbus.cyc), + ] + + # add verilog sources + self.add_sources(platform) + + @staticmethod + def add_sources(platform): + vdir = os.path.join( + os.path.abspath(os.path.dirname(__file__)), + "verilog", "rtl") + platform.add_source_dir(vdir) + platform.add_verilog_include_path(vdir) diff --git a/litex/soc/integration/soc_core.py b/litex/soc/integration/soc_core.py index 48009791b..7a4c3980b 100644 --- a/litex/soc/integration/soc_core.py +++ b/litex/soc/integration/soc_core.py @@ -278,6 +278,8 @@ class SoCCore(Module): self.add_cpu(cpu.minerva.Minerva(platform, self.cpu_reset_address, self.cpu_variant)) elif cpu_type == "rocket": self.add_cpu(cpu.rocket.RocketRV64(platform, self.cpu_reset_address, self.cpu_variant)) + elif cpu_type == "serv": + self.add_cpu(cpu.serv.SERV(platform, self.cpu_reset_address, self.cpu_variant)) else: raise ValueError("Unsupported CPU type: {}".format(cpu_type)) diff --git a/litex/soc/software/bios/boot-helper-serv.S b/litex/soc/software/bios/boot-helper-serv.S new file mode 100644 index 000000000..e8bd5c760 --- /dev/null +++ b/litex/soc/software/bios/boot-helper-serv.S @@ -0,0 +1,4 @@ + .section .text, "ax", @progbits + .global boot_helper +boot_helper: + jr x13 diff --git a/litex/soc/software/bios/sdram.c b/litex/soc/software/bios/sdram.c index f0c12edfe..897c03d50 100644 --- a/litex/soc/software/bios/sdram.c +++ b/litex/soc/software/bios/sdram.c @@ -44,6 +44,8 @@ __attribute__((unused)) static void cdelay(int i) __asm__ volatile("nop"); #elif defined (__powerpc__) __asm__ volatile("nop"); +#elif defined (__serv__) + __asm__ volatile("nop"); #else #error Unsupported architecture #endif diff --git a/litex/soc/software/include/base/irq.h b/litex/soc/software/include/base/irq.h index 4bf6786c4..0a0766e83 100644 --- a/litex/soc/software/include/base/irq.h +++ b/litex/soc/software/include/base/irq.h @@ -56,6 +56,8 @@ static inline unsigned int irq_getie(void) return (csrr(mstatus) & CSR_MSTATUS_MIE) != 0; #elif defined (__rocket__) return (csrr(mstatus) & CSR_MSTATUS_MIE) != 0; +#elif defined (__serv__) + return 0; /* FIXME */ #else #error Unsupported architecture #endif @@ -81,6 +83,8 @@ static inline void irq_setie(unsigned int ie) if(ie) csrs(mstatus,CSR_MSTATUS_MIE); else csrc(mstatus,CSR_MSTATUS_MIE); #elif defined (__rocket__) if(ie) csrs(mstatus,CSR_MSTATUS_MIE); else csrc(mstatus,CSR_MSTATUS_MIE); +#elif defined (__serv__) + /* FIXME */ #else #error Unsupported architecture #endif @@ -108,6 +112,8 @@ static inline unsigned int irq_getmask(void) return mask; #elif defined (__rocket__) return csr_readl(PLIC_ENABLED) >> 1; +#elif defined (__serv__) + return 0; /* FIXME */ #else #error Unsupported architecture #endif @@ -129,6 +135,8 @@ static inline void irq_setmask(unsigned int mask) asm volatile ("csrw %0, %1" :: "i"(CSR_IRQ_MASK), "r"(mask)); #elif defined (__rocket__) csr_writel(mask << 1, PLIC_ENABLED); +#elif defined (__serv__) + /* FIXME */ #else #error Unsupported architecture #endif @@ -154,6 +162,8 @@ static inline unsigned int irq_pending(void) return pending; #elif defined (__rocket__) return csr_readl(PLIC_PENDING) >> 1; +#elif defined (__serv__) + return 0;/* FIXME */ #else #error Unsupported architecture #endif diff --git a/litex/soc/software/libbase/crt0-serv.S b/litex/soc/software/libbase/crt0-serv.S new file mode 100644 index 000000000..6f6e9e6c0 --- /dev/null +++ b/litex/soc/software/libbase/crt0-serv.S @@ -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 diff --git a/litex/soc/software/libbase/system.c b/litex/soc/software/libbase/system.c index bb15aad06..73e657785 100644 --- a/litex/soc/software/libbase/system.c +++ b/litex/soc/software/libbase/system.c @@ -56,6 +56,9 @@ void flush_cpu_icache(void) #elif defined (__rocket__) /* FIXME: do something useful here! */ asm volatile("nop"); +#elif defined (__serv__) + /* no instruction cache */ + asm volatile("nop"); #else #error Unsupported architecture #endif @@ -101,6 +104,9 @@ void flush_cpu_dcache(void) #elif defined (__rocket__) /* FIXME: do something useful here! */ asm volatile("nop"); +#elif defined (__serv__) + /* no data cache */ + asm volatile("nop"); #else #error Unsupported architecture #endif