summaryrefslogtreecommitdiff
path: root/bsp
diff options
context:
space:
mode:
authorPalmer Dabbelt <palmer@dabbelt.com>2018-06-29 16:14:00 -0700
committerPalmer Dabbelt <palmer@dabbelt.com>2018-06-29 16:15:05 -0700
commit66ba2aac4875e9131a630c29cea989551ac4cabd (patch)
tree2605f4e81388a0513e742829ad932a93be1935c2 /bsp
parent20541dcc0b415199bd87410aa05b8302f18edaf5 (diff)
Add a CLIC interrupt example
This example is fairly simple, but it does at least demonstrate how to use a C-based preemptable interrupt handler that's been registered in CLIC mode on a SiFive E21.
Diffstat (limited to 'bsp')
l---------bsp/env/coreplexip-e21-arty/dhrystone.lds1
l---------bsp/env/coreplexip-e21-arty/flash.lds1
l---------bsp/env/coreplexip-e21-arty/init.c1
l---------bsp/env/coreplexip-e21-arty/openocd.cfg1
l---------bsp/env/coreplexip-e21-arty/platform.h1
l---------bsp/env/coreplexip-e21-arty/scratchpad.lds1
l---------bsp/env/coreplexip-e21-arty/settings.mk1
-rw-r--r--bsp/env/coreplexip-e31-arty/init.c15
-rw-r--r--bsp/env/coreplexip-e31-arty/platform.h5
-rw-r--r--bsp/env/entry.S1
-rw-r--r--bsp/include/sifive/devices/clic.h49
11 files changed, 75 insertions, 2 deletions
diff --git a/bsp/env/coreplexip-e21-arty/dhrystone.lds b/bsp/env/coreplexip-e21-arty/dhrystone.lds
new file mode 120000
index 0000000..8459e13
--- /dev/null
+++ b/bsp/env/coreplexip-e21-arty/dhrystone.lds
@@ -0,0 +1 @@
+../coreplexip-e31-arty/dhrystone.lds \ No newline at end of file
diff --git a/bsp/env/coreplexip-e21-arty/flash.lds b/bsp/env/coreplexip-e21-arty/flash.lds
new file mode 120000
index 0000000..54c1026
--- /dev/null
+++ b/bsp/env/coreplexip-e21-arty/flash.lds
@@ -0,0 +1 @@
+../coreplexip-e31-arty/flash.lds \ No newline at end of file
diff --git a/bsp/env/coreplexip-e21-arty/init.c b/bsp/env/coreplexip-e21-arty/init.c
new file mode 120000
index 0000000..de048a9
--- /dev/null
+++ b/bsp/env/coreplexip-e21-arty/init.c
@@ -0,0 +1 @@
+../coreplexip-e31-arty/init.c \ No newline at end of file
diff --git a/bsp/env/coreplexip-e21-arty/openocd.cfg b/bsp/env/coreplexip-e21-arty/openocd.cfg
new file mode 120000
index 0000000..2f4de8d
--- /dev/null
+++ b/bsp/env/coreplexip-e21-arty/openocd.cfg
@@ -0,0 +1 @@
+../coreplexip-e31-arty/openocd.cfg \ No newline at end of file
diff --git a/bsp/env/coreplexip-e21-arty/platform.h b/bsp/env/coreplexip-e21-arty/platform.h
new file mode 120000
index 0000000..311ca36
--- /dev/null
+++ b/bsp/env/coreplexip-e21-arty/platform.h
@@ -0,0 +1 @@
+../coreplexip-e31-arty/platform.h \ No newline at end of file
diff --git a/bsp/env/coreplexip-e21-arty/scratchpad.lds b/bsp/env/coreplexip-e21-arty/scratchpad.lds
new file mode 120000
index 0000000..7fbe10a
--- /dev/null
+++ b/bsp/env/coreplexip-e21-arty/scratchpad.lds
@@ -0,0 +1 @@
+../coreplexip-e31-arty/scratchpad.lds \ No newline at end of file
diff --git a/bsp/env/coreplexip-e21-arty/settings.mk b/bsp/env/coreplexip-e21-arty/settings.mk
new file mode 120000
index 0000000..2b2a962
--- /dev/null
+++ b/bsp/env/coreplexip-e21-arty/settings.mk
@@ -0,0 +1 @@
+../coreplexip-e31-arty/settings.mk \ No newline at end of file
diff --git a/bsp/env/coreplexip-e31-arty/init.c b/bsp/env/coreplexip-e31-arty/init.c
index 409eeb4..1f8b679 100644
--- a/bsp/env/coreplexip-e31-arty/init.c
+++ b/bsp/env/coreplexip-e31-arty/init.c
@@ -64,6 +64,7 @@ extern my_interrupt_function_ptr_t localISR[];
#endif
#ifndef VECT_IRQ
+uintptr_t handle_trap(uintptr_t mcause, uintptr_t epc) __attribute__((noinline));
uintptr_t handle_trap(uintptr_t mcause, uintptr_t epc)
{
if (0){
@@ -90,6 +91,16 @@ uintptr_t handle_trap(uintptr_t mcause, uintptr_t epc)
}
#endif
+#ifdef USE_CLIC
+void trap_entry(void) __attribute__((interrupt("SiFive-CLIC-preemptible"), aligned(64)));
+void trap_entry(void)
+{
+ unsigned long mcause = read_csr(mcause);
+ unsigned long mepc = read_csr(mepc);
+ handle_trap(mcause, mepc);
+}
+#endif
+
void _init()
{
#ifndef NO_INIT
@@ -97,7 +108,11 @@ void _init()
puts("core freq at " STR(CPU_FREQ) " Hz\n");
+#ifdef USE_CLIC
+ write_csr(mtvec, ((unsigned long)&trap_entry | MTVEC_CLIC));
+#else
write_csr(mtvec, ((unsigned long)&TRAP_ENTRY | MTVEC_VECTORED));
+#endif
#endif
}
diff --git a/bsp/env/coreplexip-e31-arty/platform.h b/bsp/env/coreplexip-e31-arty/platform.h
index 0ac341e..6fa79ea 100644
--- a/bsp/env/coreplexip-e31-arty/platform.h
+++ b/bsp/env/coreplexip-e31-arty/platform.h
@@ -7,10 +7,10 @@
#if __riscv_xlen == 32
#define MCAUSE_INT 0x80000000UL
-#define MCAUSE_CAUSE 0x7FFFFFFFUL
+#define MCAUSE_CAUSE 0x000003FFUL
#else
#define MCAUSE_INT 0x8000000000000000UL
-#define MCAUSE_CAUSE 0x7FFFFFFFFFFFFFFFUL
+#define MCAUSE_CAUSE 0x00000000000003FFUL
#endif
#ifdef VECT_IRQ
@@ -18,6 +18,7 @@
#else
#define MTVEC_VECTORED 0x00
#endif
+#define MTVEC_CLIC 0x02
#define IRQ_M_LOCAL 16
#define MIP_MLIP(x) (1 << (IRQ_M_LOCAL + x))
diff --git a/bsp/env/entry.S b/bsp/env/entry.S
index 1f5de24..261b2a4 100644
--- a/bsp/env/entry.S
+++ b/bsp/env/entry.S
@@ -8,6 +8,7 @@
.section .text.entry
.align 2
+ .weak trap_entry
.global trap_entry
trap_entry:
addi sp, sp, -32*REGBYTES
diff --git a/bsp/include/sifive/devices/clic.h b/bsp/include/sifive/devices/clic.h
new file mode 100644
index 0000000..b31e1ce
--- /dev/null
+++ b/bsp/include/sifive/devices/clic.h
@@ -0,0 +1,49 @@
+// See LICENSE for license details.
+
+#ifndef _SIFIVE_CLIC_H
+#define _SIFIVE_CLIC_H
+
+#define CLIC_CTRL_ADDR _AC(0x2000000,UL)
+
+#define CLIC_MSIP 0x0000
+#define CLIC_MSIP_size 0x4
+#define CLIC_MTIMECMP 0x4000
+#define CLIC_MTIMECMP_size 0x8
+#define CLIC_MTIME 0xBFF8
+#define CLIC_MTIME_size 0x8
+
+#define CLIC_INTIP 0x0800000
+#define CLIC_INTIE 0x0800400
+#define CLIC_INTCFG 0x0800800
+#define CLIC_CFG 0x0800c00
+
+// These interrupt IDs are consistent across old and new mtvec modes
+#define SSIPID 1
+#define MSIPID 3
+#define STIPID 5
+#define MTIPID 7
+#define SEIPID 9
+#define MEIPID 11
+#define CSIPID 12
+#define LOCALINTIDBASE 16
+
+#define CLIC_REG(offset) _REG32(CLIC_CTRL_ADDR, offset)
+#define CLIC_REG8(offset) (*(volatile uint8_t *)((CLIC_CTRL_ADDR) + (offset)))
+
+#ifndef CLINT_CTRL_ADDR
+#define CLINT_CTRL_ADDR CLIC_CTRL_ADDR
+#endif
+#ifndef CLINT_REG
+#define CLINT_REG CLIC_REG
+#endif
+#ifndef CLINT_MSIP
+#define CLINT_MSIP CLIC_MSIP
+#endif
+#ifndef CLINT_MTIME
+#define CLINT_MTIME CLIC_MTIME
+#endif
+#ifndef CLINT_MTIMECMP
+#define CLINT_MTIMECMP CLIC_MTIMECMP
+#endif
+
+#endif /* _SIFIVE_CLIC_H */