1 /*
2  * SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 #ifndef __RVRUNTIME_FRAMES_H__
8 #define __RVRUNTIME_FRAMES_H__
9 
10 /* Align a value up to nearest n-byte boundary, where n is a power of 2. */
11 #define ALIGNUP(n, val) (((val) + (n) - 1) & -(n))
12 
13 #ifdef STRUCT_BEGIN
14 #undef STRUCT_BEGIN
15 #undef STRUCT_FIELD
16 #undef STRUCT_AFIELD
17 #undef STRUCT_END
18 #endif
19 
20 #if defined(_ASMLANGUAGE) || defined(__ASSEMBLER__)
21 #ifdef __clang__
22 #define STRUCT_BEGIN                            .set RV_STRUCT_OFFSET, 0
23 #define STRUCT_FIELD(ctype,size,asname,name)    .set asname, RV_STRUCT_OFFSET; .set RV_STRUCT_OFFSET, asname + size
24 #define STRUCT_AFIELD(ctype,size,asname,name,n) .set asname, RV_STRUCT_OFFSET;\
25                                                 .set RV_STRUCT_OFFSET, asname + (size)*(n);
26 #define STRUCT_END(sname)                       .set sname##Size, RV_STRUCT_OFFSET;
27 #else // __clang__
28 #define STRUCT_BEGIN            .pushsection .text; .struct 0
29 #define STRUCT_FIELD(ctype,size,asname,name)    asname: .space  size
30 #define STRUCT_AFIELD(ctype,size,asname,name,n) asname: .space  (size)*(n)
31 #define STRUCT_END(sname)       sname##Size:; .popsection
32 #endif // __clang__
33 #else
34 #define STRUCT_BEGIN            typedef struct {
35 #define STRUCT_FIELD(ctype,size,asname,name)    ctype   name;
36 #define STRUCT_AFIELD(ctype,size,asname,name,n) ctype   name[n];
37 #define STRUCT_END(sname)       } sname;
38 #endif
39 
40 /*
41 -------------------------------------------------------------------------------
42    INTERRUPT/EXCEPTION STACK FRAME FOR A EXCEPTION OR NESTED INTERRUPT
43 -------------------------------------------------------------------------------
44 */
45 STRUCT_BEGIN
46 STRUCT_FIELD (long, 4, RV_STK_MEPC,    mepc)       /* Machine Exception Program Counter */
47 STRUCT_FIELD (long, 4, RV_STK_RA,      ra)         /* Return address */
48 STRUCT_FIELD (long, 4, RV_STK_SP,      sp)         /* Stack pointer */
49 STRUCT_FIELD (long, 4, RV_STK_GP,      gp)         /* Global pointer */
50 STRUCT_FIELD (long, 4, RV_STK_TP,      tp)         /* Thread pointer */
51 STRUCT_FIELD (long, 4, RV_STK_T0,      t0)         /* Temporary/alternate link register */
52 STRUCT_FIELD (long, 4, RV_STK_T1,      t1)         /* t1-2: Temporaries */
53 STRUCT_FIELD (long, 4, RV_STK_T2,      t2)
54 STRUCT_FIELD (long, 4, RV_STK_S0,      s0)         /* Saved register/frame pointer */
55 STRUCT_FIELD (long, 4, RV_STK_S1,      s1)         /* Saved register */
56 STRUCT_FIELD (long, 4, RV_STK_A0,      a0)         /* a0-1: Function arguments/return address */
57 STRUCT_FIELD (long, 4, RV_STK_A1,      a1)
58 STRUCT_FIELD (long, 4, RV_STK_A2,      a2)         /* a2-7: Function arguments */
59 STRUCT_FIELD (long, 4, RV_STK_A3,      a3)
60 STRUCT_FIELD (long, 4, RV_STK_A4,      a4)
61 STRUCT_FIELD (long, 4, RV_STK_A5,      a5)
62 STRUCT_FIELD (long, 4, RV_STK_A6,      a6)
63 STRUCT_FIELD (long, 4, RV_STK_A7,      a7)
64 STRUCT_FIELD (long, 4, RV_STK_S2,      s2)         /* s2-11: Saved registers */
65 STRUCT_FIELD (long, 4, RV_STK_S3,      s3)
66 STRUCT_FIELD (long, 4, RV_STK_S4,      s4)
67 STRUCT_FIELD (long, 4, RV_STK_S5,      s5)
68 STRUCT_FIELD (long, 4, RV_STK_S6,      s6)
69 STRUCT_FIELD (long, 4, RV_STK_S7,      s7)
70 STRUCT_FIELD (long, 4, RV_STK_S8,      s8)
71 STRUCT_FIELD (long, 4, RV_STK_S9,      s9)
72 STRUCT_FIELD (long, 4, RV_STK_S10,     s10)
73 STRUCT_FIELD (long, 4, RV_STK_S11,     s11)
74 STRUCT_FIELD (long, 4, RV_STK_T3,      t3)         /* t3-6: Temporaries */
75 STRUCT_FIELD (long, 4, RV_STK_T4,      t4)
76 STRUCT_FIELD (long, 4, RV_STK_T5,      t5)
77 STRUCT_FIELD (long, 4, RV_STK_T6,      t6)
78 STRUCT_FIELD (long, 4, RV_STK_MSTATUS, mstatus)    /* Machine Status */
79 STRUCT_FIELD (long, 4, RV_STK_MTVEC,   mtvec)      /* Machine Trap-Vector Base Address */
80 STRUCT_FIELD (long, 4, RV_STK_MCAUSE,  mcause)     /* Machine Trap Cause */
81 STRUCT_FIELD (long, 4, RV_STK_MTVAL,   mtval)      /* Machine Trap Value */
82 STRUCT_FIELD (long, 4, RV_STK_MHARTID, mhartid)    /* Hardware Thread ID in machine mode */
83 STRUCT_END(RvExcFrame)
84 
85 #if defined(_ASMLANGUAGE) || defined(__ASSEMBLER__)
86 #define RV_STK_SZ1     RvExcFrameSize
87 #else
88 #define RV_STK_SZ1     sizeof(RvExcFrame)
89 #endif
90 
91 /*
92  * Exception stack frame size, after align up to 16 bytes boundary
93  */
94 #define RV_STK_FRMSZ    (ALIGNUP(0x10, RV_STK_SZ1))
95 
96 #endif /* #ifndef __RVRUNTIME_FRAMES_H__ */
97