1/*
2 * FreeRTOS Kernel V11.1.0
3 * Copyright (C) 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved.
4 *
5 * SPDX-License-Identifier: MIT AND BSD-3-Clause
6 *
7 * Permission is hereby granted, free of charge, to any person obtaining a copy of
8 * this software and associated documentation files (the "Software"), to deal in
9 * the Software without restriction, including without limitation the rights to
10 * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
11 * the Software, and to permit persons to whom the Software is furnished to do so,
12 * subject to the following conditions:
13 *
14 * The above copyright notice and this permission notice shall be included in all
15 * copies or substantial portions of the Software.
16 *
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
19 * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
20 * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
21 * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
22 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
23 *
24 * https://www.FreeRTOS.org
25 * https://github.com/FreeRTOS
26 *
27 */
28
29/*This file is prepared for Doxygen automatic documentation generation.*/
30/*! \file *********************************************************************
31 *
32 * \brief Exception and interrupt vectors.
33 *
34 * This file maps all events supported by an AVR32UC.
35 *
36 * - Compiler:           GNU GCC for AVR32
37 * - Supported devices:  All AVR32UC devices with an INTC module can be used.
38 * - AppNote:
39 *
40 * \author               Atmel Corporation (Now Microchip):
41 *                                        https://www.microchip.com \n
42 *                       Support and FAQ: https://www.microchip.com/support/
43 *
44 ******************************************************************************/
45
46/*
47 * Copyright (c) 2007, Atmel Corporation All rights reserved.
48 *
49 * Redistribution and use in source and binary forms, with or without
50 * modification, are permitted provided that the following conditions are met:
51 *
52 * 1. Redistributions of source code must retain the above copyright notice,
53 * this list of conditions and the following disclaimer.
54 *
55 * 2. Redistributions in binary form must reproduce the above copyright notice,
56 * this list of conditions and the following disclaimer in the documentation
57 * and/or other materials provided with the distribution.
58 *
59 * 3. The name of ATMEL may not be used to endorse or promote products derived
60 * from this software without specific prior written permission.
61 *
62 * THIS SOFTWARE IS PROVIDED BY ATMEL ``AS IS'' AND ANY EXPRESS OR IMPLIED
63 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
64 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE EXPRESSLY AND
65 * SPECIFICALLY DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT,
66 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
67 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
68 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
69 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
70 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
71 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
72 */
73
74
75#include <avr32/io.h>
76#include "intc.h"
77
78
79//! @{
80//! \verbatim
81
82
83  .section  .exception, "ax", @progbits
84
85
86// Start of Exception Vector Table.
87
88  // EVBA must be aligned with a power of two strictly greater than the EVBA-
89  // relative offset of the last vector.
90  .balign 0x200
91
92  // Export symbol.
93  .global _evba
94  .type _evba, @function
95_evba:
96
97        .org  0x000
98        // Unrecoverable Exception.
99_handle_Unrecoverable_Exception:
100        rjmp $
101
102        .org  0x004
103        // TLB Multiple Hit: UNUSED IN AVR32UC.
104_handle_TLB_Multiple_Hit:
105        rjmp $
106
107        .org  0x008
108        // Bus Error Data Fetch.
109_handle_Bus_Error_Data_Fetch:
110        rjmp $
111
112        .org  0x00C
113         // Bus Error Instruction Fetch.
114_handle_Bus_Error_Instruction_Fetch:
115        rjmp $
116
117        .org  0x010
118        // NMI.
119_handle_NMI:
120        rjmp $
121
122        .org  0x014
123        // Instruction Address.
124_handle_Instruction_Address:
125        rjmp $
126
127        .org  0x018
128        // ITLB Protection.
129_handle_ITLB_Protection:
130        rjmp $
131
132        .org  0x01C
133        // Breakpoint.
134_handle_Breakpoint:
135        rjmp $
136
137        .org  0x020
138        // Illegal Opcode.
139_handle_Illegal_Opcode:
140        rjmp $
141
142        .org  0x024
143        // Unimplemented Instruction.
144_handle_Unimplemented_Instruction:
145        rjmp $
146
147        .org  0x028
148        // Privilege Violation.
149_handle_Privilege_Violation:
150        rjmp $
151
152        .org  0x02C
153        // Floating-Point: UNUSED IN AVR32UC.
154_handle_Floating_Point:
155        rjmp $
156
157        .org  0x030
158        // Coprocessor Absent: UNUSED IN AVR32UC.
159_handle_Coprocessor_Absent:
160        rjmp $
161
162        .org  0x034
163        // Data Address (Read).
164_handle_Data_Address_Read:
165        rjmp $
166
167        .org  0x038
168        // Data Address (Write).
169_handle_Data_Address_Write:
170        rjmp $
171
172        .org  0x03C
173        // DTLB Protection (Read).
174_handle_DTLB_Protection_Read:
175        rjmp $
176
177        .org  0x040
178        // DTLB Protection (Write).
179_handle_DTLB_Protection_Write:
180        rjmp $
181
182        .org  0x044
183        // DTLB Modified: UNUSED IN AVR32UC.
184_handle_DTLB_Modified:
185        rjmp $
186
187        .org  0x050
188        // ITLB Miss: UNUSED IN AVR32UC.
189_handle_ITLB_Miss:
190        rjmp $
191
192        .org  0x060
193        // DTLB Miss (Read): UNUSED IN AVR32UC.
194_handle_DTLB_Miss_Read:
195        rjmp $
196
197        .org  0x070
198        // DTLB Miss (Write): UNUSED IN AVR32UC.
199_handle_DTLB_Miss_Write:
200        rjmp $
201
202        .org  0x100
203        // Supervisor Call.
204_handle_Supervisor_Call:
205        lda.w   pc, SCALLYield
206
207
208// Interrupt support.
209// The interrupt controller must provide the offset address relative to EVBA.
210// Important note:
211//   All interrupts call a C function named _get_interrupt_handler.
212//   This function will read group and interrupt line number to then return in
213//   R12 a pointer to a user-provided interrupt handler.
214
215  .balign 4
216
217_int0:
218  // R8-R12, LR, PC and SR are automatically pushed onto the system stack by the
219  // CPU upon interrupt entry.
220#if 1 // B1832: interrupt stack changed to exception stack if exception is detected.
221  mfsr    r12, AVR32_SR
222  bfextu  r12, r12, AVR32_SR_M0_OFFSET, AVR32_SR_M0_SIZE + AVR32_SR_M1_SIZE + AVR32_SR_M2_SIZE
223  cp.w    r12, 0b110
224  brlo    _int0_normal
225  lddsp   r12, sp[0 * 4]
226  stdsp   sp[6 * 4], r12
227  lddsp   r12, sp[1 * 4]
228  stdsp   sp[7 * 4], r12
229  lddsp   r12, sp[3 * 4]
230  sub     sp, -6 * 4
231  rete
232_int0_normal:
233#endif
234  mov     r12, 0  // Pass the int_lev parameter to the _get_interrupt_handler function.
235  call    _get_interrupt_handler
236  cp.w    r12, 0  // Get the pointer to the interrupt handler returned by the function.
237  movne   pc, r12 // If this was not a spurious interrupt (R12 != NULL), jump to the handler.
238  rete            // If this was a spurious interrupt (R12 == NULL), return from event handler.
239
240_int1:
241  // R8-R12, LR, PC and SR are automatically pushed onto the system stack by the
242  // CPU upon interrupt entry.
243#if 1 // B1832: interrupt stack changed to exception stack if exception is detected.
244  mfsr    r12, AVR32_SR
245  bfextu  r12, r12, AVR32_SR_M0_OFFSET, AVR32_SR_M0_SIZE + AVR32_SR_M1_SIZE + AVR32_SR_M2_SIZE
246  cp.w    r12, 0b110
247  brlo    _int1_normal
248  lddsp   r12, sp[0 * 4]
249  stdsp   sp[6 * 4], r12
250  lddsp   r12, sp[1 * 4]
251  stdsp   sp[7 * 4], r12
252  lddsp   r12, sp[3 * 4]
253  sub     sp, -6 * 4
254  rete
255_int1_normal:
256#endif
257  mov     r12, 1  // Pass the int_lev parameter to the _get_interrupt_handler function.
258  call    _get_interrupt_handler
259  cp.w    r12, 0  // Get the pointer to the interrupt handler returned by the function.
260  movne   pc, r12 // If this was not a spurious interrupt (R12 != NULL), jump to the handler.
261  rete            // If this was a spurious interrupt (R12 == NULL), return from event handler.
262
263_int2:
264  // R8-R12, LR, PC and SR are automatically pushed onto the system stack by the
265  // CPU upon interrupt entry.
266#if 1 // B1832: interrupt stack changed to exception stack if exception is detected.
267  mfsr    r12, AVR32_SR
268  bfextu  r12, r12, AVR32_SR_M0_OFFSET, AVR32_SR_M0_SIZE + AVR32_SR_M1_SIZE + AVR32_SR_M2_SIZE
269  cp.w    r12, 0b110
270  brlo    _int2_normal
271  lddsp   r12, sp[0 * 4]
272  stdsp   sp[6 * 4], r12
273  lddsp   r12, sp[1 * 4]
274  stdsp   sp[7 * 4], r12
275  lddsp   r12, sp[3 * 4]
276  sub     sp, -6 * 4
277  rete
278_int2_normal:
279#endif
280  mov     r12, 2  // Pass the int_lev parameter to the _get_interrupt_handler function.
281  call    _get_interrupt_handler
282  cp.w    r12, 0  // Get the pointer to the interrupt handler returned by the function.
283  movne   pc, r12 // If this was not a spurious interrupt (R12 != NULL), jump to the handler.
284  rete            // If this was a spurious interrupt (R12 == NULL), return from event handler.
285
286_int3:
287  // R8-R12, LR, PC and SR are automatically pushed onto the system stack by the
288  // CPU upon interrupt entry.
289#if 1 // B1832: interrupt stack changed to exception stack if exception is detected.
290  mfsr    r12, AVR32_SR
291  bfextu  r12, r12, AVR32_SR_M0_OFFSET, AVR32_SR_M0_SIZE + AVR32_SR_M1_SIZE + AVR32_SR_M2_SIZE
292  cp.w    r12, 0b110
293  brlo    _int3_normal
294  lddsp   r12, sp[0 * 4]
295  stdsp   sp[6 * 4], r12
296  lddsp   r12, sp[1 * 4]
297  stdsp   sp[7 * 4], r12
298  lddsp   r12, sp[3 * 4]
299  sub     sp, -6 * 4
300  rete
301_int3_normal:
302#endif
303  mov     r12, 3  // Pass the int_lev parameter to the _get_interrupt_handler function.
304  call    _get_interrupt_handler
305  cp.w    r12, 0  // Get the pointer to the interrupt handler returned by the function.
306  movne   pc, r12 // If this was not a spurious interrupt (R12 != NULL), jump to the handler.
307  rete            // If this was a spurious interrupt (R12 == NULL), return from event handler.
308
309
310// Constant data area.
311
312  .balign 4
313
314  // Values to store in the interrupt priority registers for the various interrupt priority levels.
315  // The interrupt priority registers contain the interrupt priority level and
316  // the EVBA-relative interrupt vector offset.
317  .global ipr_val
318  .type ipr_val, @object
319ipr_val:
320  .word (INT0 << AVR32_INTC_IPR0_INTLEV_OFFSET) | (_int0 - _evba),\
321        (INT1 << AVR32_INTC_IPR0_INTLEV_OFFSET) | (_int1 - _evba),\
322        (INT2 << AVR32_INTC_IPR0_INTLEV_OFFSET) | (_int2 - _evba),\
323        (INT3 << AVR32_INTC_IPR0_INTLEV_OFFSET) | (_int3 - _evba)
324
325
326//! \endverbatim
327//! @}
328