1 /*
2  * SPDX-License-Identifier: BSD-2-Clause
3  *
4  * Copyright (c) 2019 Western Digital Corporation or its affiliates.
5  *
6  * Authors:
7  *   Anup Patel <anup.patel@wdc.com>
8  */
9 
10 #ifndef __SBI_TRAP_H__
11 #define __SBI_TRAP_H__
12 
13 /* clang-format off */
14 
15 /** Index of zero member in sbi_trap_regs */
16 #define SBI_TRAP_REGS_zero			0
17 /** Index of ra member in sbi_trap_regs */
18 #define SBI_TRAP_REGS_ra			1
19 /** Index of sp member in sbi_trap_regs */
20 #define SBI_TRAP_REGS_sp			2
21 /** Index of gp member in sbi_trap_regs */
22 #define SBI_TRAP_REGS_gp			3
23 /** Index of tp member in sbi_trap_regs */
24 #define SBI_TRAP_REGS_tp			4
25 /** Index of t0 member in sbi_trap_regs */
26 #define SBI_TRAP_REGS_t0			5
27 /** Index of t1 member in sbi_trap_regs */
28 #define SBI_TRAP_REGS_t1			6
29 /** Index of t2 member in sbi_trap_regs */
30 #define SBI_TRAP_REGS_t2			7
31 /** Index of s0 member in sbi_trap_regs */
32 #define SBI_TRAP_REGS_s0			8
33 /** Index of s1 member in sbi_trap_regs */
34 #define SBI_TRAP_REGS_s1			9
35 /** Index of a0 member in sbi_trap_regs */
36 #define SBI_TRAP_REGS_a0			10
37 /** Index of a1 member in sbi_trap_regs */
38 #define SBI_TRAP_REGS_a1			11
39 /** Index of a2 member in sbi_trap_regs */
40 #define SBI_TRAP_REGS_a2			12
41 /** Index of a3 member in sbi_trap_regs */
42 #define SBI_TRAP_REGS_a3			13
43 /** Index of a4 member in sbi_trap_regs */
44 #define SBI_TRAP_REGS_a4			14
45 /** Index of a5 member in sbi_trap_regs */
46 #define SBI_TRAP_REGS_a5			15
47 /** Index of a6 member in sbi_trap_regs */
48 #define SBI_TRAP_REGS_a6			16
49 /** Index of a7 member in sbi_trap_regs */
50 #define SBI_TRAP_REGS_a7			17
51 /** Index of s2 member in sbi_trap_regs */
52 #define SBI_TRAP_REGS_s2			18
53 /** Index of s3 member in sbi_trap_regs */
54 #define SBI_TRAP_REGS_s3			19
55 /** Index of s4 member in sbi_trap_regs */
56 #define SBI_TRAP_REGS_s4			20
57 /** Index of s5 member in sbi_trap_regs */
58 #define SBI_TRAP_REGS_s5			21
59 /** Index of s6 member in sbi_trap_regs */
60 #define SBI_TRAP_REGS_s6			22
61 /** Index of s7 member in sbi_trap_regs */
62 #define SBI_TRAP_REGS_s7			23
63 /** Index of s8 member in sbi_trap_regs */
64 #define SBI_TRAP_REGS_s8			24
65 /** Index of s9 member in sbi_trap_regs */
66 #define SBI_TRAP_REGS_s9			25
67 /** Index of s10 member in sbi_trap_regs */
68 #define SBI_TRAP_REGS_s10			26
69 /** Index of s11 member in sbi_trap_regs */
70 #define SBI_TRAP_REGS_s11			27
71 /** Index of t3 member in sbi_trap_regs */
72 #define SBI_TRAP_REGS_t3			28
73 /** Index of t4 member in sbi_trap_regs */
74 #define SBI_TRAP_REGS_t4			29
75 /** Index of t5 member in sbi_trap_regs */
76 #define SBI_TRAP_REGS_t5			30
77 /** Index of t6 member in sbi_trap_regs */
78 #define SBI_TRAP_REGS_t6			31
79 /** Index of mepc member in sbi_trap_regs */
80 #define SBI_TRAP_REGS_mepc			32
81 /** Index of mstatus member in sbi_trap_regs */
82 #define SBI_TRAP_REGS_mstatus			33
83 /** Index of mstatusH member in sbi_trap_regs */
84 #define SBI_TRAP_REGS_mstatusH			34
85 /** Last member index in sbi_trap_regs */
86 #define SBI_TRAP_REGS_last			35
87 
88 /* clang-format on */
89 
90 /** Get offset of member with name 'x' in sbi_trap_regs */
91 #define SBI_TRAP_REGS_OFFSET(x) ((SBI_TRAP_REGS_##x) * __SIZEOF_POINTER__)
92 /** Size (in bytes) of sbi_trap_regs */
93 #define SBI_TRAP_REGS_SIZE SBI_TRAP_REGS_OFFSET(last)
94 
95 #ifndef __ASSEMBLY__
96 
97 #include <sbi/sbi_types.h>
98 
99 /** Representation of register state at time of trap/interrupt */
100 struct sbi_trap_regs {
101 	/** zero register state */
102 	unsigned long zero;
103 	/** ra register state */
104 	unsigned long ra;
105 	/** sp register state */
106 	unsigned long sp;
107 	/** gp register state */
108 	unsigned long gp;
109 	/** tp register state */
110 	unsigned long tp;
111 	/** t0 register state */
112 	unsigned long t0;
113 	/** t1 register state */
114 	unsigned long t1;
115 	/** t2 register state */
116 	unsigned long t2;
117 	/** s0 register state */
118 	unsigned long s0;
119 	/** s1 register state */
120 	unsigned long s1;
121 	/** a0 register state */
122 	unsigned long a0;
123 	/** a1 register state */
124 	unsigned long a1;
125 	/** a2 register state */
126 	unsigned long a2;
127 	/** a3 register state */
128 	unsigned long a3;
129 	/** a4 register state */
130 	unsigned long a4;
131 	/** a5 register state */
132 	unsigned long a5;
133 	/** a6 register state */
134 	unsigned long a6;
135 	/** a7 register state */
136 	unsigned long a7;
137 	/** s2 register state */
138 	unsigned long s2;
139 	/** s3 register state */
140 	unsigned long s3;
141 	/** s4 register state */
142 	unsigned long s4;
143 	/** s5 register state */
144 	unsigned long s5;
145 	/** s6 register state */
146 	unsigned long s6;
147 	/** s7 register state */
148 	unsigned long s7;
149 	/** s8 register state */
150 	unsigned long s8;
151 	/** s9 register state */
152 	unsigned long s9;
153 	/** s10 register state */
154 	unsigned long s10;
155 	/** s11 register state */
156 	unsigned long s11;
157 	/** t3 register state */
158 	unsigned long t3;
159 	/** t4 register state */
160 	unsigned long t4;
161 	/** t5 register state */
162 	unsigned long t5;
163 	/** t6 register state */
164 	unsigned long t6;
165 	/** mepc register state */
166 	unsigned long mepc;
167 	/** mstatus register state */
168 	unsigned long mstatus;
169 	/** mstatusH register state (only for 32-bit) */
170 	unsigned long mstatusH;
171 } __packed;
172 
173 struct sbi_scratch;
174 
175 int sbi_trap_redirect(struct sbi_trap_regs *regs, struct sbi_scratch *scratch,
176 		      ulong epc, ulong cause, ulong tval);
177 
178 void sbi_trap_handler(struct sbi_trap_regs *regs, struct sbi_scratch *scratch);
179 
180 #endif
181 
182 #endif
183