summaryrefslogtreecommitdiff
path: root/libcpu
diff options
context:
space:
mode:
authorBernard Xiong <[email protected]>2020-09-22 22:03:26 +0800
committerGitHub <[email protected]>2020-09-22 22:03:26 +0800
commitd92fbba3c1dfd304b377da2d6d48e317c10fc3c4 (patch)
tree3a6f0539b28286f5721c4b5d7d482fd4a7fea4b4 /libcpu
parent8302a7224302c0624b9918855a25e12f3a3ede59 (diff)
parent60287b69fdff377ea9fdfd2f06b4ea3f6f34e32a (diff)
Merge pull request #3919 from wormsX/T-head_Smart-v1.0.0
add t-head smart-evb bsp, and risc-v cpu e906
Diffstat (limited to 'libcpu')
-rw-r--r--libcpu/risc-v/SConscript13
-rw-r--r--libcpu/risc-v/t-head/e906/SConscript12
-rw-r--r--libcpu/risc-v/t-head/e906/context_gcc.S323
-rw-r--r--libcpu/risc-v/t-head/e906/cpuport.c170
-rw-r--r--libcpu/risc-v/t-head/e906/cpuport.h55
5 files changed, 570 insertions, 3 deletions
diff --git a/libcpu/risc-v/SConscript b/libcpu/risc-v/SConscript
index 024cc5ba44..5055b533e6 100644
--- a/libcpu/risc-v/SConscript
+++ b/libcpu/risc-v/SConscript
@@ -10,10 +10,17 @@ group = []
list = os.listdir(cwd)
# add common code files
-if rtconfig.CPU != "nuclei":
- group = group + SConscript(os.path.join('common', 'SConscript'))
+if rtconfig.VENDOR == "t-head" :
+ group = group
+elif rtconfig.CPU == "nuclei" :
+ group = group
+else :
+ group = group + SConscript(os.path.join(cwd, 'common', 'SConscript'))
# cpu porting code files
-group = group + SConscript(os.path.join(rtconfig.CPU, 'SConscript'))
+if rtconfig.VENDOR == "t-head" :
+ group = group + SConscript(os.path.join(cwd, rtconfig.VENDOR, rtconfig.CPU, 'SConscript'))
+else :
+ group = group + SConscript(os.path.join(cwd, rtconfig.CPU, 'SConscript'))
Return('group')
diff --git a/libcpu/risc-v/t-head/e906/SConscript b/libcpu/risc-v/t-head/e906/SConscript
new file mode 100644
index 0000000000..2f698f530a
--- /dev/null
+++ b/libcpu/risc-v/t-head/e906/SConscript
@@ -0,0 +1,12 @@
+# RT-Thread building script for component
+
+from building import *
+
+cwd = GetCurrentDir()
+src = Glob('*.c') + Glob('*.cpp') + Glob('*_gcc.S')
+CPPPATH = [cwd]
+ASFLAGS = ''
+
+group = DefineGroup('cpu', src, depend = [''], CPPPATH = CPPPATH, ASFLAGS = ASFLAGS)
+
+Return('group')
diff --git a/libcpu/risc-v/t-head/e906/context_gcc.S b/libcpu/risc-v/t-head/e906/context_gcc.S
new file mode 100644
index 0000000000..2f5223ae63
--- /dev/null
+++ b/libcpu/risc-v/t-head/e906/context_gcc.S
@@ -0,0 +1,323 @@
+/*
+ * Copyright (c) 2006-2018, RT-Thread Development Team
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2020/08/20 zx.chen The T-HEAD RISC-V CPU E906 porting implementation
+ */
+
+#include "cpuport.h"
+
+#ifdef RT_USING_SMP
+#define rt_hw_interrupt_disable rt_hw_local_irq_disable
+#define rt_hw_interrupt_enable rt_hw_local_irq_enable
+#endif
+
+/*
+ * Functions: vPortYield
+ */
+.global vPortYield
+.type vPortYield, %function
+vPortYield:
+ li t0, 0xE080100C
+ lb t1, (t0)
+ li t2, 0x01
+ or t1, t1, t2
+ sb t1, (t0)
+
+ ret
+
+
+
+/*
+ * #ifdef RT_USING_SMP
+ * void rt_hw_context_switch_to(rt_ubase_t to, stuct rt_thread *to_thread);
+ * #else
+ * void rt_hw_context_switch_to(rt_ubase_t to);
+ * #endif
+ * a0 --> to
+ * a1 --> to_thread
+ */
+ .globl rt_hw_context_switch_to
+rt_hw_context_switch_to:
+ /* save a0 to to_thread */
+ la t0, rt_interrupt_to_thread
+ STORE a0, (t0)
+
+ /* save 0 to from_thread */
+ la t0, rt_interrupt_from_thread
+ li t1, 0
+ STORE t1, (t0)
+
+ /* set rt_thread_switch_interrupt_flag=1 */
+ la t0, rt_thread_switch_interrupt_flag
+ li t1, 1
+ STORE t1, (t0)
+
+ /* enable mexstatus SPUSHEN and SPSWAPEN */
+#if ((CONFIG_CPU_E906==1) || (CONFIG_CPU_E906F==1) || (CONFIG_CPU_E906FD==1))
+ uint32_t mexstatus;
+ mexstatus = __get_MEXSTATUS();
+ mexstatus |= (0x2 << 16);
+ __set_MEXSTATUS(mexstatus);
+#endif
+
+ csrw mscratch, sp
+ /* set software interrupt */
+ li t0, 0xE080100C
+ lb t1, (t0)
+ li t2, 0x01
+ or t1, t1, t2
+ sb t1, (t0)
+
+ /* enable global interrup */
+ csrsi mstatus, 8
+
+ ret
+
+/*
+ * #ifdef RT_USING_SMP
+ * void rt_hw_context_switch(rt_ubase_t from, rt_ubase_t to, struct rt_thread *to_thread);
+ * #else
+ * void rt_hw_context_switch(rt_ubase_t from, rt_ubase_t to);
+ * #endif
+ *
+ * a0 --> from
+ * a1 --> to
+ * a2 --> to_thread
+ */
+ .globl rt_hw_context_switch
+rt_hw_context_switch:
+ .globl rt_hw_context_switch_interrupt
+rt_hw_context_switch_interrupt:
+ /* check rt_thread_switch_interrupt_flag */
+ la t0, rt_thread_switch_interrupt_flag
+ lw t1, (t0)
+ li t2, 1
+ beq t1, t2, .reswitch
+ /* set rt_thread_switch_interrupt_flag=1 */
+ STORE t2, (t0)
+
+ /* update from_thread */
+ la t0, rt_interrupt_from_thread
+ STORE a0, (t0)
+
+.reswitch:
+ /* update to_thread */
+ la t0, rt_interrupt_to_thread
+ STORE a1, (t0)
+ /* set software interrupt */
+ li t0, 0xE080100C
+ lb t1, (t0)
+ li t2, 0x01
+ or t1, t1, t2
+ sb t1, (t0)
+
+ ret
+
+/*
+ * PendSV_Handler
+ */
+.global PendSV_Handler
+.type PendSV_Handler, %function
+PendSV_Handler:
+
+ /* check rt_thread_switch_interrupt_flag */
+ sw t0, (-4)(sp)
+ sw t1, (-8)(sp)
+ la t0, rt_thread_switch_interrupt_flag
+ lw t1, (t0)
+ beqz t1, .pendsv_exit
+
+ /* clear rt_thread_switch_interrupt_flag */
+ li t1, 0x0
+ sw t1, (t0)
+
+ /* check rt_interrupt_from_thread */
+ la t0, rt_interrupt_from_thread
+ lw t1, (t0)
+ beqz t1, .switch_to_thead
+
+ /* save from thread context */
+ lw t0, (-4)(sp)
+ lw t1, (-8)(sp)
+
+#ifdef ARCH_RISCV_FPU
+ addi sp, sp, -32 * FREGBYTES
+
+ FSTORE f0, 0 * FREGBYTES(sp)
+ FSTORE f1, 1 * FREGBYTES(sp)
+ FSTORE f2, 2 * FREGBYTES(sp)
+ FSTORE f3, 3 * FREGBYTES(sp)
+ FSTORE f4, 4 * FREGBYTES(sp)
+ FSTORE f5, 5 * FREGBYTES(sp)
+ FSTORE f6, 6 * FREGBYTES(sp)
+ FSTORE f7, 7 * FREGBYTES(sp)
+ FSTORE f8, 8 * FREGBYTES(sp)
+ FSTORE f9, 9 * FREGBYTES(sp)
+ FSTORE f10, 10 * FREGBYTES(sp)
+ FSTORE f11, 11 * FREGBYTES(sp)
+ FSTORE f12, 12 * FREGBYTES(sp)
+ FSTORE f13, 13 * FREGBYTES(sp)
+ FSTORE f14, 14 * FREGBYTES(sp)
+ FSTORE f15, 15 * FREGBYTES(sp)
+ FSTORE f16, 16 * FREGBYTES(sp)
+ FSTORE f17, 17 * FREGBYTES(sp)
+ FSTORE f18, 18 * FREGBYTES(sp)
+ FSTORE f19, 19 * FREGBYTES(sp)
+ FSTORE f20, 20 * FREGBYTES(sp)
+ FSTORE f21, 21 * FREGBYTES(sp)
+ FSTORE f22, 22 * FREGBYTES(sp)
+ FSTORE f23, 23 * FREGBYTES(sp)
+ FSTORE f24, 24 * FREGBYTES(sp)
+ FSTORE f25, 25 * FREGBYTES(sp)
+ FSTORE f26, 26 * FREGBYTES(sp)
+ FSTORE f27, 27 * FREGBYTES(sp)
+ FSTORE f28, 28 * FREGBYTES(sp)
+ FSTORE f29, 29 * FREGBYTES(sp)
+ FSTORE f30, 30 * FREGBYTES(sp)
+ FSTORE f31, 31 * FREGBYTES(sp)
+#endif
+
+ addi sp, sp, -32 * REGBYTES
+
+ STORE x1, 1 * REGBYTES(sp)
+ csrr x1, mepc
+ STORE x1, 0 * REGBYTES(sp)
+ csrr x1, mstatus
+ andi x1, x1, 8
+ beqz x1, .save_mpie
+ li x1, 0x80
+.save_mpie:
+ STORE x1, 2 * REGBYTES(sp)
+ /* x3 don't need save */
+ STORE x4, 4 * REGBYTES(sp)
+ STORE x5, 5 * REGBYTES(sp)
+ STORE x6, 6 * REGBYTES(sp)
+ STORE x7, 7 * REGBYTES(sp)
+ STORE x8, 8 * REGBYTES(sp)
+ STORE x9, 9 * REGBYTES(sp)
+ STORE x10, 10 * REGBYTES(sp)
+ STORE x11, 11 * REGBYTES(sp)
+ STORE x12, 12 * REGBYTES(sp)
+ STORE x13, 13 * REGBYTES(sp)
+ STORE x14, 14 * REGBYTES(sp)
+ STORE x15, 15 * REGBYTES(sp)
+ STORE x16, 16 * REGBYTES(sp)
+ STORE x17, 17 * REGBYTES(sp)
+ STORE x18, 18 * REGBYTES(sp)
+ STORE x19, 19 * REGBYTES(sp)
+ STORE x20, 20 * REGBYTES(sp)
+ STORE x21, 21 * REGBYTES(sp)
+ STORE x22, 22 * REGBYTES(sp)
+ STORE x23, 23 * REGBYTES(sp)
+ STORE x24, 24 * REGBYTES(sp)
+ STORE x25, 25 * REGBYTES(sp)
+ STORE x26, 26 * REGBYTES(sp)
+ STORE x27, 27 * REGBYTES(sp)
+ STORE x28, 28 * REGBYTES(sp)
+ STORE x29, 29 * REGBYTES(sp)
+ STORE x30, 30 * REGBYTES(sp)
+ STORE x31, 31 * REGBYTES(sp)
+
+ /* store from_thread sp */
+ la t0, rt_interrupt_from_thread
+ lw t0, (t0)
+ sw sp, (t0)
+
+.switch_to_thead:
+ /* restore to thread context
+ * sp(0) -> epc;
+ * sp(1) -> ra;
+ * sp(i) -> x(i+2)
+ */
+ la t0, rt_interrupt_to_thread
+ lw t0, (t0)
+ LOAD sp, (t0)
+
+ /* restore ra to mepc */
+ LOAD a1, 0 * REGBYTES(sp)
+ csrw mepc, a1
+ LOAD x1, 1 * REGBYTES(sp)
+
+ /* force to machin mode(MPP=11) */
+ li a1, 0x1880
+ csrs mstatus, a1
+ LOAD a1, 2 * REGBYTES(sp)
+ csrs mstatus, a1
+ /* x3 don't need restore */
+ LOAD x4, 4 * REGBYTES(sp)
+ LOAD x5, 5 * REGBYTES(sp)
+ LOAD x6, 6 * REGBYTES(sp)
+ LOAD x7, 7 * REGBYTES(sp)
+ LOAD x8, 8 * REGBYTES(sp)
+ LOAD x9, 9 * REGBYTES(sp)
+ LOAD x10, 10 * REGBYTES(sp)
+ LOAD x11, 11 * REGBYTES(sp)
+ LOAD x12, 12 * REGBYTES(sp)
+ LOAD x13, 13 * REGBYTES(sp)
+ LOAD x14, 14 * REGBYTES(sp)
+ LOAD x15, 15 * REGBYTES(sp)
+ LOAD x16, 16 * REGBYTES(sp)
+ LOAD x17, 17 * REGBYTES(sp)
+ LOAD x18, 18 * REGBYTES(sp)
+ LOAD x19, 19 * REGBYTES(sp)
+ LOAD x20, 20 * REGBYTES(sp)
+ LOAD x21, 21 * REGBYTES(sp)
+ LOAD x22, 22 * REGBYTES(sp)
+ LOAD x23, 23 * REGBYTES(sp)
+ LOAD x24, 24 * REGBYTES(sp)
+ LOAD x25, 25 * REGBYTES(sp)
+ LOAD x26, 26 * REGBYTES(sp)
+ LOAD x27, 27 * REGBYTES(sp)
+ LOAD x28, 28 * REGBYTES(sp)
+ LOAD x29, 29 * REGBYTES(sp)
+ LOAD x30, 30 * REGBYTES(sp)
+ LOAD x31, 31 * REGBYTES(sp)
+
+ addi sp, sp, 32 * REGBYTES
+
+#ifdef ARCH_RISCV_FPU
+ FLOAD f0, 0 * FREGBYTES(sp)
+ FLOAD f1, 1 * FREGBYTES(sp)
+ FLOAD f2, 2 * FREGBYTES(sp)
+ FLOAD f3, 3 * FREGBYTES(sp)
+ FLOAD f4, 4 * FREGBYTES(sp)
+ FLOAD f5, 5 * FREGBYTES(sp)
+ FLOAD f6, 6 * FREGBYTES(sp)
+ FLOAD f7, 7 * FREGBYTES(sp)
+ FLOAD f8, 8 * FREGBYTES(sp)
+ FLOAD f9, 9 * FREGBYTES(sp)
+ FLOAD f10, 10 * FREGBYTES(sp)
+ FLOAD f11, 11 * FREGBYTES(sp)
+ FLOAD f12, 12 * FREGBYTES(sp)
+ FLOAD f13, 13 * FREGBYTES(sp)
+ FLOAD f14, 14 * FREGBYTES(sp)
+ FLOAD f15, 15 * FREGBYTES(sp)
+ FLOAD f16, 16 * FREGBYTES(sp)
+ FLOAD f17, 17 * FREGBYTES(sp)
+ FLOAD f18, 18 * FREGBYTES(sp)
+ FLOAD f19, 19 * FREGBYTES(sp)
+ FLOAD f20, 20 * FREGBYTES(sp)
+ FLOAD f21, 21 * FREGBYTES(sp)
+ FLOAD f22, 22 * FREGBYTES(sp)
+ FLOAD f23, 23 * FREGBYTES(sp)
+ FLOAD f24, 24 * FREGBYTES(sp)
+ FLOAD f25, 25 * FREGBYTES(sp)
+ FLOAD f26, 26 * FREGBYTES(sp)
+ FLOAD f27, 27 * FREGBYTES(sp)
+ FLOAD f28, 28 * FREGBYTES(sp)
+ FLOAD f29, 29 * FREGBYTES(sp)
+ FLOAD f30, 30 * FREGBYTES(sp)
+ FLOAD f31, 31 * FREGBYTES(sp)
+
+ addi sp, sp, 32 * FREGBYTES
+#endif
+
+.pendsv_exit:
+ mret
+
+
+
diff --git a/libcpu/risc-v/t-head/e906/cpuport.c b/libcpu/risc-v/t-head/e906/cpuport.c
new file mode 100644
index 0000000000..5597aa237a
--- /dev/null
+++ b/libcpu/risc-v/t-head/e906/cpuport.c
@@ -0,0 +1,170 @@
+/*
+ * Copyright (c) 2006-2018, RT-Thread Development Team
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2020/08/20 zx.chen The T-HEAD RISC-V CPU E906 porting code.
+ */
+
+#include <rthw.h>
+#include <rtthread.h>
+
+#include "cpuport.h"
+
+#ifndef RT_USING_SMP
+volatile rt_ubase_t rt_interrupt_from_thread = 0;
+volatile rt_ubase_t rt_interrupt_to_thread = 0;
+volatile rt_uint32_t rt_thread_switch_interrupt_flag = 0;
+#endif
+
+struct rt_hw_stack_frame
+{
+ rt_ubase_t epc; /* epc - epc - program counter */
+ rt_ubase_t ra; /* x1 - ra - return address for jumps */
+ rt_ubase_t mstatus; /* - machine status register */
+ rt_ubase_t gp; /* x3 - gp - global pointer */
+ rt_ubase_t tp; /* x4 - tp - thread pointer */
+ rt_ubase_t t0; /* x5 - t0 - temporary register 0 */
+ rt_ubase_t t1; /* x6 - t1 - temporary register 1 */
+ rt_ubase_t t2; /* x7 - t2 - temporary register 2 */
+ rt_ubase_t s0_fp; /* x8 - s0/fp - saved register 0 or frame pointer */
+ rt_ubase_t s1; /* x9 - s1 - saved register 1 */
+ rt_ubase_t a0; /* x10 - a0 - return value or function argument 0 */
+ rt_ubase_t a1; /* x11 - a1 - return value or function argument 1 */
+ rt_ubase_t a2; /* x12 - a2 - function argument 2 */
+ rt_ubase_t a3; /* x13 - a3 - function argument 3 */
+ rt_ubase_t a4; /* x14 - a4 - function argument 4 */
+ rt_ubase_t a5; /* x15 - a5 - function argument 5 */
+ rt_ubase_t a6; /* x16 - a6 - function argument 6 */
+ rt_ubase_t a7; /* x17 - s7 - function argument 7 */
+ rt_ubase_t s2; /* x18 - s2 - saved register 2 */
+ rt_ubase_t s3; /* x19 - s3 - saved register 3 */
+ rt_ubase_t s4; /* x20 - s4 - saved register 4 */
+ rt_ubase_t s5; /* x21 - s5 - saved register 5 */
+ rt_ubase_t s6; /* x22 - s6 - saved register 6 */
+ rt_ubase_t s7; /* x23 - s7 - saved register 7 */
+ rt_ubase_t s8; /* x24 - s8 - saved register 8 */
+ rt_ubase_t s9; /* x25 - s9 - saved register 9 */
+ rt_ubase_t s10; /* x26 - s10 - saved register 10 */
+ rt_ubase_t s11; /* x27 - s11 - saved register 11 */
+ rt_ubase_t t3; /* x28 - t3 - temporary register 3 */
+ rt_ubase_t t4; /* x29 - t4 - temporary register 4 */
+ rt_ubase_t t5; /* x30 - t5 - temporary register 5 */
+ rt_ubase_t t6; /* x31 - t6 - temporary register 6 */
+#ifdef ARCH_RISCV_FPU
+ rv_floatreg_t f0; /* f0 */
+ rv_floatreg_t f1; /* f1 */
+ rv_floatreg_t f2; /* f2 */
+ rv_floatreg_t f3; /* f3 */
+ rv_floatreg_t f4; /* f4 */
+ rv_floatreg_t f5; /* f5 */
+ rv_floatreg_t f6; /* f6 */
+ rv_floatreg_t f7; /* f7 */
+ rv_floatreg_t f8; /* f8 */
+ rv_floatreg_t f9; /* f9 */
+ rv_floatreg_t f10; /* f10 */
+ rv_floatreg_t f11; /* f11 */
+ rv_floatreg_t f12; /* f12 */
+ rv_floatreg_t f13; /* f13 */
+ rv_floatreg_t f14; /* f14 */
+ rv_floatreg_t f15; /* f15 */
+ rv_floatreg_t f16; /* f16 */
+ rv_floatreg_t f17; /* f17 */
+ rv_floatreg_t f18; /* f18 */
+ rv_floatreg_t f19; /* f19 */
+ rv_floatreg_t f20; /* f20 */
+ rv_floatreg_t f21; /* f21 */
+ rv_floatreg_t f22; /* f22 */
+ rv_floatreg_t f23; /* f23 */
+ rv_floatreg_t f24; /* f24 */
+ rv_floatreg_t f25; /* f25 */
+ rv_floatreg_t f26; /* f26 */
+ rv_floatreg_t f27; /* f27 */
+ rv_floatreg_t f28; /* f28 */
+ rv_floatreg_t f29; /* f29 */
+ rv_floatreg_t f30; /* f30 */
+ rv_floatreg_t f31; /* f31 */
+#endif
+};
+
+/**
+ * This function will initialize thread stack
+ *
+ * @param tentry the entry of thread
+ * @param parameter the parameter of entry
+ * @param stack_addr the beginning stack address
+ * @param texit the function will be called when thread exit
+ *
+ * @return stack address
+ */
+rt_uint8_t *rt_hw_stack_init(void *tentry,
+ void *parameter,
+ rt_uint8_t *stack_addr,
+ void *texit)
+{
+ struct rt_hw_stack_frame *frame;
+ rt_uint8_t *stk;
+ int i;
+
+ stk = stack_addr + sizeof(rt_ubase_t);
+ stk = (rt_uint8_t *)RT_ALIGN_DOWN((rt_ubase_t)stk, REGBYTES);
+ stk -= sizeof(struct rt_hw_stack_frame);
+
+ frame = (struct rt_hw_stack_frame *)stk;
+
+ for (i = 0; i < sizeof(struct rt_hw_stack_frame) / sizeof(rt_ubase_t); i++)
+ {
+ ((rt_ubase_t *)frame)[i] = 0xdeadbeef;
+ }
+
+ frame->ra = (rt_ubase_t)texit;
+ frame->a0 = (rt_ubase_t)parameter;
+ frame->epc = (rt_ubase_t)tentry;
+
+ /* force to machine mode(MPP=11) and set MPIE to 1 */
+ frame->mstatus = 0x00007880;
+
+ return stk;
+}
+
+
+/**
+ * This function will disable global interrupt
+ *
+ * @param none
+ *
+ * @return zero
+ */
+
+rt_base_t rt_hw_interrupt_disable(void)
+{
+ __asm volatile("csrc mstatus, 8");
+ return 0;
+}
+
+/**
+ * This function will ennable global interrupt
+ *
+ * @param level not used
+ *
+ * @return none
+ */
+void rt_hw_interrupt_enable(rt_base_t level)
+{
+ __asm volatile("csrs mstatus, 8");
+}
+
+/** shutdown CPU */
+void rt_hw_cpu_shutdown()
+{
+ rt_uint32_t level;
+ rt_kprintf("shutdown...\n");
+
+ level = rt_hw_interrupt_disable();
+ while (level)
+ {
+ RT_ASSERT(0);
+ }
+}
diff --git a/libcpu/risc-v/t-head/e906/cpuport.h b/libcpu/risc-v/t-head/e906/cpuport.h
new file mode 100644
index 0000000000..90efc07653
--- /dev/null
+++ b/libcpu/risc-v/t-head/e906/cpuport.h
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2006-2018, RT-Thread Development Team
+ *
+ * SPDX-License-Identifier: Apache-2.0
+ *
+ * Change Logs:
+ * Date Author Notes
+ * 2020-08-20 zx.chen The first version
+ */
+
+#ifndef CPUPORT_H__
+#define CPUPORT_H__
+
+#include <rtconfig.h>
+
+/* bytes of register width */
+#ifdef ARCH_RISCV_64
+#define DFSTORE fsd
+#define DFLOAD fld
+#define SFSTORE fsw
+#define SFLOAD flw
+#define STORE sd
+#define LOAD ld
+#define REGBYTES 8
+#define SFREGBYTES 4
+#define DFREGBYTES 8
+#else
+#define DFSTORE fsd
+#define DFLOAD fld
+#define SFSTORE fsw
+#define SFLOAD flw
+#define STORE sw
+#define LOAD lw
+
+#define REGBYTES 4
+#define SFREGBYTES 4
+#define DFREGBYTES 8
+#endif
+
+#ifdef ARCH_RISCV_FPU
+#ifdef ARCH_RISCV_FPU_D
+#define FSTORE fsd
+#define FLOAD fld
+#define FREGBYTES 8
+#define rv_floatreg_t rt_int64_t
+#endif
+#ifdef ARCH_RISCV_FPU_S
+#define FSTORE fsw
+#define FLOAD flw
+#define FREGBYTES 4
+#define rv_floatreg_t rt_int32_t
+#endif
+#endif
+
+#endif