1 #ifndef ZEPHYR_INCLUDE_ARCH_NIOS2_NIOS2_H_
2 #define ZEPHYR_INCLUDE_ARCH_NIOS2_NIOS2_H_
3
4 /* SPDX-License-Identifier: Xnet */
5
6 /******************************************************************************
7 * *
8 * License Agreement *
9 * *
10 * Copyright (c) 2008 Altera Corporation, San Jose, California, USA. *
11 * All rights reserved. *
12 * *
13 * Permission is hereby granted, free of charge, to any person obtaining a *
14 * copy of this software and associated documentation files (the "Software"), *
15 * to deal in the Software without restriction, including without limitation *
16 * the rights to use, copy, modify, merge, publish, distribute, sublicense, *
17 * and/or sell copies of the Software, and to permit persons to whom the *
18 * Software is furnished to do so, subject to the following conditions: *
19 * *
20 * The above copyright notice and this permission notice shall be included in *
21 * all copies or substantial portions of the Software. *
22 * *
23 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR *
24 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, *
25 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE *
26 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER *
27 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING *
28 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER *
29 * DEALINGS IN THE SOFTWARE. *
30 * *
31 * This agreement shall be governed in all respects by the laws of the State *
32 * of California and by the laws of the United States of America. *
33 * *
34 ******************************************************************************/
35
36 /*
37 * This header provides processor specific macros for accessing the Nios2
38 * control registers.
39 */
40
41 #ifdef __cplusplus
42 extern "C"
43 {
44 #endif /* __cplusplus */
45
46 /*
47 * Number of available IRQs in internal interrupt controller.
48 */
49 #define NIOS2_NIRQ 32
50
51 /* Size in bits of registers */
52 #define SYSTEM_BUS_WIDTH 32
53
54 #ifndef _ASMLANGUAGE
55
56 #include <zephyr/types.h>
57 #include <zephyr/arch/cpu.h>
58 #include <zephyr/sys/sys_io.h>
59
60 /*
61 * Functions for accessing select Nios II general-purpose registers.
62 */
63
64 /* ET (Exception Temporary) register */
_nios2_read_et(void)65 static inline uint32_t _nios2_read_et(void)
66 {
67 uint32_t et;
68
69 __asm__("mov %0, et" : "=r" (et));
70 return et;
71 }
72
_nios2_write_et(uint32_t et)73 static inline void _nios2_write_et(uint32_t et)
74 {
75 __asm__ volatile("mov et, %z0" : : "rM" (et));
76 }
77
_nios2_read_sp(void)78 static inline uint32_t _nios2_read_sp(void)
79 {
80 uint32_t sp;
81
82 __asm__("mov %0, sp" : "=r" (sp));
83 return sp;
84 }
85
86 /*
87 * Functions for useful processor instructions.
88 */
z_nios2_break(void)89 static inline void z_nios2_break(void)
90 {
91 __asm__ volatile("break");
92 }
93
_nios2_report_stack_overflow(void)94 static inline void _nios2_report_stack_overflow(void)
95 {
96 __asm__ volatile("break 3");
97 }
98
99 /*
100 * Low-level cache management functions
101 */
_nios2_dcache_addr_flush(void * addr)102 static inline void _nios2_dcache_addr_flush(void *addr)
103 {
104 __asm__ volatile ("flushda (%0)" :: "r" (addr));
105 }
106
z_nios2_dcache_flush(uint32_t offset)107 static inline void z_nios2_dcache_flush(uint32_t offset)
108 {
109 __asm__ volatile ("flushd (%0)" :: "r" (offset));
110 }
111
z_nios2_icache_flush(uint32_t offset)112 static inline void z_nios2_icache_flush(uint32_t offset)
113 {
114 __asm__ volatile ("flushi %0" :: "r" (offset));
115 }
116
z_nios2_pipeline_flush(void)117 static inline void z_nios2_pipeline_flush(void)
118 {
119 __asm__ volatile ("flushp");
120 }
121
122 /*
123 * Functions for reading/writing control registers
124 */
125
126 enum nios2_creg {
127 NIOS2_CR_STATUS = 0,
128 NIOS2_CR_ESTATUS = 1,
129 NIOS2_CR_BSTATUS = 2,
130 NIOS2_CR_IENABLE = 3,
131 NIOS2_CR_IPENDING = 4,
132 NIOS2_CR_CPUID = 5,
133 /* 6 is reserved */
134 NIOS2_CR_EXCEPTION = 7,
135 NIOS2_CR_PTEADDR = 8,
136 NIOS2_CR_TLBACC = 9,
137 NIOS2_CR_TLBMISC = 10,
138 NIOS2_CR_ECCINJ = 11,
139 NIOS2_CR_BADADDR = 12,
140 NIOS2_CR_CONFIG = 13,
141 NIOS2_CR_MPUBASE = 14,
142 NIOS2_CR_MPUACC = 15
143 };
144
145 /* XXX I would prefer to define these as static inline functions for
146 * type checking purposes. However if -O0 is used (i.e. CONFIG_DEBUG is on)
147 * we get errors "Control register number must be in range 0-31 for
148 * __builtin_rdctl" with the following code:
149 *
150 * static inline uint32_t z_nios2_creg_read(enum nios2_creg reg)
151 * {
152 * return __builtin_rdctl(reg);
153 * }
154 *
155 * This compiles just fine with -Os.
156 */
157 #define z_nios2_creg_read(reg) __builtin_rdctl(reg)
158 #define z_nios2_creg_write(reg, val) __builtin_wrctl(reg, val)
159
160 #define z_nios2_get_register_address(base, regnum) \
161 ((void *)(((uint8_t *)base) + ((regnum) * (SYSTEM_BUS_WIDTH / 8))))
162
_nios2_reg_write(void * base,int regnum,uint32_t data)163 static inline void _nios2_reg_write(void *base, int regnum, uint32_t data)
164 {
165 sys_write32(data,
166 (mm_reg_t)z_nios2_get_register_address(base, regnum));
167 }
168
_nios2_reg_read(void * base,int regnum)169 static inline uint32_t _nios2_reg_read(void *base, int regnum)
170 {
171 return sys_read32((mm_reg_t)z_nios2_get_register_address(base, regnum));
172 }
173
174 #endif /* _ASMLANGUAGE */
175
176 /*
177 * Nios II control registers that are always present
178 */
179 #define NIOS2_STATUS status
180 #define NIOS2_ESTATUS estatus
181 #define NIOS2_BSTATUS bstatus
182 #define NIOS2_IENABLE ienable
183 #define NIOS2_IPENDING ipending
184 #define NIOS2_CPUID cpuid
185
186 /*
187 * Bit masks & offsets for Nios II control registers.
188 * The presence and size of a field is sometimes dependent on the Nios II
189 * configuration. Bit masks for every possible field and the maximum size of
190 * that field are defined.
191 *
192 * All bit-masks are expressed relative to the position
193 * of the data with a register. To read data that is LSB-
194 * aligned, the register read data should be masked, then
195 * right-shifted by the designated "OFST" macro value. The
196 * opposite should be used for register writes when starting
197 * with LSB-aligned data.
198 */
199
200 /* STATUS, ESTATUS, BSTATUS, and SSTATUS registers */
201 #define NIOS2_STATUS_PIE_MSK (0x00000001)
202 #define NIOS2_STATUS_PIE_OFST (0)
203 #define NIOS2_STATUS_U_MSK (0x00000002)
204 #define NIOS2_STATUS_U_OFST (1)
205 #define NIOS2_STATUS_EH_MSK (0x00000004)
206 #define NIOS2_STATUS_EH_OFST (2)
207 #define NIOS2_STATUS_IH_MSK (0x00000008)
208 #define NIOS2_STATUS_IH_OFST (3)
209 #define NIOS2_STATUS_IL_MSK (0x000003f0)
210 #define NIOS2_STATUS_IL_OFST (4)
211 #define NIOS2_STATUS_CRS_MSK (0x0000fc00)
212 #define NIOS2_STATUS_CRS_OFST (10)
213 #define NIOS2_STATUS_PRS_MSK (0x003f0000)
214 #define NIOS2_STATUS_PRS_OFST (16)
215 #define NIOS2_STATUS_NMI_MSK (0x00400000)
216 #define NIOS2_STATUS_NMI_OFST (22)
217 #define NIOS2_STATUS_RSIE_MSK (0x00800000)
218 #define NIOS2_STATUS_RSIE_OFST (23)
219 #define NIOS2_STATUS_SRS_MSK (0x80000000)
220 #define NIOS2_STATUS_SRS_OFST (31)
221
222 /* EXCEPTION register */
223 #define NIOS2_EXCEPTION_REG_CAUSE_MASK (0x0000007c)
224 #define NIOS2_EXCEPTION_REG_CAUSE_OFST (2)
225 #define NIOS2_EXCEPTION_REG_ECCFTL_MASK (0x80000000)
226 #define NIOS2_EXCEPTION_REG_ECCFTL_OFST (31)
227
228 /* PTEADDR (Page Table Entry Address) register */
229 #define NIOS2_PTEADDR_REG_VPN_OFST 2
230 #define NIOS2_PTEADDR_REG_VPN_MASK 0x3ffffc
231 #define NIOS2_PTEADDR_REG_PTBASE_OFST 22
232 #define NIOS2_PTEADDR_REG_PTBASE_MASK 0xffc00000
233
234 /* TLBACC (TLB Access) register */
235 #define NIOS2_TLBACC_REG_PFN_OFST 0
236 #define NIOS2_TLBACC_REG_PFN_MASK 0xfffff
237 #define NIOS2_TLBACC_REG_G_OFST 20
238 #define NIOS2_TLBACC_REG_G_MASK 0x100000
239 #define NIOS2_TLBACC_REG_X_OFST 21
240 #define NIOS2_TLBACC_REG_X_MASK 0x200000
241 #define NIOS2_TLBACC_REG_W_OFST 22
242 #define NIOS2_TLBACC_REG_W_MASK 0x400000
243 #define NIOS2_TLBACC_REG_R_OFST 23
244 #define NIOS2_TLBACC_REG_R_MASK 0x800000
245 #define NIOS2_TLBACC_REG_C_OFST 24
246 #define NIOS2_TLBACC_REG_C_MASK 0x1000000
247 #define NIOS2_TLBACC_REG_IG_OFST 25
248 #define NIOS2_TLBACC_REG_IG_MASK 0xfe000000
249
250 /* TLBMISC (TLB Miscellaneous) register */
251 #define NIOS2_TLBMISC_REG_D_OFST 0
252 #define NIOS2_TLBMISC_REG_D_MASK 0x1
253 #define NIOS2_TLBMISC_REG_PERM_OFST 1
254 #define NIOS2_TLBMISC_REG_PERM_MASK 0x2
255 #define NIOS2_TLBMISC_REG_BAD_OFST 2
256 #define NIOS2_TLBMISC_REG_BAD_MASK 0x4
257 #define NIOS2_TLBMISC_REG_DBL_OFST 3
258 #define NIOS2_TLBMISC_REG_DBL_MASK 0x8
259 #define NIOS2_TLBMISC_REG_PID_OFST 4
260 #define NIOS2_TLBMISC_REG_PID_MASK 0x3fff0
261 #define NIOS2_TLBMISC_REG_WE_OFST 18
262 #define NIOS2_TLBMISC_REG_WE_MASK 0x40000
263 #define NIOS2_TLBMISC_REG_RD_OFST 19
264 #define NIOS2_TLBMISC_REG_RD_MASK 0x80000
265 #define NIOS2_TLBMISC_REG_WAY_OFST 20
266 #define NIOS2_TLBMISC_REG_WAY_MASK 0xf00000
267 #define NIOS2_TLBMISC_REG_EE_OFST 24
268 #define NIOS2_TLBMISC_REG_EE_MASK 0x1000000
269
270 /* ECCINJ (ECC Inject) register */
271 #define NIOS2_ECCINJ_REG_RF_OFST 0
272 #define NIOS2_ECCINJ_REG_RF_MASK 0x3
273 #define NIOS2_ECCINJ_REG_ICTAG_OFST 2
274 #define NIOS2_ECCINJ_REG_ICTAG_MASK 0xc
275 #define NIOS2_ECCINJ_REG_ICDAT_OFST 4
276 #define NIOS2_ECCINJ_REG_ICDAT_MASK 0x30
277 #define NIOS2_ECCINJ_REG_DCTAG_OFST 6
278 #define NIOS2_ECCINJ_REG_DCTAG_MASK 0xc0
279 #define NIOS2_ECCINJ_REG_DCDAT_OFST 8
280 #define NIOS2_ECCINJ_REG_DCDAT_MASK 0x300
281 #define NIOS2_ECCINJ_REG_TLB_OFST 10
282 #define NIOS2_ECCINJ_REG_TLB_MASK 0xc00
283 #define NIOS2_ECCINJ_REG_DTCM0_OFST 12
284 #define NIOS2_ECCINJ_REG_DTCM0_MASK 0x3000
285 #define NIOS2_ECCINJ_REG_DTCM1_OFST 14
286 #define NIOS2_ECCINJ_REG_DTCM1_MASK 0xc000
287 #define NIOS2_ECCINJ_REG_DTCM2_OFST 16
288 #define NIOS2_ECCINJ_REG_DTCM2_MASK 0x30000
289 #define NIOS2_ECCINJ_REG_DTCM3_OFST 18
290 #define NIOS2_ECCINJ_REG_DTCM3_MASK 0xc0000
291
292 /* CONFIG register */
293 #define NIOS2_CONFIG_REG_PE_MASK (0x00000001)
294 #define NIOS2_CONFIG_REG_PE_OFST (0)
295 #define NIOS2_CONFIG_REG_ANI_MASK (0x00000002)
296 #define NIOS2_CONFIG_REG_ANI_OFST (1)
297 #define NIOS2_CONFIG_REG_ECCEN_MASK (0x00000004)
298 #define NIOS2_CONFIG_REG_ECCEN_OFST (2)
299 #define NIOS2_CONFIG_REG_ECCEXC_MASK (0x00000008)
300 #define NIOS2_CONFIG_REG_ECCEXC_OFST (3)
301
302 /* MPUBASE (MPU Base Address) Register */
303 #define NIOS2_MPUBASE_D_MASK (0x00000001)
304 #define NIOS2_MPUBASE_D_OFST (0)
305 #define NIOS2_MPUBASE_INDEX_MASK (0x0000003e)
306 #define NIOS2_MPUBASE_INDEX_OFST (1)
307 #define NIOS2_MPUBASE_BASE_ADDR_MASK (0xffffffc0)
308 #define NIOS2_MPUBASE_BASE_ADDR_OFST (6)
309
310 /* MPUACC (MPU Access) Register */
311 #define NIOS2_MPUACC_LIMIT_MASK (0xffffffc0)
312 #define NIOS2_MPUACC_LIMIT_OFST (6)
313 #define NIOS2_MPUACC_MASK_MASK (0xffffffc0)
314 #define NIOS2_MPUACC_MASK_OFST (6)
315 #define NIOS2_MPUACC_C_MASK (0x00000020)
316 #define NIOS2_MPUACC_C_OFST (5)
317 #define NIOS2_MPUACC_PERM_MASK (0x0000001c)
318 #define NIOS2_MPUACC_PERM_OFST (2)
319 #define NIOS2_MPUACC_RD_MASK (0x00000002)
320 #define NIOS2_MPUACC_RD_OFST (1)
321 #define NIOS2_MPUACC_WR_MASK (0x00000001)
322 #define NIOS2_MPUACC_WR_OFST (0)
323
324 #ifdef __cplusplus
325 }
326 #endif /* __cplusplus */
327
328 #endif /* ZEPHYR_INCLUDE_ARCH_NIOS2_NIOS2_H_ */
329