1/* This file is part of the ATMEL AVR32-UC3-SoftwareFramework-1.6.0 Release */ 2 3/*This file is prepared for Doxygen automatic documentation generation.*/ 4/*! \file ********************************************************************* 5 * 6 * \brief Exception and interrupt vectors. 7 * 8 * This file maps all events supported by an AVR32. 9 * 10 * - Compiler: GNU GCC for AVR32 11 * - Supported devices: All AVR32 devices with an INTC module can be used. 12 * - AppNote: 13 * 14 * \author Atmel Corporation: http://www.atmel.com \n 15 * Support and FAQ: http://support.atmel.no/ 16 * 17 ******************************************************************************/ 18 19/* Copyright (c) 2009 Atmel Corporation. All rights reserved. 20 * 21 * Redistribution and use in source and binary forms, with or without 22 * modification, are permitted provided that the following conditions are met: 23 * 24 * 1. Redistributions of source code must retain the above copyright notice, this 25 * list of conditions and the following disclaimer. 26 * 27 * 2. Redistributions in binary form must reproduce the above copyright notice, 28 * this list of conditions and the following disclaimer in the documentation 29 * and/or other materials provided with the distribution. 30 * 31 * 3. The name of Atmel may not be used to endorse or promote products derived 32 * from this software without specific prior written permission. 33 * 34 * 4. This software may only be redistributed and used in connection with an Atmel 35 * AVR product. 36 * 37 * THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR IMPLIED 38 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 39 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE 40 * EXPRESSLY AND SPECIFICALLY DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR 41 * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES 42 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 43 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND 44 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 45 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 46 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE 47 * 48 */ 49 50#if !__AVR32_UC__ && !__AVR32_AP__ 51 #error Implementation of the AVR32 architecture not supported by the INTC driver. 52#endif 53 54 55#include <avr32/io.h> 56 57 58//! @{ 59//! \verbatim 60 61 62 .section .exception, "ax", @progbits 63 64 65// Start of Exception Vector Table. 66 67 // EVBA must be aligned with a power of two strictly greater than the EVBA- 68 // relative offset of the last vector. 69 .balign 0x200 70 71 // Export symbol. 72 .global _evba 73 .type _evba, @function 74_evba: 75 76 .org 0x000 77 // Unrecoverable Exception. 78_handle_Unrecoverable_Exception: 79 rjmp $ 80 81 .org 0x004 82 // TLB Multiple Hit. 83_handle_TLB_Multiple_Hit: 84 rjmp $ 85 86 .org 0x008 87 // Bus Error Data Fetch. 88_handle_Bus_Error_Data_Fetch: 89 rjmp $ 90 91 .org 0x00C 92 // Bus Error Instruction Fetch. 93_handle_Bus_Error_Instruction_Fetch: 94 rjmp $ 95 96 .org 0x010 97 // NMI. 98_handle_NMI: 99 rjmp $ 100 101 .org 0x014 102 // Instruction Address. 103_handle_Instruction_Address: 104 rjmp $ 105 106 .org 0x018 107 // ITLB Protection. 108_handle_ITLB_Protection: 109 rjmp $ 110 111 .org 0x01C 112 // Breakpoint. 113_handle_Breakpoint: 114 rjmp $ 115 116 .org 0x020 117 // Illegal Opcode. 118_handle_Illegal_Opcode: 119 rjmp $ 120 121 .org 0x024 122 // Unimplemented Instruction. 123_handle_Unimplemented_Instruction: 124 rjmp $ 125 126 .org 0x028 127 // Privilege Violation. 128_handle_Privilege_Violation: 129 rjmp $ 130 131 .org 0x02C 132 // Floating-Point: UNUSED IN AVR32UC and AVR32AP. 133_handle_Floating_Point: 134 rjmp $ 135 136 .org 0x030 137 // Coprocessor Absent: UNUSED IN AVR32UC. 138_handle_Coprocessor_Absent: 139 rjmp $ 140 141 .org 0x034 142 // Data Address (Read). 143_handle_Data_Address_Read: 144 rjmp $ 145 146 .org 0x038 147 // Data Address (Write). 148_handle_Data_Address_Write: 149 rjmp $ 150 151 .org 0x03C 152 // DTLB Protection (Read). 153_handle_DTLB_Protection_Read: 154 rjmp $ 155 156 .org 0x040 157 // DTLB Protection (Write). 158_handle_DTLB_Protection_Write: 159 rjmp $ 160 161 .org 0x044 162 // DTLB Modified: UNUSED IN AVR32UC. 163_handle_DTLB_Modified: 164 rjmp $ 165 166 .org 0x050 167 // ITLB Miss. 168_handle_ITLB_Miss: 169 rjmp $ 170 171 .org 0x060 172 // DTLB Miss (Read). 173_handle_DTLB_Miss_Read: 174 rjmp $ 175 176 .org 0x070 177 // DTLB Miss (Write). 178_handle_DTLB_Miss_Write: 179 rjmp $ 180 181 .org 0x100 182 // Supervisor Call. 183_handle_Supervisor_Call: 184 rjmp $ 185 186 187// Interrupt support. 188// The interrupt controller must provide the offset address relative to EVBA. 189// Important note: 190// All interrupts call a C function named _get_interrupt_handler. 191// This function will read group and interrupt line number to then return in 192// R12 a pointer to a user-provided interrupt handler. 193 194 .balign 4 195 196_int0: 197 mov r12, 0 // Pass the int_level parameter to the _get_interrupt_handler function. 198 call _get_interrupt_handler 199 cp.w r12, 0 // Get the pointer to the interrupt handler returned by the function. 200 breq _spint0 // If this was not a spurious interrupt (R12 != NULL), jump to the handler. 201 call rt_interrupt_enter 202 icall r12 203 call rt_interrupt_leave 204 ssrf AVR32_SR_GM_OFFSET /* Disable global interrupt */ 205 lda.w r12, rt_interrupt_nest /* Is nested interrupt? */ 206 ld.w r11, r12[0] 207 cp.w r11, 0 208 brne _spint0 209 lda.w r12, rt_thread_switch_interrupt_flag /* Is thread switch required? */ 210 ld.w r11, r12[0] 211 cp.w r11, 1 212 breq rt_hw_context_switch_interrupt_do 213_spint0: 214 csrf AVR32_SR_GM_OFFSET /* Enable global interrupt */ 215 rete // If this was a spurious interrupt (R12 == NULL), return from event handler. 216 217 218_int1: 219 mov r12, 1 // Pass the int_level parameter to the _get_interrupt_handler function. 220 call _get_interrupt_handler 221 cp.w r12, 0 // Get the pointer to the interrupt handler returned by the function. 222 breq _spint1 // If this was not a spurious interrupt (R12 != NULL), jump to the handler. 223 call rt_interrupt_enter 224 icall r12 225 call rt_interrupt_leave 226 ssrf AVR32_SR_GM_OFFSET /* Disable global interrupt */ 227 lda.w r12, rt_interrupt_nest /* Is nested interrupt? */ 228 ld.w r11, r12[0] 229 cp.w r11, 0 230 brne _spint1 231 lda.w r12, rt_thread_switch_interrupt_flag /* Is thread switch required? */ 232 ld.w r11, r12[0] 233 cp.w r11, 1 234 breq rt_hw_context_switch_interrupt_do 235_spint1: 236 csrf AVR32_SR_GM_OFFSET /* Enable global interrupt */ 237 rete // If this was a spurious interrupt (R12 == NULL), return from event handler. 238 239 240_int2: 241 mov r12, 2 // Pass the int_level parameter to the _get_interrupt_handler function. 242 call _get_interrupt_handler 243 cp.w r12, 0 // Get the pointer to the interrupt handler returned by the function. 244 breq _spint2 // If this was not a spurious interrupt (R12 != NULL), jump to the handler. 245 call rt_interrupt_enter 246 icall r12 247 call rt_interrupt_leave 248 ssrf AVR32_SR_GM_OFFSET /* Disable global interrupt */ 249 lda.w r12, rt_interrupt_nest /* Is nested interrupt? */ 250 ld.w r11, r12[0] 251 cp.w r11, 0 252 brne _spint2 253 lda.w r12, rt_thread_switch_interrupt_flag /* Is thread switch required? */ 254 ld.w r11, r12[0] 255 cp.w r11, 1 256 breq rt_hw_context_switch_interrupt_do 257_spint2: 258 csrf AVR32_SR_GM_OFFSET /* Enable global interrupt */ 259 rete // If this was a spurious interrupt (R12 == NULL), return from event handler. 260 261 262_int3: 263 mov r12, 3 // Pass the int_level parameter to the _get_interrupt_handler function. 264 call _get_interrupt_handler 265 cp.w r12, 0 // Get the pointer to the interrupt handler returned by the function. 266 breq _spint3 // If this was not a spurious interrupt (R12 != NULL), jump to the handler. 267 call rt_interrupt_enter 268 icall r12 269 call rt_interrupt_leave 270 ssrf AVR32_SR_GM_OFFSET /* Disable global interrupt */ 271 lda.w r12, rt_interrupt_nest /* Is nested interrupt? */ 272 ld.w r11, r12[0] 273 cp.w r11, 0 274 brne _spint3 275 lda.w r12, rt_thread_switch_interrupt_flag /* Is thread switch required? */ 276 ld.w r11, r12[0] 277 cp.w r11, 1 278 breq rt_hw_context_switch_interrupt_do 279_spint3: 280 csrf AVR32_SR_GM_OFFSET /* Enable global interrupt */ 281 rete // If this was a spurious interrupt (R12 == NULL), return from event handler. 282 283 284rt_hw_context_switch_interrupt_do: 285 mov r11, 0 286 st.w r12[0], r11 /* Clear rt_thread_switch_interrupt_flag */ 287 stm --sp, r0-r7 /* Push R0-R7 */ 288 lda.w r12, rt_interrupt_from_thread /* Get old thread SP */ 289 ld.w r12, r12[0] 290 lda.w r11, rt_interrupt_to_thread /* Get new thread SP */ 291 ld.w r11, r11[0] 292 st.w r12[0], sp /* Store old thead SP */ 293 ld.w sp, r11[0] /* Load new thread SP */ 294 ldm sp++, r0-r7 /* Pop R0-R7 (new thread) */ 295 rete /* RETE pops R8-R12, LR, PC, SR automatically */ 296 297 298// Constant data area. 299 300 .balign 4 301 302 // Values to store in the interrupt priority registers for the various interrupt priority levels. 303 // The interrupt priority registers contain the interrupt priority level and 304 // the EVBA-relative interrupt vector offset. 305 .global ipr_val 306 .type ipr_val, @object 307ipr_val: 308 .word (AVR32_INTC_INT0 << AVR32_INTC_IPR_INTLEVEL_OFFSET) | (_int0 - _evba),\ 309 (AVR32_INTC_INT1 << AVR32_INTC_IPR_INTLEVEL_OFFSET) | (_int1 - _evba),\ 310 (AVR32_INTC_INT2 << AVR32_INTC_IPR_INTLEVEL_OFFSET) | (_int2 - _evba),\ 311 (AVR32_INTC_INT3 << AVR32_INTC_IPR_INTLEVEL_OFFSET) | (_int3 - _evba) 312 313 314//! \endverbatim 315//! @} 316